Coyote's User Story

The directors of the ACME Corporation are throwing ideas at the wall. After a string of missed targets and embarrassing flops, the company badly needs a win.

“We could always launch a new line of safes,” suggests Product. “With all of these security breaches, nothing screams ‘peace of mind’ like a few tons of—“

“But millenials aren’t in-market for safes,” interrupts Marketing. “We need something bigger, more disruptive—“

“—like the portable clouds?” finishes R&D. “They’re nearly ready for production.”

“We can shoot higher than portable clouds,” says Sales confidently. “How about another rocket? No-one can ever have enough rockets!”

More terrestrial concerns occupy the void between the customer’s very furry ears. As Famishus Vulgarus scans the desolate landscape for any sign of food, ACME’s directors are missing the point. The one thing their customer needs—the only thing their customer needs—isn’t a safe, cloud, or a rocket. It’s dinner.

This is ACME’s opportunity! But faced with a panoply of contraptions they could build, the directors are struggling to commit. With cash dwindling and time running out, their caution is understandable: any misfire could blow the whole enterprise to the bottom of Calamity Canyon.

When they settle on a plan—Rockets!—they spring into action and leave the customer behind. Sales and Product negotiate on range, payload, and timeline; Marketing campaigns to snatch back mindshare in the increasingly crowded commercial-launch field; and R&D tells anyone who will listen about a powerful new propellant. And poor Wile E. is left with his belly button engaging in an increasingly passionate flirtation with his spine.

Products need customers. Long before a rocket can flop from the drawing board into history’s wastebin of unneeded products, it’s worth a candid look at why we’re building what we’re about to build. Paper is cheap. Let’s give ACME a hand in describing the putative need:

A customer catches the Road Runner so they can eat.

Clear enough, and it’s all there: actor, action, and motivation, packed and ready for fortune cookie slips, sticky notes, or the product management tool du jour. Contrast with “build The Rocket,” which—while adequate description for such an obvious task—tells us nothing about the underlying problem The Rocket exists to solve. Giving our users a face helps us empathize with them, prioritize their needs, and use their motivations to guide us as we smooth out the edges.

Beyond keeping focus on the customer, user stories help product discussions take place at an appropriate level. Sticking to the form leaves no room for implementation details to sidetrack conversation. “How” is conspicuously absent from “who does what, and why.” User stories let us assess value and prioritize the path to success before we dive into specifics. They read well in a kanban queue—fortune cookies!—and they’re cheap to discard. We won’t avoid the detours and complications of implementation, but we can test them in the context of a deliberate strategy.

Product development is fraught with so many threats and distractions that it’s a wonder we ship anything at all. Like so many of the tools and techniques employed in the process, user stories can feel like extraneous paper-pushing. Why bother?

Communication,” of course! User stories don’t guarantee a great product, but they do structure the conversations that conceive it. Ultimately, they are a tool: if they aren’t building shared context and focusing discussion, don’t use them.

Epilogue

ACME’s Marketing marketed like never before and Sales filled up the order book. Product delivered under budget, and for the first time in anyone’s memory an on-time launch was all systems go. Then word began to leak: the rockets, big and shiny as they were, were useless for catching the Road Runner. Everything fell apart.

And while the directors of the ACME Corporation huddle in the conference room throwing ideas at the wall, a lonely Coyote scans the desert for any glimpse of the only food around…

Folks, that’s all.




Any Color You Like

We know what we’ll get at Dearborn Motors, and we don’t need to know anything about manufacturing to get it. For just a few hundred dollars and a signature on the dotted line, there’s a shiny black car eager to go wherever adventure may lead.

<Car customer="rj" received="850.00" currency="USD" />

Contrast this batteries-included specimen with Dearborn’s only other product–a nuts-and-bolts DIY guide–and we understand why declarative interfaces are so appealing: if we can reach a desired state simply by describing it, we get to skip the oil and grime of the gritty details it takes to get there.

But after a few years of getting lost in between all the other black cars crowding the highway, gee—wouldn’t it be nice to have a blue one instead?

If we owned Dearborn some fresh colors would be cake. One new field on the purchase order and a few adjustments in the paint shop and a shiny blue car could be in our hands by tomorrow. But we unfortunately don’t own Dearborn Motors and their recalcitrant support team dismisses our request. Black—and only black—shall it be.

We’ve just learned an important lesson: while declarative interfaces provide terrific simplicity, they claim total jurisdiction over their domain. If we need a feature beyond their purview, our only option is to expand the domain to allow it:

<Car color="blue" customer="rj" received="850.00" currency="USD" />

This raises its own challenges: we’re now on the hook to support a new permutation (color) and all of the machinery it requires, and if back-compatibility (or a stubborn vendor) keeps us from expanding the domain, well, we’re out of luck. Nothing for it but to hand over the keys and go home.

Though Dearborn has long since retired their DIY manual, it’s hard to forget the flexibility imbued in those oil-slicked plans. How different would history be if we could customize the car on our own?

let paintedCar = paint(car, 'blue');

Not bad! But why stop at color? If it were up to us, the roads could be jammed with jalopies of every shape and size.

let car = VehicleFactory.create('cabriolet')
car = addEngine(car, 'v8')
car = addTransmission(car, 6)

for (i = 0; i < 4; i++) {
  car = addTire(car);
}

let paintedCar = paint(car, 'blue');

These instructions can be modified to produce many different types of vehicle. Customers have to get under the hood, but once there they can use, replace, and compose our vehicle-production facilities for whatever cases they may have.

Here we’ve come full circle: even while building vehicles up from the ground, we’re still employing declarative interfaces. While addTire is fully self-contained, addEngine delivers the specified engine while insulating us from the details of installation. The trick is that the functions here each claim a much smaller domain than Dearborn Motors’ <Car /> API.

In tight, stable domains where end states are well-understood, a declarative solution might be just the thing. But it will also lacks flexibility—the cold, hard currency needed to navigate shifting requirements and emerging use-cases. While a declarative interfaces can eventually grant simple, predictable access to the sophisticated machinery beneath, we may not be quite ready for it. If we aren’t ready to claim the domain, well, let’s roll up sleeves and get back to work!




code2png

Sharing code snippets isn’t always easy: between character limits on Twitter and formatting limitations everywhere else, it sometimes feels like the internet is trying to keep beautifully-formatted sample code out. And while there are plenty of tools for converting syntax-highlighted code into distribution-ready images, there’s a certain inconvenience to leaving the command line to use them.

Enter code2png, the easy way to generate beautiful snapshots from the comfort of the command line.

Installing via npm is as easy as:

$ npm install -g code2png
$ code2png hello.c -o hello.png

And et voilà! Out the other end comes a beautiful snapshot, syntax-highlighted and ready to take on the world.

Generated screenshot
hello.c.png

How it works

Instead of creating beautiful snapshots from a desktop utility or the browser, code2png brings a browser (namely, PhantomJS) to where the code is. With a syntax-highlighting assist from Prism snippets from stdin or flat files are converted into HTML documents, snapshotted, and returned to the filesystem.

It isn’t subtle, but unwritten code rarely is. It’s functional–and brief. Better, smaller, faster? There’ll be time for that soon.

View all posts