Thursday, September 25, 2014

is email dead?

it was a rainy night; cold too. i got the call from 5th precinct that another protocol had taken the long trip to nowheresville.

"whadda we got here, charlie?" i asked o'malley, the flatfoot in charge of keeping the press hounds at bay.

"not sure, sir" he mewled back. something was wrong. o'malley was shaken up. something was definitely wrong.

"okay, let's take a look at the corpse." o'malley lifted up the sheet and i gasped. damn if it wasn't ol' mr. killer app himself: email.

i scouted the apartment for leads. this was gonna be a tough one. mr. email had fallen in with a rough crowd late in life. pictures of nigerian princes covered the walls. unused S/MIME keys littered the floor. poor guy, once a king, now an afterthought.

"hey! we caught this guy snooping around!" one of the shirts said pushing a punk kid in front of him. "go on & tell 'em your name"

"he doesn't have to," i say, "i'd recognize young mr. orkut anywhere. say... weren't you lost in the amazon jungle or something?"

"amazon? what kind of chump do you take me for, copper?" said the young punk. "i've an honest job down in rio. ask anybody."

"okay orkut. i might just do that. but what with wave and buzz missing in action... you really want me talking to facebook?"

"okay copper, i'll tell ya' what ya wanna know. but i don't know what happened to buzz. i heard he retired with google reader."

that last bit hit like a punch in the gut. i had forgot about reader's "retirement." they say it was her decision, but no one knows for sure. when you can't keep a classy dame like google reader safe on the streets and louts like g+ are running the show rather than cooling the sheets at sun quinten? it stinks, i tell you. like yesterday's session keys.

the coroner finally arrived and started poking around the body. "HOLY SMOKES! HE'S NOT DEAD!" he says.

sure enough, his breath just barely fogs the broken screen of my iPhone 6+. "o'malley! get your guys to clear out the press, we need room to get mr. email to the hearse.. er.. ambulance."

so there i am leaning over the old jake, helping the coroner wrestle him onto a gurney. and then it hits me, his breath smells bad; real bad, the kind of bad you don't get naturally, like a mix of hong kong rot-gut and half refined texas sweet crude. i used to catch a whiff of that smell whenever i went to the talkies cinema off shoreline road. it smelled... like microsoft.

"hey jay," i call to the coroner as he's wheeling email out the door, "while you're down at the hospital, get one of the saw-bones to test the old man for exchange."

"EXCHANGE!?" he cries back, "you don't think he's mixed up with the bellevue mob, do you?"

"i'm not sure, jay. but test him anyway," i answer, "call it a hunch, i think i might have caught wind of a rat."

the rest of the night goes like a million other nights: buried in paperwork and drowned by cheap scotch. and as the sun rises through the acrid smog of silicon valley, i find myself lost in thought mumbling to myself, "microsoft, it can't be you, can it?"

Wednesday, August 20, 2014

On Internet Enabled Watches

This is a quick post to encapsulate a few thoughts I've been having about SmartWatches. In case you haven't heard, SmartWatches are going to be next year's "break-out hit technology," and have been for the last several years. It shouldn't surprise people I'm a little bearish on the SmartWatch concept as it stands today, but I think it's less to do with the market and more to do with specific limitations of existing technology.

In short, SmartWatches are a neat idea, but they need to hit reasonably low price-points with appropriate performance before we'll start seeing them strapped to everyone's wrists.

The HP-01 Image courtesy Wikimedia Commons
But first a little history... Wrist watches were apparently a thing as far back as Elizabethan England (who knew?) and were worn almost exclusively by women until the early 20th century. Men were apparently big fans of pocket watches in the old days. Which sort of got me thinking... are mobile phones the modern pocket watch? I can't tell you how many people I know who use their phones as watches. In the early 70's digital watches appeared and were almost immediately lampooned by Douglas Adams in the Hitch-Hiker's Guide to the Galaxy.

The first "Smart Watch" I can find reference to is the Hewlett-Packard HP-01. Look at this thing! Is it not a marvel to behold!? Seriously, I was a kid when this thing came out and remember thinking it was the coolest thing since sliced bread and David Cassidy combined.

Users of the HP-01 could use a proto-stylus to enter reverse polish notation programs to run on the device. Tracking fuel consumption on a small airplane was the canonical example the HP folks gave. Every second it would multiply elapsed time by your fuel usage rate and display how much fuel it thought you had in your fuel tanks. I once wrote a program on a HP-01 simulator to display the current mission elapsed time for the Pathfinder rover on Mars. Cool beans if you're tech geek like me, but with a price tag of $650, it's not a mainstream product.
Handspring Treo 300.  From Wikimedia Commons (again)

And for the second bit of history, let's look at the Palm Treo. This bad boy hit the stores in 2002 (though this is a picture of the Treo 300, which didn't come out until 2003.) Wait! Weren't we talking about watches? Why are we looking at a Treo?

The Treo was the first successful PalmOS device that didn't need to be connected to your PC. Sure, the user experience of syncing with networked servers sucked and required additional software. But it was possible and a lot of people did it.

Nike Fuel + Band.
Image from Wikimedia Commons
And now let's look at existing SmartWatches. This is the Nike Fuel. It's one of the new breed of wearable activity trackers targeting fitness peoples. Oh wait. Hold on. Nike couldn't sell enough of these to make it worth their while. Nevermind. (That being said, there was a pretty stiff after-market of these things after Nike axed the project. So it's not like there's zero market.)

And here's the Pebble watch. It seems to be everyone's current favourite, despite offerings from Samsung and the rumoured iWatch waiting to destroy the market with it's Apple flavoured consumer electronics dominance. The pebble comes with "regular" BlueTooth and BlueTooth LE
Pebble. From Wikimedia Commons
(Low Energy) so in theory, you should be able to pair it with your PC or you iPhone. But getting it to pair with your PC requires mad Python hacking skillz.

And don't get me started about the Samsung offerings. Not only do they only pair with smart-phones, they only pair with a couple of different models of Samsung smart-phones. No thank you Samsung. I don't want my SmartWatch purchase to be useless if I drop my SmartPhone in the bathtub.

So what's your point?

Thanks for staying with me as I bounced around between seemingly unrelated bits of consumer electronics footnotes. I guess what I'm trying to say is:

  1. These things are still pretty expensive. Nike had a customer base and still couldn't push these things out the door for $150.
  2. The experience of using a SmartWatch sucks. Not for us, of course. If you're reading this, you're probably one of the techno-elite who repartitions the logical volume groups on your Linux desktop for fun on the weekend. But if your have to go through the bluetooth pairing dance to get your watch to talk to your phone, you've probably lost half your market.
  3. People want to get at their data, they don't care that it's on their PC, on their phone or in the cloud. They want to turn on their phone and pull up a picture of their grand-kids. Or have their watch send fitness / movement data to a program somewhere.
But SmartWatches as a product class aren't a complete bust. That's one of the reasons I threw in the bit about the Treo. You don't see any Treos on the street anymore, but if you look at the iPhone and various Android phones, you see features that were pioneered by Handspring. And I think the SmartWatch market is where the SmartPhone market was thirteen years ago. We've had a few market entrants, but their experience mostly sucks and they're too expensive. Maybe next year we'll see the "Treo" of SmartWatches. Maybe it'll be Pebble releasing a slightly cheaper product with a better user experience.

What makes a better experience?

Users want their devices to "just work." You can probably get away with forcing people to do the BlueTooth pairing dance if you correctly communicate the security and privacy reasons behind pairing. But after that, they want their device to operate with zero additional complexity. What does this mean?
  1. For the sake of all that is holy, allow your device to pair with more than one computer. I have a cluster of PCs at the office and a cluster of PCs at the home. I want my SmartWatch to work with all of them. Don't artificially restrict me to only working with one PC.
  2. Consider making deals with WiFi Access Point manufacturers to put BlueToothLE support in their firmware. Many modern access points have USB ports and there are several BTLE USB dongles out there. Wouldn't it be simpler if your Access Point provided your BTLE dial-tone? In theory you could have a software component on the access point that relayed application layer messages to local PCs or cloud services.
  3. Put as much of the configuration on the big screen as possible. This should be a no-brainer, but we still see people making products that require you to use the small screen on the wearable device. No. Just... No.
Anyway... I hope this has been interesting to someone out in the world. Feel free to drop me comments via email or twitter. Special shout-out to @jonathanstark and @balmer who ignored my twitter-brand snarkiness to have as close to a real conversation as you can have about consumer electronics 140 characters at a time.

Monday, July 28, 2014

the terminals shine

getting ready to start my day, doing a couple little tasks while watching AMC's Halt & Catch Fire in the background. i really love the show; mostly 'cause it's like re-living the microcomputer revolution. kids today don't know what it was like. every month something new and innovative came out. and most of the things that came out withered and died 'cause they were too expensive or the market for the product didn't really exist.

but at the time, that didn't matter too much. it was a crazy time and there were no rules. or rather, people were more willing to creatively bend them. i was on the tech side of the fence in the 80s and was privileged to work on firmware, application programs and even an operating system to compete with MacOS and Microsoft Windows. i wrote a lot of very cool code, but strangely, the only thing that's still in use from back in the day is some code for older ATM machines & a hack i wrote for DOS / Netware.

the common mis-conception of the 80's was sofware was written by lone coders working feverishly through the night. and that's not completely untrue. but there were plenty of small organizations, three or four coders working together to get stuff done. (and remember, this is back when version control was flinging floppies around the room.)

one of my favorite bits of writing from the time is this bit from Geoffrey James:

"The computer center is empty,
Silent except for the whine of the cooling fans.
I walk the rows of CPUs,
My skin prickling with magnetic flux.
I open a door, cold and hard,
And watch the lights dancing on the panels.
A machine without soul, men call it,
But its soul is the sweat of my comrades,
Within it lie the years of our lives,
Disappointment, friendship, sadness, joy,
The algorithmic exaltations,
The long nights filled with thankless toil,
I hear the echoes of sighs and laughter,
And in the darkened offices
The terminals shine like stars." --from The Tao of Programming

Saturday, July 19, 2014

on enlightenment

had an amazing dream this morning where i reached enlightenment.

starting out as a visit to my childhood home in ohio, i remarked to myself how it looked different than what i remembered. further investigation revealed portions of it had been taken over as a dormitory by wright state university (apparently it was also much larger than i remember.)

randomly wandering into the downstairs family room, "i" split into multiple individuals representing not only the different parts of myself, but avatars of friends, family and mentors responsible for shaping my personality with Charles Baker playing the role of the friendly trickster and Peg AtKisson carrying a sword, representing my intellect.

my task was to complete (within a fixed amount of time) an introductory multiple choice test and then query 5 (sometimes 6) guardians of the experience of humanity (librarians of the akashic record?) to discover the secret to enlightenment. agriculture, mechanics (tool building), programming, and music/literature were the guardians i remember.

after being confused by a few questions, the part of me that was memory whispered a strategy in my ear. treating it like a logic puzzle, i asked each guardian what i had to ask the others to achieve enlightenment. apparently this was a good strategy, and in retrospect makes me wonder if half of the guardians always told the truth and the others always told lies.

the last couple of answers were unintelligible jibberish, but memory helped me out here and i just repeated the lines fed to me (thanks, mnemeosyne!)

when you reach enlightenment, there's apparently a very nice cocktail party where all the pieces of your psyche mingle, catch up on gossip and generally have a good time. i commented to one of the guardians that i didn't feel especially more enlightened and was told that i'm not the one who was enlightened.

it turns out that the i that i perceive myself to be is not the i that is enlightened. upon attaining enlightenment, every bit of you is enlightened and it's an experience that the conscious ego can't comprehend (maybe that's why it looks like a cocktail party where the rest of my society of mind is having a good time.)

Tom Deplonty will be happy to hear one of his compositions was being performed at the party. So Tom... you're apparently going to pen the soundtrack for enlightenment (no pressure.)

Wednesday, July 9, 2014

The Persistent Myth of Product

This morning i had to take it a little easy. I burned myself out last night debugging and needed a small break. So i spent a little extra time sipping my coffee, enjoying my garden and reading a random book from my young adulthood. The book i picked up from my bookshelf was Michael Tomcsyk's "The Home Computer Wars." It's a first-hand account of Commodore's rise as a home computing juggernaut in the early 1980's. Written in an informal, first-person style, it's a surprisingly fun read; sort of like a romance novel for tech geeks.

One of the things I noticed about the book was how few rules there were to making "hit computer products" in the early 80's. The market was still developing and everyone seemed to have their pet theories for how to build the next, great thing. The locations involved, Sunnyvale and Santa Clara, made me think of the companies I worked for in the valley; how their approach to structuring a business was straight out of the 80's and how that's probably why they're no longer around.

I'm thinking mostly of PalmSource, the software spin-off of Palm, Inc. PalmSource was structured in a pretty standard way: executive management at the top, different divisions for sales, marketing, operations and engineering. We worked in matrix style teams with product definition the responsibility of the team's product manager. I don't want to dispiarage anyone on the PalmSource team; with very few exceptions everyone involved were highly competent professionals. But in retrospect, I believe PalmSource's organization and rigid responsibilities set it up for failure.

My team was working on the software to secure apps on the device from other, potentially rogue apps. I was happy with the work I was doing, but the software security work I was doing quickly laid bare a sad truth: our product manager had no idea why we were including security features.

People who have implemented security features on products will probably understand how frustrating this can be. Security features frequently do things like pop up dialogue boxes or cause certain types of data accesses to fail. As feature developers, we can dial up the access protection and annoying interactions or we can dial them down. It's not exactly true that good user interface and good security are mutually exclusive, but it's frequently the case (especially in the first rev of a product.)

So as developers, we cheat. We have our software refer to configuration files to say how frequently we should annoy the user and what resources we don't let other programs access. It's great for the software developer, but it's really just kicking the can down the road. Someone, somewhere needs to make a decision about how often you annoy the user. And it's a horrible choice. If you err on the side of caution, people hate your user interface. If you err on the side of convenience, you open yourself up to vulnerabilities.

At PalmSource, we convinced ourselves that our product manager would make these decisions or would be the conduit for customer requirements. But we made a bit of a mistake. Our product manager, while very competent in the general handheld space, had about zero experience with security features and not a whole lot of experience evaluating user experience. And this was the guy who was going to make the decision in the usable vs. secure issue.

I don't blame our product manager. He was a good guy put in a situation outside his area of expertise. It did take him a little longer to recognize this than it should have, but he had a lot on his plate. As engineers, we had no way to report this issue to upper management because our management was actively hostile toward security features. (Seriously, my manager once fell asleep during a meeting when we were trying to explain the problem to him.) We had no authority to make a decision on our own, because PalmSource's corporate culture was "product tells engineering what to build, not the other way around."

In several old-school companies, the product management group is responsible for surveying the market, making educated guesses about economic trends and customer behaviour and developing a target for price and performance. Usually (hopefully) guided by the executive team's directives on ROI and general location in the price / quality matrix, they help engineering prioritize features for the products under development.

But it's increasingly important for product managers to have a deep knowledge of the product features. In the old days when the division between product marketing and engineering was established, products were effectively widgets with five or ten bullet-point features. The "quality" of your product was defined by the presence of a bullet-pointed feature or it's relative feature. Product managers didn't need to know what the features did, only that we had one.

Fast forward to the modern era... The iPhone finally got the term "user experience" on the lips of executives. Just-In-Time manufacturing is the default rather than the exception and various SaaS successes have people talking about how to provide value through an API. Selling software in Sili Valley is less about putting bullet points on boxes and more about adapting your API to fit into someone else's value chain.

So why do we still have product managers that aren't also sales engineers? Why did I, as an engineer, have to explain the business ramifications of poor design choices to our product manager? Why did I have to use back-channels to find engineers in our customer's organizations and ask *them* about their business objectives?

And I think the answer is "the Persistent Myth of Product."

There's a truism in marketing that to make money you can do two things: figure out what people want and make that, or figure out what you're good at making and make people want to buy it. In the early 80's, the vast majority of the populous wasn't familiar with what computers could do. It's safe to say people didn't know what they wanted. Sure, we all thought we wanted a device with more flashy graphics, a better keyboard and more memory. But that's just the "computer fetishist" view of computing products. What we needed to know in the early 80's was how these devices were going to fit into our lives.

And while I like to grouse about Apple's developer support from time to time, it's hard to argue they didn't do an EXCELLENT job communicating how Apple products fit into people's lives. When the Macintosh came out, IBM offered a series of ham-fisted windowing programs to counter the Mac's "ease of use" argument; ditto for Digital Research; ditto for Microsoft. I believe IBM and Microsoft survived because they understood the lucrative enterprise market.

In the early 2000's, Apple struck again with the iPod. It wasn't the first personal audio player, but it was the first to not treat the user interface as a bolt-on afterthought. And Apple did another EXCELLENT job communicating how the iPod fit in a user's life: buy an iPod, take your music with you. By comparison, Diamond and Creative were selling Rios and NOMADs like you would sell a PC component: by listing bullet points on the side of a box.

Traditional product managers are taught to identify key features of a product segment and then communicate those features to an engineering team. They are taught that all you have to do is make a widget slightly cheaper or slightly better and the world will beat a path to your door. And in many segments this is true.

But it's not true in software. Or at least it's not true for organizations that don't want to rely on dumb luck.

"Product" is not defined by a market, but by observing people, figuring out how technology can affect their lives, building it and communicating that change to the end user. Don't depend on an existing market to tell you what to build. Depend on your customer's need first. Or... figure out what you're good at building and figure out how it fits into your customer's life.

Monday, June 30, 2014

A Conservative Justification for Single-Payer Health Insurance

People who know me are sometimes surprised when I describe myself as "conservative on some issues." And to be sure, I'm mostly a raging lefty. But I've always wondered why "conservatives" oppose single payer systems. I believe a single-payer system like Canada's would be a net benefit to the United States and could be justified by "Buckley-esque" conservative ideals.

In the United States the cost of treating acute conditions in the uninsured comes from the public purse. So let's say you don't have health insurance and you're rendered unconscious in a car crash. You're taken to the hospital emergency room and revived. The hospital has already spent money on you before they could determine you couldn't pay for the treatment. So you're stabilized, shown the door and usually, the local county picks up the bill.

That's a bit of a contrived example, but it clearly shows what happens: if someone doesn't have insurance to cover the cost of medical care, it's the state that picks up the tab. Something that's a little more likely is due to some unforeseen circumstance or a previously hidden chronic condition, you need acute care. Maybe it's an accident around the home. Maybe you didn't have cash to pay for an annual colonoscopy and you have abdominal pain from stage 3 colon cancer. Treating a patient for complications due to late term cancer is considerably more expensive than detection and prevention. Put another way, appeals to the public purse are minimized if indigent and low income workers who cannot otherwise afford effective health care are provided with preventative care.

But in this country, we tie health insurance to employment. This made a lot more sense fifty years ago when the cost of health care was lower and employee turnover was lower. Health insurance was originally offered by employees as an incentive, but as costs increased it became more of an expectation. This is bad because employer provided health insurance introduces an artificial attachment to under-productive employment. That is, instead of working the job that best uses your talents or allows you to maximally contribute to economic productivity, you go for the job that offers the best health care.

In my own case, I left a "good job" to pursue an entrepreneurial opportunity. I was lucky I had enough cash to pay for COBRA coverage while my new business venture became a going concern. Other people will not be in this situation. A worker who thinks of a new process or a new invention will be hampered in their pursuit by the cost of health insurance. Minimizing the out-of-pocket expense for entrepreneurs during the initial "start up" phase of their business, gives them more "runway" to go from concept to minimum viable product. Reducing the cost of entrepreneurship increases the incidence of start-ups; increasing the incidence of start-ups increases the likelihood productivity-enhancing intellectual property is delivered to the marketplace.

And from the perspective of a mature enterprise, health care costs are now the single fastest growing expense and the least easy to predict. When I was an entrepreneur, our health care costs doubled every year as benefits went down slightly. The current system benefits large employers with larger risk pools at the expense of small and medium sized enterprises who must deal with unpredictable increases in health care coverage.

Also, the United States has the third highest per-capita health expenditure while enjoying the lowest rate of positive health outcomes of the top 17 industrialized nations. If we could replicate the Canadian model, shifting to a single-payer model would facilitate better negotiation for end consumers and more consistent pricing for health care services and medicines.

This is a just an outline of a real argument, but I think it presents the basics. We're already in a situation where the public pays for some coverage: emergency rooms, medicare, medicaid. Tying insurance coverage to employment encourages under-productive employment and minimizes the United States' competitive stance with respect to productivity-enhancing intellectual property which is frequently developed by small organizations with no stake in existing solutions.

Single-payer health care:
  • reduces the per capita cost of health care
  • removes barriers to technological innovation
  • eliminates disparities between large and small enterprises
How is this not conservative?


Sunday, June 29, 2014

Meaningful Change?

so here's an idea for a political party... the "change the narrative to something not especially crazy" party. it goes something like this...

life's tough, but if we work together it's not nearly as difficult to ensure we all get by. in the post WWII era, most of us have been lucky enough to have inexpensive food, inexpensive transportation and meaningful labor. our parent's (or grand-parent's) families lived in a world where one person's salary was enough to have a very comfortable living.

we told ourselves we were really good people (hell, we had just kicked the snot out of the nazis) while ignoring slavery, misogyny, fixed markets, ostracism of non-conformists and meddling in the internal affairs of foreign nations for financial benefit.

as time went on there were more people to feed and more competition for our goods. margins started getting shaved and we had to do more work for less pay. but we had become accustomed to cheap oil and cheap food, and felt it was our birthright.

we didn't notice when companies and government started telling us convenient untruths. "centralized monoculture food is the best way to grow food," they said. "people of the third world are clamoring for freedom, which is why we overthrew the tyrants ruling them," they said.

but i think we all know the score. we just don't want to own up to it.

in the united states (and australia) we're coasting on the economic push our parents and grand-parents gave us after the world went crazy for several years and did a number on germany and japan. this was after the russians were doing numbers on themselves in an effort to escape the czars and develop infrastructure in europe's most backward sister.

we _have_ done a lot of really cool stuff. the transistor? ossm. space flight? double ossm. i'm not saying we're a big ball of fail.

but i think we may have lost sight on what makes this country great. and while we're losing sight of that, we're starting to listen to corporate (and governmental) interests who profit from our ignorance.

the reason we have high taxes has very little to do with welfare queens and a lot to do with a bloated defense department. no. i'm not talking about US service-persons who risk their lives every day. what i am saying is as a people we've put a government in place that disgraces their sacrifice. we maintain a large military so we can dictate terms to trading partners. we need these good terms because we chose to purchase energy from abroad rather than develop internal infrastructure or better yet, develop more efficient cities, cars and food production.

we've come to accept corruption and human rights abuses abroad and at home if it means we get cheap steak and iPhones.

but sure. it seemed like a good idea at the time.

we no longer have the moral authority to claim we honor words like "freedom" or even "democracy." our religious leaders are co-opted into a system that benefits them while vilifying "the other." our media corporations have long retired the notion they are a public service and operate solely for profit. and of course, that's what our legal system requires them to do, to rigorously pursue the minimum viable information product that still makes them profitable.

we have abandoned the idea that universal education and an enlightened populous is a pre-requisite for an open, democratic society and now view our children's educational experience as a profit opportunity.
we live in a market, not a society.

but it's not too late to change. we CAN choose a different narrative. we can invest in our communities and our children. we can invest in more efficient fuels and cars. we can grow more of our food closer to our homes. we can spend the money we were spending on the most recent iPhone on infrastructure to create a sustainable society in which each child is fed and educated.

but first we have to stop vilifying each other. we have to spend a little more time digging into issues rather than shouting slogans. we can stop jealously guarding our stash and help our neighbors raise their metaphorical barn.

Things I'm Working On...

Just sort of thinking about San Francisco housing prices. And every time I think of San Francisco, I also think of George Takei saying "San Francisco, I was born there," in one of the Trek movies. It's clear his character Hikaru Sulu, really digs on the city. Other characters from the movie have ties to SF; James Kirk has an apartment there (at the opening of the first movie, he's working a desk job at Star Fleet Command in SF) and others no doubt have good memories off off-duty time at Star Fleet Academy (also in SF.)

So I get to thinking of a darker trek world where our beloved protagonists are members of a ruling elite, able to travel between the stars only because of the toil and suffering of untold under-workers you never see on camera. This is clearly not what Gene Roddenberry was originally thinking the future would be like, of course, but modern times seem much less optimistic than the late 60's. So just for fun, I'm thinking of the "Occupy Star Fleet" world. It's not as bloodthirsty as the mirror universe, but perpetuates the "haves vs have nots" Roddenberry originally wanted to say we escaped.

Who are the characters in such a world? I'm not going to sully the image of the canonical bridge crew by having them go all mirror-universe on the poors. That would be vaguely insulting to the characters (and the actors who portray them.) Instead, I'm creating new characters who are members of an exploited class; a class that lives outside the mindset of Star Fleet personnel. It's not that the classic Trek folk are actively putting these people down, it's just they don't even know they exist.

The first character is Tamiko Tenno (or 天皇 民子 for my kanji reading friends.) She's sort of a modern-day Antigone, who kicks off the story when a sequence of events brings her loyalty to her family in conflict with the power of the state. Depending on whom you listen to, the name "Tamiko" implies a "popular" origin while "Tenno" is the appellation applied to emperors in Japan, so she's setup for class conflict already. The first story I'm working out introduces Tamiko-san and is more or less just a re-telling of the Antigone myth (hey. great artists just know what to steal.) Also, go read about Antigone on the WikiPedia if you're unfamiliar with it.

But what's a great leading character without a perfidious antagonist? I mean sure, the whole story is setup to have "man vs. society" and "man vs. his social nature" type conflict, but a good antagonist will be a great personification of the hidden social forces that serve to betray the ideals of individual agency in the Star Trek universe. Tamiko-san will battle "Shift Supervisor Creon" in the first story, but after his demise we'll find he was a servant of a higher, darker authority.

Our eternal antagonist is a sort of reversed Queen of Pentacles, she takes delight in the subdued personal wealth of the Trek universe, but her primary conceit is more akin to that of Omelas: the elevation of humanity's elite justifies the invention of a wretched class. Unlike the traditional interpretation of the Queen of Pentacles being a character of worldly finery, in our story her finery is ideological. She never waivers from the path of "furthering the cause of humanity," even if she is losing her own humanity in the process. Our antagonist is clearly a "true believer," and we all know how dangerous attachment to dogmatic ideals can be.

Anyway... this is just an update of some of the things I'm thinking about and working on this weekend. More updates as they become available.

Monday, May 5, 2014

Install the Latest NodeJS for Raspberry Pi via apt-get

As part of our testing regime for Starless, I build the latest version of node.js from source, package it in a .deb file and push it to one of our servers. It recently dawned on me that other people might want an easy way to install the latest released version of node on their Raspberry Pi's. So here's a quick HOWTO:

Step 0 : Download Raspbian, Copy it to an SD-Card and Boot.

I'm going to assume you've done this already. If not, there are several good "getting started" guides out there. I like the one at http://elinux.org/RPi_Easy_SD_Card_Setup, personally.

Step 1 : Add the "Gonk" repository to /etc/apt/sources.list

Add the following line to the end of /etc/apt/sources.list and run `apt-get update`:

deb http://sm5.us/gonk wheezy main

Here's how I did it:

sudo -s
echo "deb http://sm5.us/gonk wheezy main" >> /etc/apt/sources.list
apt-get update

Step 2 : Un-install the older nodejs package (if installed)

At the time I wrote this, version 0.6.19 of node.js is provided by the main repo. In an ideal world, I would spend the time to make it so you don't have to uninstall the stock package, but I'm somewhat lazy, so just uninstall the stock package if it's installed.

Run the command `nodejs --version` and if you get something like v0.6.19, run these commands:

sudo apt-get remove nodejs
sudo apt-get autoremove

Step 3 : Install the nodejs-latest package

Run the command `apt-get install nodejs-latest` to get the latest released version of node from the Gonk repo:

sudo apt-get install nodejs-latest

Step 4 : Send me an email reminding me to publish the GPG key for the Gonk repo

The apt-get command will balk when you run the install command that it's an unsigned package. Surprisingly, this has less to do with me being too lazy to generate a key and more to do with me being too lazy to fix my test system to not break when I push out new, signed packages.

I'm eventually going to fix that, but if you send an email to meadhbh+fixyerbuildsystem@smithee.us, i'll probably do it sooner rather than later. (though i'm definitely going to do it before we push out an official Starless release.)

And as always, send me an email if you have questions or comments.

Saturday, May 3, 2014

everything is incremental

"everything is incremental," said the sloth to the frog, sitting in the hot tub.

"by the way, does it seem a little warmer, friend sloth?" he replied.

"yes! isn't it great!" the lobster said, jumping in the deep end of the tub. "i found the temperature switch on the tub and opened it full bore before jumping in!"

they were found the next morning beside the tub, drunken, hung-over and slightly pinkened. because it turns out a frog will eventually jump out of a gradually warming hot tub, but when he's out with his friend the lobster and the sloth, he'll drink several times his weight in sake and pass out.

but it's still true it's hard sometimes to see small incremental changes over time.

Saturday, April 19, 2014

More Headless Raspbian Beta Testing

A couple weeks ago I announced I was working on a headless configuration tool for Raspbian devices. I just pushed out an updated beta distro for general testing. I added a few things to the mix:
  1. Network Configuration - you can now configure your network via the web page.
  2. Network Profiles - not only can you configure the network via the web page, you can store configurations as "profiles" so you can easily move your device between different networking environments (home, work, mobile, etc.)
  3. Remote Reboot - If you have a remote device, you can now reboot it remotely with the web interface rather than walking over to it and power cycling it.
To test out the updated beta distro, just do this:
  1. Download the file http://sm5.us/2014-01-07-starless-raspbian.zip and unzip it. You should wind up with a file called 2014-01-07-starless-raspbian.img. Beware though, the zip file is about 800MB, so make sure you're downloading it over a decent connection.
  2. Copy this file onto a spare SD Card using your favorite tool. I use Ubuntu as my daily driver, so I use the command `sudo dd if=2014-01-07-starless-raspbian.img of=<SD Card Device> where <SD Card Device> is the name of the unix device file representing the SD Card. The good people over at eLinux.org have put together a good wiki page describing how to do this in non-unixy environments.
  3. Put the SD Card into your RasPi and give the thing a boot. If you're going to be doing wireless, make sure you're using a USB wireless interface that uses the Realtek 81XX chipset (like this one sold by AdaFruit.) But you should also be able to use the built-in ethernet adapter on the Raspberry Pi Model B's.
  4. It will take a little while to boot. If you have a PiSwitch board, you should see both the recovery and nominal lights turn on for a bit, then turn off, then turn on again. If you want to configure it via a handheld device like a tablet or iPhone, attach to the wireless network 'starless' using 'starless' as the WPA password.
  5. After the device has booted and you've joined the starless WiFi network, point your browser at: http://starless.local/ - you should be greeted with a user interface that looks something like this:

  6. Click on the "User Accounts" menu item to create a user account for yourself, then click on the "Network" menu item to create a network profile for your device. On the "Create Network Profile" screen, you can configure your device to attach to your local wireless network using DHCP like this:

  7. Now click on the "Reboot, etc." menu item and click the Reboot button. In about a minute you should be able to attach to the device from the wireless network you configured or via the wired ethernet network. The admin UI is still available at http://starless.local/ (if your device knows how to do mDNS) or you can ssh into the device and run the raspi-config utility:


  8. And that's about it. Ping me with questions or comments here or on twitter (@OhMeadhbh) or via email at OhMeadhbh [at] gmail [dot] com.

Saturday, April 12, 2014

Using Multiple Versions of Node.JS on Raspbian

People who know me know I'm a fan of Node.JS, the "JavaScript on the server" development framework. And while I would love to say it's all sweetness and light in Node-Land, sometimes there are some dark clouds. One of the darkest current clouds is version dependencies. It's not as bad as it used to be, but every now and again we still get a situation where we might want to punt on the latest version and use the "most recent version that exhibits a particular behaviour."

But the way node is packaged on Debian (and Raspbian) you generally get an old version installed directly in /usr. At Smithee, et al, we've taken a slightly different tack. We install node in /opt/node-v$VERSION with soft-links scattered throughout the file-system to point back to /opt.

For example, on my Raspberry Pi right now, I have two versions of node v0.10.26 and v0.6.5 (yeah. don't ask.) So, /opt on my machine contains the following node-related directories:

Directory What's There
/opt/node-v0.10.26 Modern, daily use node installation
/opt/node-v0.6.5 Legacy node installation

Then I added some soft links to make the system think i had installed version 0.10.26 in /usr:

From To Description
/opt/node /opt/node-v0.10.26 Current default node
/usr/bin/node /opt/node/bin/node Node executable
/usr/include/node /opt/node/include/node Node include files
/usr/lib/node_modules /opt/node/lib/node_modules Node modules (including npm)
/usr/lib/dtrace/node.d /opt/node/lib/dtrace/node.d dtrace descriptor for node
/usr/share/man/man1/node.1 /opt/node/share/man/man1/node.1 Man page for node

So if I want to use version 0.10.26, i use node normally. But if I need to use version 0.6.5, i put /opt/node-v0.6.5/bin in the path before /usr. And when version 0.10.27 comes out, i install it in /opt/node-v0.10.27 and point /opt/node to point to there. If it turns out I have to revert for some reason, all I have to do is change /opt/node to point back to /opt/node-v0.10.26.

If you want to try this out yourself, here's a .deb file you can install with the command `sudo dpkg -i nodejs_0.10.26-1.armhf.deb`. Or, if you like tar files, here is a tar file with node v0.10.26 you can install with the command `( cd /; sudo tar xzvf node_v0.10.26_raspian.tar.gz )`. Both should work with a stock 2014-01-07-wheezy-raspbian system. 

Tuesday, April 8, 2014

Chapter 117 of my still unnamed Space Viking saga

"Okay Gunnr, read it back to me," Fram asked like an youngling asking a parent to read them a story.

"Fram. You really should learn to read and write on your own."

"Pish! I read and write modern. I never got the hang of this old stuff." Fram replied with an amazing lack of annoyance. "C'mon. Read it back. I want to make sure it's perfect!"

"Fram." It took only one word to convey her annoyance. "You'll never learn if you don't try."

"Uh... My helmet's fogging up! I can't see it clearly." It would have been a good excuse had it been true. But Gunnr didn't have a clear view of the front side of his vacc suit, so...

"Okay. Fine." she said, the annoyance giving way to acceptance. There was no way Fram was going to get on with life until this was over. "It reads, 'In the year of the city twenty-three seven-hundred eighty-five, Fram Steinfríðrson had this stone erected in memory of himself, because he was so awesome.'"

"Does it really say 'awesome'?" he asked, "That sounds a little conceited."

"And erecting a rune-stone on an asteroid doesn't make you seem full of yourself, Fram." she said with mock seriousness. "Besides, it actually translates as 'fantastic.'"

Monday, April 7, 2014

What should a computer interface look like?

So I was thinking about how computer/human interfaces reveal biases in their developers.

The early micro-computers I used booted up directly into BASIC. And that makes sense; they were built mostly by hackers, for hackers. Built at a time when people thought, "oh yeah, everyone will be writing their own programs to solve random problems around the house."

Various Xerox machines like the Alto and the Star introduced the "desktop metaphor" which was famously used later in the Apple Macintosh. Jef Raskin, considered the god-father of the Macintosh built a machine for writers, focused on the keyboard. If you get a chance to fiddle with a Canon Cat, it's worth doing. It is a radically different idea for how people should interact with computers.

If you can figure out what Microsoft Windows' primary user interface metaphor is, please let me know. Classic Windows is mostly a desktop; Metro seems to be a "scrollable cork-board of applications or documents" or something.

So this got me thinking, what does the UI of devices like iOS and Android phones reveal about their developers?

My take on iOS is it lets you do a small number of things easily and with admirable grace. Once you try to do something it doesn't want you to do, the steely smirk of Steve Jobs' out of the ether to smack you upside the head. "It's fucking beautiful the way it is!" a disembodied voice says, "Quit trying to do things it wasn't designed for! Maybe you should just get one of those Android phones. Or better yet, go get a Windows Phone." You walk away realizing how unworthy you are of the iOS platform.

To me, iOS says "we know more than you do." And that would be fine if I didn't have to pay $13/month to listen to music i already paid for or could get the address book application to sync properly.

On the Android side, you turn on the phone and... MY OPINION OF ANDROID IS NOT RESPONDING. WAIT? QUIT?

You eventually find a USB cable, download the Android debugger, kill the bloatware process HTC auto-launched at startup and proceed to be confused by configuration options which are amazingly similar to the previous version's config options, but have radically different effects. Android reveals the bias of a typical handset software vendor: "OMG. I can't believe you bought this!"

We're moving into world where the "Internet of Things" is supposed to be the next big thing. Based on what I've seen so far, I'm vaguely bearish on commercial IoT offerings. To start with, there's about zero interoperability. I should be able to whip over to Amazon and buy a 10-pack of ZigBee / BLE / whatever temperature sensors for $32.99. They should come up on a network and respond to administrative requests with a string describing their function; bonus points if they include a description of the protocol they respond to.

What do we get instead? fucking Nest. This is the future? Stop this train, I want to get off. I'll have a better time running a Commodore 64 emulator on my Raspberry Pi.

Sunday, April 6, 2014

Beta Testing a Headless Raspberry Pi Confgurator

So I finally had the time to hobble together an open source version of the headless Raspberry Pi config interface I've been working on. It's used in applications where you want your Raspberry Pi to act as a "headless" server (i.e. - it doesn't have a video screen.) The configuration steps you would normally perform using the raspi-config utility are performed using a web page accessed over the network.

If you have a Raspi with a USB wireless adapter (like this one, sold by Adafruit) you'll be able to test it out. Note. This rev only works with the adapters that use the RTL 871X driver. The official version will support many more USB devices, and you can always access the interface over the wired network connection.

To try it out, download the image from http://sm5.us/2014-01-07-starless-raspbian.img.bz2, unzip the file, then write the image to a SD card. After that, you just boot your raspi and look for a wireless network whose name is something like starlessXXXXXX. Connect to the wireless network using the pass phrase starless, and then go to http://y.sm5.us/ to see the admin interface.

I haven't configured mDNS yet, so accessing the interface via the wired interface on a Model B is a little trickier. It's setup to do DHCP on eth0, so if you have your raspi working now with DHCP, it should still work. You'll have to figure out what the IP address is by yourself, but that's the hardest part. I've configured my DHCP server to always hand out the same IP address to my raspi, so i just added the line

192.168.1.3  y.sm5.us

to the /etc/hosts file. Your raspi probably has a different IP address, so... substitute 192.168.1.3 with whatever your IP address is.

The interesting bit I'm trying to test out right now is to make sure the interface works with popular mobile phones and tablets. Unlike previous web experiments, I'm not doing anything fancy, so as long as you have a reasonably modern browser that handles JavaScript and jQuery, you should be fine.

If you have questions, comments or just want to tell me you tried it and it worked, ping me at @OhMeadhbh on twitter or via email at OhMeadhbh [at] gmail [dot] com.

-Cheers!

p.s. - like most of the project names I use, the name "starless" comes from a King Crimson song; "Starless and Bible Black" in this instance.

Tuesday, March 25, 2014

Why I Don't Care About Brendan Eich's Prop 8 Donation

The social media universe is all a'twitter about Brendan Eich's recent promotion to CEO of the Mozilla Corporation (MoCo). Brendan Eich is, as you probably remember, the guy who invented the JavaScript programming language. Eich was at the time, an engineer at Netscape, moving over to the "Mozilla Organization" in 1998 and then the Mozilla Foundation (MoFo) in 2003. By this time he had risen to a position of technical leadership and was, in fact, one of co-founders of the official Mozilla Foundation 501(c)(3). As the Mozilla Foundation morphed into the Mozilla Corporation for tax reasons, Eich eventually landed as MoCo's CTO.

The thing that has the twitter-verse up in arms is Eich's contribution in 2008 to a Pro-Prop-8 organization. For people outside California, Proposition 8 (aka Prop 8) was the "marriage is legally defined in California as being between one man and one woman" proposition that went before the electorate and (somewhat surprisingly) passed. Prop-8 has since been overturned by the courts and all is as it should be.

But there are a lot of us queers in the tech industry and it turns out we have access to political donation rosters (actually, everyone has access to these rosters, they're public information.) And we apparently have reasonably good memories. In 2012 someone noticed the donation and a brouhaha emerged. When Eich was named MoCo's CEO yesterday, the brouhaha re-emerged with some people saying we should boycott Mozilla. Rarebit, for instance, removed their color puzzle app from the Mozilla Marketplace in protest.

In the interests of full disclosure, I worked for MoCo for a brief period of time in 2013 and met Mr. Eich several times. I did not work especially closely with him, nor did we discuss politics. But I had enough encounters to develop this impression: Brendan Eich is a Geek (and I mean that in the good way.) He is, like many in Sili Valley, slightly nerdy, a little more focused on tech subjects than on intra-personal skills. He's not rude, it's just clear he would annoy the living hell out of Emily Post.

I've seen Eich interact with people at MoCo, including people I know he knew were gay. He didn't appear to treat them in any way differently.

And yes, it is troubling to find the CEO of Mozilla's name on a list of people who donated to political causes that sought to deny basic human rights to a minority population. But I personally believe the issue is not so much an issue of homophobia than it is ignorance. I honestly believe Brendan Eich grew up in an environment that reinforced ideas of the moral superiority of "traditional" relationships and he never gave it a second thought.

It would be very nice if Mr. Eich would come out and say something like "Totally sorry about that Prop-8 donation. Upon further reflection, I think it was an inappropriate thing to do." But honestly, I don't think he's under any obligation to do so.

Corporations aren't people, nor are they responsible for the beliefs of their employees. By boycotting Mozilla (the corporation) because one employee did something politically objectionable, you are asking the corporation to police not only the behaviour of it's employees, but also their beliefs. I find Eich's support of Proposition 8 objectionable, but it is more objectionable to ask corporations to deny promotion to individuals who exercise their right to support political efforts outside the corporation.

If you're looking for reasons to hate on Mozilla, there are several to choose from: FirefoxOS' "race to the bottom" strategy, declining market share or questions surrounding the post-2014 funding from Google now that MoCo competes with Android, etc. But having a CEO who thinks my marriage was abhorrent? That's just life in a pluralistic society.

Wednesday, March 19, 2014

Chapter 3 of my still unnamed Space Vikiing saga

"Hierophant of Discord," Fram said while slapping down his card, "ditch 'em if ya' got 'em!"

An audible sigh came up from Gerstlauer; he had bid blind, not knowing if Fram could cover him.

Gunnr played next, wincing as she threw down the Queen of Discord. She had been saving it to win the next trick and now her plans fell apart. Fram and Gertlauer giggled like kindergartners at the site and broke into full-on laughter as Gert threw down the King of Claw.

"You bid zero with the King of Claw, you have huge balls, my friend!" Wido, the fourth of the card players, cracked at the sight.

Gunnr retorted sourly, "He bid blind. He couldn't have known. His balls are of normal size." The only one of the four to take the loss personally, she complained "come on, let's finish it and get back to work."

"Gunnr, it's just a game. Many days you take us for five times as many points as you lost here," sagt Fram, just becoming aware of her sourness. "But yes, we have three minutes before work resumes. My last two cards are shit," he said, throwing them down face-up on the table leaving Wido and Gerstlauer to argue over who took the last
two tricks.

Gunnr was up and walking back towards her work-station at the forge control. Every bit of her body language screamed tenseness.

Fram caught up with Gunnr, who had already made it several meters from the table. Summoning every bit of grandfatherly softness he could, "what's wrong?"

She waved him away, "Don't try that grandfather business on me! You're not _that_ old," she shot back with surprising venom for someone who had worked with Fram for almost a decade.

It was true Fram wasn't quite old enough to be her grandfather, but could easily be her father. Genetics on the colony were such to make it impossible, of course. But genetics don't stop people from familial attachments; the entire colony would be in a sorry state if it did.

Growing concerned with Gunnr's mood, he tried a different tack, "Gunnr. You have to be here every moment of every day. I won't have you risk injury on my rig 'cause your head is a million miles away."

"No Fram. It's okay. I'm fine." she protested.

Fram was trying to figure out if he had asked her two or three times. Traditions varied amonst the colonists, but all bought into the concept of the heroic self-sufficient individual. Common manners were to deny any sort of help two or three times before admitting you were in need. Fram was old enough to realize what kind of crap this tradition was. He had seen too many people get into too much trouble 'cause they were too proud to let someone help them. The simple fact of the matter was the colony's existence was too tenuous for pride to get in the way of survival.

"Gunnr. I am your work foreman and your friend. I will stay here all day playing stupid manner games, but I will not leave until you tell me what is wrong."

Gunnr leaned in close and whispered a few words in Fram's ear.

All Fram could say in reply was, "Holy shit."

"Yeah," she replied, "you want me here, still?"

"You want to take a day or two off? We're way ahead on our quota, we can manage without you a couple days."

"No Fram, I think I want to be here. Working will take my mind off it." Gunnr replied.

"That's fine. But I want to slow down a bit; no sense tempting fate," Fram said, his eyes darting back and forth the way they do when he's crafting a plan, "Tamsen will ask why we're slowing down though, so let's make up a story of instrument failure or something."

In the eight years Fram had known Gunnr, the hug she gave him was the first time he had know her to do anything even slightly feminine. Taken aback a little, "I love you too, sweetheart," was the only thing he could think to say as he hugged her back.

Thursday, January 30, 2014

A Quick Note About the Space Economy

In the last week I've been in a couple very good conversations with people about developing the "space economy." And it's all good; from private launch companies like Orbital and SpaceX to cohorts of enthusiasts willing to die on Mars in the name of exploration and reality television ratings. But there's one thing people have been missing... the space economy isn't about going there and bringing things back, it's about going there, in-situ resource utilization and then staying there a while

So it's great when we can launch people to the ISS to research what happens to pumpkin seeds in zero-g, but until they can order a pizza for delivery in LEO, we don't really have a space economy. At best, we have a terrestrial economy with brief forays into orbit. Until we have enough development of non-terrestrial resources that the majority of productive activity is for the benefit of other non-terrestrial development, we're not going to have a space economy.

Just Sayin'.

Tuesday, January 28, 2014

Using SN-App to Avoid Reinventing the Wheel

Software people who know me know I don't like cut an paste programming. If you can refactor common bits of code out of a program, you probably should. Copying code leads to drudgery and errors if you find you have to change all those places where you hit Ctrl-V. So you can imagine how torked I was at the Node.JS common practice of building new code every time you built a new app. (Granted, it's less common than it used to be, but it's still surprisingly common.)

After the first three connect.js apps I wrote, I refactored the common bits out and made a quick "app runner" that read a config file, used its contents to decide what bits of connect.js middleware to use and then call a different JavaScript module... the one with the "real" code in it. After a couple years of refining, I recently released it as SN-App.

If you use connect.js or express.js, you might find it useful. Rather than writing code to explicitly add commonly used middleware to your Connect or Express app, you build a JSON file listing which bits of middleware you want to load and their parameters. SN-App reads this file and adds the appropriate middleware for you.

Here's a simple SN-App config file. Readers familiar with Connect can probably guess what will happen when it's processed:

properties.json:
{
  "title": "SampleApp",
  "favicon": "static/favicon.ico",
  "static": "static",
  "listen": {
    "port": 80
  }
}

When you execute the SN-App application with the command `sn-app --config file://properties.json`, it loads Connect's "static" middleware to serve static files out of the directory "static" and listens for requests on port 80.

But why use Node if you're just going to serve static files? If you add these lines to the config file, it will turn on the Body Parser middleware and load an additional JavaScript module from src/logic.js:

  "bodyParser": true,
  "source": "src/logic"

And if you're a little lazy, you can ask SN-App to build a skeletal web application for you, complete with a skeletal Bootstrap or Semantic-UI front page. If you wanted to build a simple app to run on port 9001 and served a Semantic-UI index page, just do this:

sn-app-build --title SampleApp --port 9001 --static static \
  --css semanticui
make
sn-app --config file://SampleApp.json

Up and running in seconds flat. If you want to do anything interesting, you'll likely have to edit the SampleApp.json file to do anything interesting, but hey, you were going to do that anyway. SN-App doesn't write the interesting bits for you, it gets the boring bits out of your way so you can get straight to the fun stuff.

Lastly, you can ask SN-App to build a debian init file for you. After running sn-app-build to build the app skeleton and running sn-app to make sure it works, the sn-app-initgen command will generate an init file suitable for inclusion in >/etc/init.d:

sn-app-initgen --name SampleApp --desc "A Sample Application" \
  --dir `pwd` > /etc/init.d/sample
ln -s `which sn-app` SampleApp
chmod 755 /etc/init.d/sample
insserv sample
# Older debians may have to use update-rc.d instead of insserv.

Installing SN-App is pretty straight-forward as well; just use NPM:

sudo npm install -g sn-app

And with that, you're ready to go. For detailed info about properties file options, see the documentation at https://github.com/smithee-us/sn-app - and as always, ping me with questions or comments.

Sunday, January 26, 2014

Why I Developed the SN-Props Package for Node.JS

People who know me know I'm a bit of a nut for Node.JS, the JavaScript Application Framework. Over the past several years, I've been writing packages to make developing applications easier. The one that can have immediate utility to virtually all Node developers is SN-Props (fomerly node-props.) On the surface, it looks like a simple package that reads a JSON configuration file from the command-line and passes it to the program shortly after launch. It certainly does do that, but it's even a little more capable, so I figured it would be useful to describe what I was trying to build and the problem I was trying to solve.

In the old days the preferred method of changing the behavior of a program from "Development Mode" to "Production Mode" was via the NODE_ENV environment variable. Before you launched the program, you set this variable to "production" or "development." Inside the program, you would check the environment variable and change your settings appropriately. This led to code that looked like this:

var listen_port;
var listen_addr;
var db_addr;
var db_pass;

if( "production" === process.env.NODE_ENV ) {
  listen_addr = "0.0.0.0";
  listen_port = 80;
  db_addr = "prod-db.example.com";
  db_pass = "DJl87sJXX01";
} else {
  listen_addr = "127.0.0.1";
  listen_port = 8080;
  db_addr = "localhost";
  db_pass = "password";
}

The biggest problem I have with code like this is it makes Node applications brittle. You wind up hard-coding things like database addresses & passwords into the app. If your operations staff needs to change the IP address or password of a machine, you have to track down a developer. And worse -- you wind up committing your database passwords to your source repo.

So the next thing we tried was to read a different JSON configuration file based on the environment variable. That file would contain all your favorite settings in a separate file. During development, you would use the file "dev.json" and in production you would look for "prod.json":

prod.json:

{
  "listen_addr":"0.0.0.0",
  "listen_port": 80,
  "db_addr": "prod-db.example.com",
  "db_pass": "DJl87sJXX01"
}

dev.json:
{
  "listen_addr":"127.0.0.1",
  "listen_port": 8080,
  "db_addr": "localhost",
  "db_pass": "password"
}

This is MUCH better. You no longer have to hard-code config options into the source and your ops staff doesn't have to worry about inadvertently borking production code if they need to change production settings.

At about this time, I started working with "redundant arrays of indepensive web apps." A typical deployment for me would be to have six copies of an app server running simultaneously. And through the magic of virtualization, we would sometimes add an extra two or three servers to meet high-demand periods.

After trying to ensure that exactly the right version of a configuration file made it onto any given server, I realized I wanted was to store my config JSON files on an internal web server. Instead of reading a file on the local file-system for config settings, I just queried the web server. This worked pretty well: I only had to configure one or two files on a single web server to change the behavior of the entire cluster. Yes, I could have used SCP to copy config files, but it was a bit of a pain to program our deploy system to distribute the right file to newly started instances and time it so we pushed the file out before the app started but after the openssh server started. No. It was much better to have the application itself pull it's config data instead of having a central server push the config to new machines.

I was very happy with this solution until we split our app into shards. All of the sudden we needed to have a lot more per-machine config data. Our initial idea was to load up the config server with a bunch of different files, one per machine and make the apps smart enough to pull the right file. This turned out to be annoying due to the large number of config settings that were common to all machines. If you wanted to change a global setting, you had to change the setting in each of the per-machine config files.

The answer was to split our config settings into per-app and per-machine settings. The per machine settings included IP addresses of proxies & sometimes databases. The per app settings included things like tables, usernames and passwords for databases and the like. And after writing a few apps that made two explicit HTTP(S) queries after starting up, it made sense to move that behavior into it's own package.

And that is how the SN-Props was born (though we called it node-props back then.) And this is how I use it today. I put per-machine settings in a local file and per-app or global settings on an internal web server. The per-machine settings file would likely look like this:

{
  "listen": {
    "port": 9001,
    "host": "127.0.0.1"
  },
  "telemetry": "http://west-coast.telemetry.sm5.us/"
}

while the global settings file would look like this:

{
  "appname": "Cookr",
  "tagline": "Crowdfunding innovative recipes since 2014",
  "database": {
    "host": "cookr.db.sm5.us",
    "user": "cookr",
    "password": "DJl87sJXX01",
    "collection": "cookr_main"
  }
}

To start the service, I don't monkey with environment variables, i just create three versions of the various settings files: one for development, another for integration testing and a third for production. When i want to start the app, I list the URLs of the config files on the command line:
/opt/node/bin/node cookr.js --config file:///etc/permachine.json --config http://deploy.int.sm5.us/cookr.json

The SN-Props package is licensed with under a MIT License, so you can use it as well. Here's a code sample of how easy it is to use:

require( 'sn-props' ).read( function( properties ) {
  // Do something with the properties here. The object passed to this
  // function has the contents of all config files merged into it.

} );

Monday, January 13, 2014

Kill. The. Web.

While the world wide web has done a wonderful job of creating inter-operable network applications and distributed data repositories, it has also constrained our thinking about what it means live in a networked society. Despite efforts to make the web "bi-directional" it is still predominantly a one-way publication media.

This needs to change.

"The Web" means everything is reduced to electronic text and graphics that fit in a 960 x 800 array of pixels. This is an acceptable format for reading or even watching videos. Ubiquitous multimedia means we can even listen to music, radio programs or news. Content comes from a server, operated by a single corporate entity, usually a great distance away.

But watch this video excerpt from Adam Curtis "All Watched Over by Machines of Loving Grace:"


Loren Carpenter Experiment at SIGGRAPH '91 from Zachary Murray on Vimeo.

The web, for all its wonders, can't replicate this simple experiment from the early 1990's. The web is about dissolving locality and proximity. To be sure, this is a remarkable achievement. But it's not enough.

We need to think about proximity and closeness.

Not so much because we are social creatures, but because proximity facilitates feedback. The web is not about feedback. EMail, for all it's benefits, does not scale well with increasing numbers of human participants. Intent and meaning dissolve as more people participate in an email thread. Twitter and Facebook have better immediacy, but limitations on content and ownership make them frustrating to use for many tasks. IRC is a collection of text lines; good for many situations, but again, it is frequently difficult to understand why someone is or isn't responding.

Proximity facilitates rich interpersonal communication and rapid feedback.

The web is wonderful, but it was designed to demolish the effects of geographic distribution, not explicitly to support tasks requiring near-immediate feedback. The web doesn't really need to die, but it needs to be supplemented by tools to support meaningful real-time collaboration.