<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:geo="http://www.w3.org/2003/01/geo/wgs84_pos#" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:media="http://search.yahoo.com/mrss/" xmlns:yt="http://gdata.youtube.com/schemas/2007" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
   <channel>
      <title>as days pass by: a weblog by Stuart Langridge</title>
      <description>scratched tallies on the prison wall</description>
      <link>http://pipes.yahoo.com/pipes/pipe.info?_id=0b36d196b9e83fe728bf34a46a14a10d</link>
      <atom:link rel="next" href="http://pipes.yahoo.com/pipes/pipe.run?_id=0b36d196b9e83fe728bf34a46a14a10d&amp;_render=rss&amp;page=2" />
      <pubDate>Mon, 21 May 2012 13:44:26 +0000</pubDate>
      <generator>http://pipes.yahoo.com/pipes/</generator>
      <atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/kryogenix" /><feedburner:info xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" uri="kryogenix" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
         <title>How to make APIs that people like</title>
         <link>http://www.kryogenix.org/days/2012/05/12/how-to-make-apis-that-people-like</link>
         <description>&lt;p&gt;A short presentation I gave at today's &lt;a rel="nofollow" target="_blank" href="http://www.multipack.co.uk/"&gt;Multipack&lt;/a&gt; &lt;a rel="nofollow" target="_blank" href="http://lanyrd.com/2012/multipack-presents-may/"&gt;Show and Tell&lt;/a&gt; on "&lt;a rel="nofollow" target="_blank" href="http://www.kryogenix.org/code/apis-like"&gt;How to make APIs that people like&lt;/a&gt;".&lt;/p&gt;

&lt;p&gt;The tl;dr version: your API is part of your user experience. Take your UX knowledge -- design for the user, not for yourself; think about the user journey rather than just modelling your underlying infrastructure; make it understandable and intuitive and focused on their need -- and do all the same things when designing an API.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_3b149fe0fd6ec7a678d3ae05a4ab6d3e</guid>
         <pubDate>Sat, 12 May 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Waiting</title>
         <link>http://www.kryogenix.org/days/2012/05/03/waiting</link>
         <description>&lt;p&gt;&lt;a rel="nofollow" target="_blank" href="http://www.codinghorror.com/blog/2012/05/buying-happiness.html"&gt;Buying Happiness &amp;mdash; Jeff Atwood&lt;/a&gt;&lt;/p&gt;
&lt;blockquote&gt;&lt;strong&gt;Pay now and consume later&lt;/strong&gt;: Immediate gratification can lead you to make purchases you can't afford, or may not even truly want. Impulse buying also deprives you of the distance necessary to make reasoned decisions. It eliminates any sense of anticipation, which is a strong source of happiness. For maximum happiness, savor (maybe even prolong!) the uncertainty of deciding whether to buy, what to buy, and the time waiting for the object of your desire to arrive.&lt;/blockquote&gt;
&lt;p&gt;Next time &lt;a rel="nofollow" target="_blank" href="http://www.jonobacon.org/"&gt;Jono&lt;/a&gt; complains at me for spending six months agonising and analysing about a new phone or new laptop or something, I shall tell him: it is &lt;strong&gt;science&lt;/strong&gt;.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_6c42664e17293cfe430a2998b5a6817a</guid>
         <pubDate>Thu, 03 May 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Ubuntu One Files for the Nokia N9</title>
         <link>http://www.kryogenix.org/days/2012/05/01/ubuntu-one-files-for-the-nokia-n9</link>
         <description>&lt;p&gt;A first release: &lt;a rel="nofollow" target="_blank" href="http://kryogenix.org/code/u1fn9/"&gt;Ubuntu One Files for the Nokia N9&lt;/a&gt;. Includes short YouTube video with nice music. Still lots to do, of course.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_a188386791ea6fb477e53445d1c56995</guid>
         <pubDate>Tue, 01 May 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Conference wars</title>
         <link>http://www.kryogenix.org/days/2012/04/25/conference-wars</link>
         <description>&lt;p&gt;Just had an odd little idea.&lt;/p&gt;

&lt;p&gt;Imagine you go off to a conference -- one of the ones where you wander around and look at stuff and talk to people in corridors and so on, not one of the ones where you sit in the same seat for the whole day and then go home. And when you pick up your lanyard and badge, there's an extra little stack of cards and you can take one, if you want. A card has on it, say, ten empty boxes with "Deaths" written above them, and it's a little bit taller than your conference badge so when you put it in the badge case it pokes up above the badge a bit. What this means is that taking one of the cards means you're playing the conference game, and other people can see that you are (because the card pokes up a bit). So, when you're walking around and you see someone else playing the game... you Roshambo them. (That's Scissors-Paper-Stone, or Rock-Paper-Scissors, for those who don't know the term "Roshambo".) The loser takes out their little card and puts an X in one of their "Deaths" boxes, in sight of the winner. Then each goes their separate ways. If all your Deaths boxes have been Xed then you're dead and no longer playing; put your card in your pocket.&lt;/p&gt;

&lt;p&gt;No idea if this'd actually work, but I think it'd be cool. Fun little thing to be doing while you're enjoying the conference. I can imagine it would have worked well at LugRadio Live, for example.&lt;/p&gt;

&lt;h3&gt;Extra thoughts&lt;/h3&gt;

&lt;p&gt;On the back of the card, have a special move, and a number of "hour" boxes, one per hour in the conference day. A special move would be something like, say, "Dynamite" -- if your opponent plays rock, you automatically win, regardless of what you yourself played. If you use a special move to win, visibly put a tick in the corresponding hour box (so you can only use a special move once per hour, or five times in total, or something).&lt;/p&gt;

&lt;p&gt;If it gets close to the end of the day, how do still-alive players find one another in order to do battle? Haven't quite worked this out yet.&lt;/p&gt;

&lt;p&gt;Printing up a stack of the cards would be cool, but I suppose it's not strictly necessary -- someone can just draw themselves a card if they want.&lt;/p&gt;

&lt;p&gt;There are a bunch of sensibleness rules -- you can't fight the same person twice in succession, for example -- in order to stop two people fighting until one of them is eliminated from the game entirely. Of course, given the rules lawyers, probably you need to stop three people standing in a triangle and fighting until one is eliminated, but that's basically covered by the generalised "don't be a dick" rule :)&lt;/p&gt;

&lt;p&gt;It should be possible to tweak the cards for the particular conference... if you've got a zillion attendees and they all want to play, maybe you need more than ten deaths, or you get more special moves, or whatever. That seems easy enough.&lt;/p&gt;

&lt;p&gt;Let me know if you try it out.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_0c786a074d3df4d4e03c79895161faaa</guid>
         <pubDate>Wed, 25 Apr 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Decades</title>
         <link>http://www.kryogenix.org/days/2012/04/23/decades</link>
         <description>&lt;p&gt;I've been writing this blog for ten years, as of this weekend.&lt;/p&gt;

&lt;p&gt;In that decade, I've written 510,216 words here, which is &lt;a rel="nofollow"
 target="_blank" href="http://en.wikipedia.org/wiki/List_of_longest_novels"&gt;about the
same length as &lt;em&gt;War and Peace&lt;/em&gt; or &lt;em&gt;Les Miserables&lt;/em&gt;&lt;/a&gt; although it's
a little more focused on technology than on the impact of the Napoleonic era 
on Tsarist society. After poking around with a bit of maths, a few stats
in the form of a bunch of &lt;a rel="nofollow" target="_blank" href="http://zachseward.com/sparktweets/"&gt;small bar 
graphs&lt;/a&gt;.

&lt;h3&gt;A bunch of small bar graphs&lt;/h3&gt;
&lt;table&gt;&lt;tr&gt;&lt;td&gt;Posts per year&lt;/td&gt;
&lt;td&gt;▇▄▅▅▃▂▂▂▁▁▁&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Word count per year&lt;/td&gt;
&lt;td&gt;▇▄▃▃▃▂▂▂▁▁▁&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Word count average&lt;/td&gt;
&lt;td&gt;▃▂▂▂▂▃▂▃▃▃▇&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Amount I mention Ubuntu&lt;/td&gt;
&lt;td&gt;▁▁▁▁▁▁▁▂▄▇▄&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Average number of comments&lt;/td&gt;
&lt;td&gt;▁▅▃▃▃▄▄▇▅▆▆&lt;/td&gt;&lt;/tr&gt;
&lt;/table&gt;

&lt;p&gt;That last one's interesting. It seems that the number of comments on posts
has stayed relatively steady over the last ten years, which is nice. There are
a few things that skew that, though:&lt;/p&gt;

&lt;h3&gt;Top 5 commented posts&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;How to be rich and famous&lt;/a&gt;: 1005&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Carphone Warehouse customer service&lt;/a&gt;: 246&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Autism test&lt;/a&gt;: 218&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Sorttable v2: making your tables even more sortable&lt;/a&gt;: 216&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;K700i&lt;/a&gt;: 145&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The first three of those are posts which attracted a shedload of comments from
people who didn't bother to read the actual post itself but basically used
it as a forum to talk about the subject. This sort of thing is self-reinforcing;
if you write something about a cat dying then people comment saying "my cat
died, it was so sad" and then you move your way up the Google rankings for people
looking to write about their cat dying; they come and post some more, repeat
until false. The infamous &lt;a rel="nofollow"&gt;How to be rich and famous&lt;/a&gt;
post is one of only two where I've interfered with the comment stream; I stopped
comments on that post for a while because it became (a) a place for hopeful 
teenagers to ask how they could get famous and, (b) more worryingly, a place
for hopeful teenagers to post their phone numbers and addresses so that someone
could ring them up and say "hey, we want you to be the next pop star, keep your
eye out for the limo". So, I put a stop to that because I got bored of redacting
mobile numbers out of the posts, and telling people to &lt;em&gt;not do that, what 
are you, fuckin' morons? stop it!&lt;/em&gt;, didn't seem to have any effect.&lt;/p&gt;

&lt;p&gt;The other post that got the comment stream interfered with was &lt;a rel="nofollow"
 target="_blank" href="http://www.kryogenix.org/days/2005/02/25/warehouse"&gt;the one about
Carphone Warehouse&lt;/a&gt;, whose sad story is told in &lt;a rel="nofollow"
 target="_blank" href="http://www.kryogenix.org/days/2006/04/27/redaction-of-comments"&gt;Redaction
of comments&lt;/a&gt;. Le sigh, again. I'm &lt;em&gt;still&lt;/em&gt; conflicted about what I
did there. Ah, history.&lt;/p&gt;

&lt;p&gt;It's clear from the graphs that I write less often but write more text when
I actually do pen something. I suspect that a lot of this, over the last
few years at least, is down to &lt;a rel="nofollow" target="_blank" href="http://twitter.com/sil"&gt;Twitter&lt;/a&gt;
eating up my desire to write snippet-y stuff; back in the old days (cue
Hovis music) we used to write short stuff on blogs rather than Twitter or
Tumblr. You kids these days, don't know you're born, etc.&lt;/p&gt;

&lt;p&gt;God, I feel old all of a sudden.&lt;/p&gt;

&lt;h3&gt;Top 5 posts by length&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Desktop Couch IRC talk&lt;/a&gt;: 4381&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Adding Ubuntu One support to your applications, an IRC lecture&lt;/a&gt;: 3558&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;My new phone, 2012 edition&lt;/a&gt;: 2987&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;Monkey Island 2, for about the fifth time&lt;/a&gt;: 2357&lt;/li&gt;
&lt;li&gt;&lt;a rel="nofollow"&gt;That was LugRadio Live 2009&lt;/a&gt;: 1854&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The top two of those are transcripts of IRC lectures and therefore don't really
count. Of the next three, two were written in the last two months, which suggests
that long-form writing is more my métier these days.&lt;/p&gt;

&lt;p&gt;The design… oh, the design. A history of web design done by someone
who has no bloody idea what he's doing, in animated gif form…&lt;/p&gt;

&lt;p style="text-align:center;"&gt;&lt;img src="http://www.kryogenix.org/random/kohistory.gif" alt=""&gt;&lt;/p&gt;

&lt;p&gt;I'd forgotten about some of those. The &lt;a rel="nofollow" target="_blank" href="http://archive.org"&gt;Internet 
Archive&lt;/a&gt;, as ever, does its usual sterling job. It didn't seem to have 
everything, or more accurately it didn't seem to pick up the CSS for everything,
so a bunch of snapshots it took were 1995-style plain Times New Roman HTML, but
one can't really complain (in particular, the pink design that everyone hated
failed to be immortalised into history. I liked that one.)&lt;/p&gt;

&lt;p&gt;It's amazing what's come in and gone away. Remember linklogs? Blogrolls?
Bloglines? RSS autodiscovery being an exciting thing? And now we're all mobile
and HTML5 and responsive (well, I'm not, but one thing at a time). Presumably
a decade from now this place will be powered by pure hydrogen and exist in a
glittering mesh of collaborative consciousness joining us across the stars or
something.&lt;/p&gt;

&lt;p&gt;I might even have fixed the title elements by then.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;As days pass by&lt;/em&gt;, eh? That's 3655 days passed by. Here's to the
next few thousand.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_77d51ab541b954bd271b0848af65be66</guid>
         <pubDate>Mon, 23 Apr 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Publishing a folder with Ubuntu One</title>
         <link>http://www.kryogenix.org/days/2012/04/18/publishing-a-folder-with-ubuntu-one</link>
         <description>&lt;p&gt;Ubuntu One has the concept of &lt;em&gt;publishing&lt;/em&gt; a file — that is, giving a file in your personal cloud a URL so that anyone can download it, if you tell them the URL — but you can't currently do that with a whole folder of files. Since that'd be quite a useful thing to be able to do, and it's not yet supported by U1 itself, I wrote a little script to do it, &lt;a rel="nofollow" target="_blank" href="http://bazaar.launchpad.net/~sil/+junk/utility-programs/view/head:/u1-publish-folder"&gt;u1-publish-folder&lt;/a&gt; (the script needs you to be on Ubuntu 12.04, which is released next week). Simply do &lt;code&gt;u1-publish-folder /path/to/synced/folder&lt;/code&gt; and it'll give you a URL for the index for that folder; a handy way to get a bunch of files to someone without a U1 account&lt;span style="color:red;" title="are there such people? surely not!"&gt;*&lt;/span&gt; where they can pick and choose the ones they want (rather than sending them a zip file, or sharing a folder with them).&lt;/p&gt;

&lt;p&gt;The way it actually works is to publish all the files in the folder, then create an HTML index file linking to all those published files, then sync and publish the index. So you get a directory listing, like Apache gives you when you browse a folder: &lt;a rel="nofollow" target="_blank" href="http://ubuntuone.com/4rNvr04irwoXkYcFeaeU4L"&gt;List of files in testpublishfolder&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The thing I found nicest about this is working with &lt;code&gt;SyncDaemonTool&lt;/code&gt;, the Python U1 controller. Combined with Twisted's &lt;code&gt;defer.inlineCallbacks&lt;/code&gt; stuff, it makes dealing with U1 really easy:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;@defer.inlineCallbacks
def dosomething():
    sd = SyncDaemonTool()
    metadata = yield sd.get_metadata("/home/aquarius/Documents/somefile")
    print metadata
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Normally, &lt;a rel="nofollow" target="_blank" href="http://shotofjaq.org/2010/03/going-async/"&gt;dealing with async stuff is hard&lt;/a&gt;, but it's just dead easy this way; simply throw in a &lt;code&gt;yield&lt;/code&gt; and you can write code as if it's normally synchronous but it's &lt;em&gt;actually&lt;/em&gt; async, so your program doesn't block while it's working and you don't need to invent a zillion "callback" functions (whether they're anonymous functions or not). I like this.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_e41e0119d983c381b690d3a511dac605</guid>
         <pubDate>Wed, 18 Apr 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Potton in 2012, a video drivearound</title>
         <link>http://www.kryogenix.org/days/2012/04/09/potton-in-2012-a-video-drivearound</link>
         <description>&lt;p&gt;About six months ago I saw a YouTube video of Bedford, the nearest big
town to where I grew up, in the mid-eighties. (It probably wasn't
&lt;a rel="nofollow" target="_blank" href="http://www.youtube.com/watch?v=oyugYKsPSCU"&gt;this one&lt;/a&gt; but that's
fairly close.) It was fascinating; we used to go shopping in Bedford back then
when I was a kid, and seeing all the shops that are no longer there was
most interesting. Anyway, I mentioned this to my dad, and he said: we should
do something like that for Potton, the town in which I grew up (and in which
my parents still live). Today we did exactly that; since Potton is a small town,
we drove down every street in town and recorded it on video.&lt;/p&gt;

&lt;p&gt;You learn a new respect for the Google Street Car people doing this, I can
tell you.&lt;/p&gt;

&lt;p&gt;I wanted to add maps and details of which street was which in the video, and
after some playing around with the OpenShot video editor&lt;span style="color:red;"
 title="which crashes a lot more than it should"&gt;*&lt;/span&gt; I worked out how to
do just that. Each street gets a couple of seconds of "title" showing its name
and also where it is on a map of Potton. The maps were made possible by
&lt;a rel="nofollow" target="_blank" href="http://www.openstreetmap.org"&gt;OpenStreetMap&lt;/a&gt;, which is like Google
Maps crossed with Wikipedia; it's a map of the whole world, but it's created by
people and not by corporations who want money to licence it, and therefore 
you're allowed to use the maps to do interesting things.&lt;/p&gt;

&lt;p&gt;Warning: technical stuff about vector graphics formats coming up. Skip this
paragraph if you don't care.&lt;/p&gt;

&lt;p&gt;What I did was get a map of Potton from OSM, export it as SVG,
and then go through that map in Inkscape and mark each road with the name of
that road. I was enormously pleased to see that each road on an OSM SVG is an
individual path (making this possible). OSM people: if you wanted to do 
something really cool, then in an SVG export make each path have the name of
the road that it is as its ID (rather than "path2319" or whatever). This is
probably quite hard (each road has at least the path defining the street itself,
a path defining the border of that street, and the text), but naming these as
"roadHighStreet_main", "roadHighStreet_background", and "roadHighStreet_text"
or something might be possible. Anyway, once I had an SVG with all the IDs set
to be the street names, &lt;a rel="nofollow"
 target="_blank" href="http://www.kryogenix.org/code/make_potton_svgs.py"&gt;a quick Python script&lt;/a&gt;
was enough to turn that into one SVG per road with that road highlighted in red.
(You can get &lt;a rel="nofollow" target="_blank" href="http://www.kryogenix.org/code/Potton.svg"&gt;the SVG of 
Potton with all roads marked with IDs&lt;/a&gt; as well, if it's useful to you.) The
script also creates an "overlay SVG" for each road name as well, so that I could
overlay the road name onto the video so you can see at any point where you are
in town.&lt;/p&gt;

&lt;p&gt;End of technical stuff.&lt;/p&gt;

&lt;p&gt;This was a fun little project. I mean, what you've got is a video which is
nearly two hours long and is nothing but driving round a small Bedfordshire
town, so it ain't gonna win any Oscars, but I'm pleased we did it. Maybe in 
twenty years someone will find this on YouTube and be amazed at what Potton 
looked like in 2012.&lt;/p&gt;

&lt;p&gt;&lt;a rel="nofollow" target="_blank" href="http://youtu.be/eqzB7hf88GA"&gt;Potton in 2012, a video drivearound&lt;/a&gt; (and &lt;a rel="nofollow"
 target="_blank" href="http://archive.org/details/PottonIn2012AVideoDrivearound"&gt;
downloadable in webm and h.264 format&lt;/a&gt;)&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_5956e3163de95eaa93203badf6971674</guid>
         <pubDate>Mon, 09 Apr 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>This time, more than any other time</title>
         <link>http://www.kryogenix.org/days/2012/03/27/this-time-more-than-any-other-time</link>
         <description>&lt;blockquote&gt;"Here lies Edmund Blackadder. And he's bloody annoyed."&lt;/blockquote&gt;

&lt;p&gt;Tonight I went to see my daughter dance in a show. Also there with me was my 
ex-wife's mother, and the chap she married a couple of months ago. So I suppose
that would make him my future-step-ex-father-in-law. For simplicity we'll
call him Rowland. Anyway, I wanted to video a particular bit of the show (a bit
with Niamh in, obviously) but couldn't since I was a row or two back, so Rowland
did it on his phone. During the interval I said: I'd like that video, and I know
Sam&lt;span style="color:red;" title="ex-wife"&gt;*&lt;/span&gt; would too because that
particular bit wasn't in last night's show, which &lt;em&gt;she&lt;/em&gt; saw. And Rowland
said: OK, how do I get it to you?&lt;/p&gt;

&lt;p&gt;Now, this is a modern flagship smartphone he's holding in his hand, not 
some ancient Sagem thing with buttons. So I said: just email it to me. How do I
do that? he says, and hands me the phone. It turns out that he's got this phone
in order that he can get the football results on it, and to send text messages.
Never set up an email account: didn't even know you &lt;em&gt;could&lt;/em&gt; read email
on phones. He's a smart guy; just doesn't care about the technology, and who
can blame him? Still, OK, I've got a video on this phone, and I want to
get it to me, somehow. We've got good internet coverage. So, how do I do it?
Guess away!&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;email it to my own email address&lt;/strong&gt;: can't do that, because
he hasn't set up his email account, and I can't ask him to do so because we're
sitting in the audience of a show and he doesn't know how anyway.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;text it to my phone&lt;/strong&gt;: nope, video's too big (40MB or so)&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;upload it to my Ubuntu One account&lt;/strong&gt;: before we start here,
this is his phone, so I was understandably wary of signing into any of 
&lt;em&gt;my&lt;/em&gt; accounts on it, but since he doesn't have any of his own accounts
set up, perhaps I have no choice. So, reluctantly, I sign into Ubuntu One as 
myself and try uploading&amp;hellip; and the browser crashes. Try it again, crashes
again. Hm, thinks I, sounds like we've got a bug there. Sign out of U1. What 
else can I try?&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Use some temporary file upload service&lt;/strong&gt;: ok. How does one
find one of these which isn't just for warez and porn and hooky videos? (You 
may have noticed that I am &lt;em&gt;living&lt;/em&gt; &lt;a rel="nofollow"
 target="_blank" href="http://xkcd.com/949/"&gt;xkcd.com/949/&lt;/a&gt; at this point.) Bit of 
Googling, and I found one which looked sensible (note:
the key trigger word, at least at this point in time, is "html5"; it may get
you a bunch of hot air and bullshit from industry analysts, but if a site 
mentions it then it's probably relatively modern, at least.) Try uploading (I
can't remember which one I found), and&amp;hellip; browser crashes. So it's not an
Ubuntu One problem (phew!), it's just with file uploading from this browser.
Bloody fantastic. What else can I do?&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;bluetooth it to &lt;em&gt;my&lt;/em&gt; phone&lt;/strong&gt;: tried that, and my phone
rejected it but I don't know why. Can you send 40MB files over Bluetooth? Maybe
this is a fault in my phone. Don't know. Didn't work. Next attempt.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;sign in to my email account and send it to myself&lt;/strong&gt;: OK. There
are three email clients on this phone (three email clients for fuck's
fucking sake!?&amp;#8253;). One of them is a gmail app. I am scared of signing
into my gmail account in an official gmail app in case the phone Learns My Account
and I can't remove it easily. Second email app says "Your trial has expired.
Please renew your subscription" (honestly? Trialware on a &lt;em&gt;phone&lt;/em&gt;? What
kind of shitty world do we live in where this is a good idea??). Third email 
app, I create a new email account which is my gmail account (with fear and
trepidation), and try sending an email to myself with the video attached. 
"Email sending&amp;hellip;", it says, followed by&amp;hellip; nothing. No indication
that it had worked or had not, except that I had no email (and that there was
no way that 40MB had uploaded that fast). Tried it twice; same thing. Delete
my email account from crappy email client. Next.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;sign into my gmail account in official gmail app&lt;/strong&gt;: fearful
plan, this. Fortunately, it failed early enough that I didn't have to try;
attempting it gives "file too big to attach". Thanks a fucking
bundle, gmail. Oh no wait, no thanks at all. Try something else.&lt;/p&gt;

&lt;p&gt;Now somewhat desperate. There is a "flickr" app here. Maybe I can upload
the video to my flickr account? Flickr does videos now, I think. Sign in to
flickr app with ancient Yahoo ID, video starts uploading! yay! FIFTEEN MINUTES
later it gets to 100%, and... then just sits there at 100% without completing.
And then it goes back to zero and starts again. It gets to 65% done a second 
time and then the show ended. Since my only two options were to go home or
to throw Rowland's phone into a volcano and &lt;em&gt;then&lt;/em&gt; go home, I gave him
back his phone and went home.&lt;/p&gt;

&lt;p&gt;We have failed as an industry.&lt;/p&gt;

&lt;p&gt;Now, there are those of you reading this and thinking: that wouldn't have
happened if he'd have had &lt;em&gt;this phone&lt;/em&gt; or &lt;em&gt;this app&lt;/em&gt; or 
&lt;em&gt;this software&lt;/em&gt; or &lt;em&gt;this service&lt;/em&gt;. Stop thinking that. This is
a guy not interested in technology who bought a flagship internet device and
has been appallingly let down by that. How will he be helped by you sneering
and using his failure as an excuse to score political points? We're in this
to help users, remember: not just the ones who think as we do, but the ones
who &lt;em&gt;rely on us&lt;/em&gt; to build things for them because they don't know what
they're doing. If your response is honestly "well, he should have spent more
on a phone to get something better", then I'm exceedingly disillusioned by you.
"The internet brings freedom, but only to rich people"? Really? Is this what
the Open Web, the technological revolution is all about? If your answer is
"he needs different software"&amp;hellip; really? Are we ever going to get past
the point where saying "I have a problem" just gets you a hundred responses 
about how it's your fault for having picked the wrong computer? We have failed
as an industry. If the best we can do is fight amongst ourselves and scratch 
like cats in a bag then it's hardly surprising we fail so badly. Then again,
perhaps we're not in this to help people; we're in this to make money and 
helping is a sort of epiphenomenon. Some of us may be thinking: a company who
builds a product this frustrating will surely be eliminated by the marketplace.
Leaving aside for a moment how the tech crowd, normally as liberal a group
of people as you might want to meet, become rabid free-market boosters when
a product we like becomes popular (football teams have had a chant about this
pernicious behaviour for decades now. It goes: you only sing when you're 
winning), think about all the people who get inadvertently screwed by this
laissez-faire capitalism. Every company who gets "eliminated by the market"
still sold a shedload of devices to a shedload of people, and all we have for
them is to say "soz, dude, you made the wrong choice, you've been eliminated
by the market, you are the weakest link, goodbye"? Can't we do better?&lt;/p&gt;

&lt;p&gt;There's nothing we can do, though! comes the cry. What can we, innocent
technical people, do to influence the movements and decisions and marketing and
choices and products of some of the largest companies on earth? I don't know.
But take that feeling of helplessness you have right there, and now &lt;em&gt;imagine
how helpless you'd feel if you didn't even understand the technology&lt;/em&gt;. 
That's how helpless our users are when we get it wrong, or when someone else
gets it wrong and instead of helping we tell screwed people that it's their
own fault for buying the blue phone instead of the one we recommended.&lt;/p&gt;

&lt;p&gt;Niamh danced superbly, by the way.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_6efb5116e06f03f2487b256c3aa9153f</guid>
         <pubDate>Tue, 27 Mar 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Step away from the localStorage</title>
         <link>http://www.kryogenix.org/days/2012/03/20/step-away-from-the-localstorage</link>
         <description>&lt;p&gt;There has been much discussion (&lt;a rel="nofollow"
 target="_blank" href="http://hacks.mozilla.org/2012/03/there-is-no-simple-solution-for-local-storage/"&gt;example&lt;/a&gt;, &lt;a rel="nofollow"
 target="_blank" href="https://blog.mozilla.com/tglek/2012/02/22/psa-dom-local-storage-considered-harmful/"&gt;example&lt;/a&gt;, &lt;a rel="nofollow"
 target="_blank" href="http://webreflection.blogspot.co.uk/2012/03/whats-localstorage-about.html"&gt;example&lt;/a&gt;, &lt;a rel="nofollow"
 target="_blank" href="http://paul.kinlan.me/we-need-to-kill-off-the-localstorage-api/"&gt;example&lt;/a&gt;) 
recently about how the &lt;a rel="nofollow" target="_blank" href="https://developer.mozilla.org/en/DOM/Storage"&gt;in-browser localStorage API&lt;/a&gt; 
is terrible and must be killed with fire.&lt;/p&gt;

&lt;p&gt;My first reaction here is &lt;a rel="nofollow"
 target="_blank" href="http://www.thedailymash.co.uk/news/health/leave-bacon-out-of-it,-health-experts-warned-20071031506/"&gt;step
away from the bacon, son, leave the bacon out of this&lt;/a&gt;. The localStorage API
seems to have a few quoted problems, the main ones being that it's synchronous,
it does file IO, and it's got bad event support. Put against that, rather 
snidely it seems, is the benefit that "it's easy to use".&lt;/p&gt;

&lt;p&gt;Did I miss a meeting? Is being easy to use suddenly a bad thing? Isn't that
one of the major benefits of using Apple stuff, that it makes sense and people
can get it without a PhD in computer science? Or does that only apply to 
&lt;em&gt;users&lt;/em&gt;, who are presumably too busy on the sofa with a bag of Cheetos,
and not to &lt;em&gt;developers&lt;/em&gt;, who are meant to do things the hard way whenever
possible?&lt;/p&gt;

&lt;p&gt;Doing file IO and having bad event support are, certainly, issues with 
localStorage if you're trying to use it for any kind of really serious data
storage. If you're Gmail, maybe you want something better. But you know what?
Most of the things I build aren't Gmail, and most of the things you build aren't
either. I don't need event support for localStorage; I just want to stash a
value in it and then move on. That's all. Doing file IO… well, any storage
mechanism had better be doing file IO at &lt;em&gt;some&lt;/em&gt; point so that my 
data gets saved to disc!&lt;/p&gt;

&lt;p&gt;Ah, no, say the detractors, but it's &lt;em&gt;synchronous&lt;/em&gt;. That's bad: it 
blocks. This seems to boil down to two problems: it might block my tab, and
it might block other people's tabs. Now, that's an issue, right enough. However,
blocking my tab is something that I can think about and decide whether I'm
prepared to run the risk or not. Because what you're asking for is that I replace
this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;localStorage.setItem("key", "value");&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;with this&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;storeSomething = function(key, value) {
    var request = indexedDB.open("mydbname",
        "This is a description of the database.");
    request.onsuccess = function(e) {
        var v = "1.0";
        var db = e.target.result;
        if (v!= db.version) {
            var setVrequest = db.setVersion(v);
            setVrequest.onsuccess = function(e) {
                var store = db.createObjectStore(
                    "myobjectstore", 
                    {keyPath: "timeStamp"});
                var request = store.put({key: value, 
                    "timeStamp" : new Date().getTime()});
                request.onsuccess = function(e) {
                    // now carry on with what I was doing
                };
            };
        }
    };
}&lt;/code&gt;&lt;/pre&gt;


&lt;p&gt;and you know what? Given that choice… I believe I might at least
sometimes choose that blocking my tab for a microsecond and very occasionally
blocking my tab for two whole seconds is actually OK. I'm allowed! It's my 
tab!&lt;/p&gt;

&lt;p&gt;Fine, I'm being a bit facetious. There are problems with localStorage, and
it would be good to see them resolved. But there are alternatives other than
"you must ditch it and use IndexedDB, Mr Developer", I think. What would be 
wrong with providing an asynchronous variant of localStorage, so I do 
&lt;code&gt;localStorage.setItemAsync("key", "value", function() { carryon... })&lt;/code&gt;?
Mozilla say "Implement localStorage in an asynchronous fashion in browsers – 
actively disregarding the spec? (this could set a dangerous precedent though)",
as if the idea of the browser manufacturers working together to adjust the spec
is just impossible; did I miss something there? The spec process is open to
stuff being adjusted or added to; that's the point of it, right? And 
localStorage use in my tab blocking other people's tabs… I can't think 
of a nice way of saying "that's a browser issue", but it is. I feel sad having 
to say that, because I know that the engineers at Mozilla and other places have done
superhuman work in this area and will continue to do so, but really one tab
blocking causing others to block is surely something which is a problem for
more than just localStorage?&lt;/p&gt;

&lt;p&gt;There are problems with localStorage. Real ones. But I think that those
calling for its complete removal are vastly underestimating the attractiveness
of an API that's easy to use, and also vastly underestimating how annoying it is
to be forced to use something way more complicated because it copes better with
pathological cases. I'd love to hear more argument on this subject, but I don't
want it to look like there's a consensus around "it must go". Someone needs to
speak up for developers who just wanna get stuff done, like me...&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_3e4eabcf30dcafee154bf36c4b3c00ae</guid>
         <pubDate>Tue, 20 Mar 2012 00:00:00 +0000</pubDate>
      </item>
      <item>
         <title>Ubuntu Accomplishments and Ubuntu One</title>
         <link>http://www.kryogenix.org/days/2012/03/16/ubuntu-accomplishments-and-ubuntu-one</link>
         <description>&lt;p&gt;Those of you who read &lt;a rel="nofollow" target="_blank" href="http://planet.ubuntu.com/"&gt;Planet Ubuntu&lt;/a&gt; 
will doubtless have seen Jono Bacon talking about the &lt;a rel="nofollow"
 target="_blank" href="https://wiki.ubuntu.com/Accomplishments"&gt;Ubuntu Accomplishments&lt;/a&gt;
system that he's been working on along with a growing community of developers
and testers. That system uses &lt;a rel="nofollow" target="_blank" href="https://one.ubuntu.com"&gt;Ubuntu One&lt;/a&gt;
to communicate your accomplishments to the central server that signs them off,
and today I'd like to talk about why it does that.&lt;/p&gt;

&lt;p&gt;There are a bunch of little reasons why the Accomplishments system uses
Ubuntu One, and one big reason. The big reason is this: &lt;strong&gt;running a
service that serves lots of people is hard&lt;/strong&gt;. Ask anyone in a startup;
ask Twitter; ask anyone who has seen a webpage saying &lt;code&gt;504 Gateway 
Timeout&lt;/code&gt; or "We're experiencing a lot of traffic at the moment". If your
service becomes popular, making it able to cope with the number of people using
it is a difficult job. You need to have servers for the web service itself,
servers to fail over onto if those get too busy or crash, servers to 
load-balance between them, servers to run haproxy, servers to be the front-end,
servers to cope with unwrapping SSL, servers to run the underlying database,
servers, servers, servers. It's hard work, and the state of the art evolves
every single day. And this is because a web service is &lt;em&gt;synchronous&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;You may think here, "huh?". Take a step back. The Ubuntu Accomplishments
system lets you get two&lt;span style="color:red;"
 title="three, actually, but the third is sort of theoretical at the moment"&gt;*&lt;/span&gt;
types of accomplishments: &lt;em&gt;local&lt;/em&gt; and &lt;em&gt;machine-verified&lt;/em&gt;. Local
accomplishments are things that only occur on your machine: you've just beaten
Solitaire, for example. We need not talk further of those here. Machine-verified
accomplishments are those which you are awarded (by a script running on your
machine which checks whether you've accomplished them) and then that award is
verified by another machine, so you can't lie about having them; this is things
like filing your first Launchpad bug, joining your Ubuntu loco team, and so on.
The obvious way to build this system would be to have the script which runs on
your machine check whether you've filed your first Launchpad bug, and then if
you &lt;em&gt;have&lt;/em&gt;, to request &lt;code&gt;http://ubuntuac.com/verify?email=me@example.com&amp;accom=first-launchpad-bug&lt;/code&gt;
and have that server verify that you have indeed got it. However, imagine a world
in which many many people have installed the accomplishments system; our poor
ubuntuac.com server would be overwhelmed. We'd have to care about haproxy and
load-balancing and front-ends and nagios and so on. Now, this might actually be
OK for an Ubuntu service — the Canonical sysadmins are excellent at their 
jobs — but it ought to be possible to build things without needing a whole
sysadmin team.&lt;/p&gt;

&lt;p&gt;This is exactly the same issue that desktop programs have; if you try and
do something which might take a long time, and then block waiting for the result,
your application hangs. Reading a file will make your app go grey if it turns
out to be a long file. The way to fix this is to be &lt;em&gt;asynchronous&lt;/em&gt;,
to request the file and have it load in the background and then call you back
when it's done. Building a popular service is similar. The way to build such
a service isn't to hit some verify URL and then wait for the result, because 
then the service has to rush to give you an answer, conscious that you're waiting
for it. Be asynchronous. And that's what Ubuntu One brings to the Accomplishments
system. Instead of verifying an accomplishment immediately, the Accomplishments
system stores it in Ubuntu One, in a folder which is shared with the 
Accomplishments server. It'll then be synced to Ubuntu One, and then to the
Accomplishments server; the server can verify it at its leisure and then sign
the accomplishment, and that signature is then synced back to Ubuntu One and
then down to your machine. None of these steps are harmed by waiting. If your
computer goes offline halfway through the process, no problem: your 
accomplishment will be synced when you go back online. If the Accomplishments
server has a million things to do, no problem; it works through them as fast
as it can manage and each will be done in turn. If Ubuntu One itself crashes,
no problem; your accomplishments will sync when it recovers. If the Accomplishments server
dies, no problem; you're not waiting for a URL from it, so you'll not get
a Gateway Timeout; instead, the server will be fixed from crashing and then
just carry on with its list of files, and any accomplishments that were sent to
it while it was dead will still arrive.&lt;/p&gt;

&lt;p&gt;Of course, it would be possible to build a web service and an Accomplishments
client which achieved this in other ways. Have the Accomplishments client detect
whether you're online and queue up requests if you're not; have it detect if the
connection drops while it's asking for verification; have the Accomplishments
server receive a verify request URL and then return an "it's in my queue, here's
your claim ticket" token and have the client periodically poll for that ticket
or wait on a Comet connection. But that's still a lot of effort, and it's a lot
of effort that Ubuntu One &lt;em&gt;already does for you&lt;/em&gt;. The Accomplishments 
client can get all this network-y retries-y queue-y cleverness just by dropping 
a file in a folder, and doing it that way means that services can be built by
normal mortals rather than super-network-experts. Go asynchronous and let
someone else do the really difficult work for you. That's why the Accomplishments
system uses Ubuntu One, and it's why it's able to exist and scale without having
an army of sysadmins keeping it going, no matter how many people use it.&lt;/p&gt;

&lt;p&gt;If you're interested in building services which work like this, chat to me, because
I run the Ubuntu One app developer programme.&lt;/p&gt;</description>
         <author>sil</author>
         <guid isPermaLink="false">0b36d196b9e83fe728bf34a46a14a10d_41676b4fe7151900f7bd889a547ab0bc</guid>
         <pubDate>Fri, 16 Mar 2012 00:00:00 +0000</pubDate>
      </item>
   </channel>
</rss><!-- fe3.yql.bf1.yahoo.com compressed/chunked Mon May 21 13:44:26 UTC 2012 -->

