Control streaming audio on a remote PC with node.js

Over the weekend I got impatient waiting for my Chromecast to arrive so I built netbook-web-streamer. It’s a node.js app that loads URLs in an iframe on a remote PC that’s plugged into your large speakers. I use it to listen to playlists on songza and individual songs from youtube.

To play a song, enter it in the form on the homepage, or click the bookmarklet when you’re on a page you want the remote PC to load.

netbook audio streamer UI

How this works

There are 3 routes ’/’, ’/loadUrl’, and ’/audio’.

/ is the homepage. From there you can send xhr GET requests to /loadUrl with a &url param. The node.js view then broadcasts a event to a client that has loaded /audio. The event handler on the client takes the url value from the message and loads it in an iframe.

The only complication is that youtube forbids running videos on the main site in an iframe by sending an x-frame-options header. The workaround is to extract the video id from the url and turn it into an embed url.

Build an animated gif photo booth with HTML5 and JavaScript

I built an animated gif photobooth for the Indeed July 2013 hackathon.

Screen Shot 2013-07-19 at 2.14.51 PM

We got some good shots.

Gif photobeerhighfive

If you just want to run the app, the source is on GitHub: There’s no public demo because the code isn’t terribly secure and the images it produces are about 3mb each. But don’t let that stop you from playing with it.

If you want to implement something like this on your own, avoid Flash-based libraries like “jquery-webcam-plugin” or “scriptcam”. They’re a waste of time. New versions of Chrome let you do everything you want through Canvas and WebRTC’s Stream API.

First, read MDN’s excellent article, Taking webcam photos. They have annotated some JavaScript that shows how to grab a frame from a <video> stream, write it to a canvas, and getImageData() into the src attribute of an image element to display it on the page for a user.

I put some jQuery on top of their code to capture a bunch of frames in quick succession and POST the base-64 encoded data urls to a Flask backend. The Flask view  waits until it receives every frame in the set and stitches them together with ImageMagick.

The ImageMagick part is key. PIL and Pillow are huge timesucks for something this simple. ffmpeg is a nightmare. I dare you to look at its man page. If you ever want to create gifs, just use ImageMagick. It’s by far the easiest option.

Anyway, there are a few big issues with this project that are symptomatic of a hackathon. First, it takes a few CPU-intensive milliseconds in between image captures to load the canvas into a data url. This holds up the one and only thread, temporarily locking up the UI and preventing you from having a buttery smooth framerate. You could probably fix this with Web Workers. The other problem is that uploading 15 base64 strings containing medium-sized images takes longer than sending binary data like you would for a multipart/form-data file upload. You could get around this by writing the images to files with the File API and then uploading them from disk. And finally, the batches of images are grouped only by millisecond timestamp, so a unique identifier should be added if you want to get this ready for prime time.


git diff with full context

By default, git diff only spits out three lines of context above and below your changes. However, it’s possible to include the entire file. Generate a patch of some changes with full context:

git diff --no-prefix -U1000 > /tmp/mydiff.patch

If you’ve already committed your changes, you can use git show with the same syntax:

git show --no-prefix -U1000 > /tmp/mydiff.patch

These are useful for pre-commit code reviews in Crucible. You can just upload the resulting patch file.

The –no-prefix option gets rid of the “/a/” and “/b/” destination prefixes that show up by default.

The -U flag specifies lines of context. You might need to increase this if there are more than 1000 lines between your changes.

If you don’t want to type all that out, add an alias in your ~/.gitconfig file.

 code-review = diff -p --no-prefix -U1000

Then you can just do:

git code-review > /tmp/mydiff.patch


WordPress has great docs

See those nicely ordered links in the sidebar?

“Projects, Mentions, Web Development Tools”

Thank the WordPress documentarians for that. This theme (wp_svbtle) doesn’t sort them by page_order by default. You have to add this snippet in its header.php.

$pagesArgs = Array(
    'sort_order' => 'ASC',
    'sort_column' => 'menu_order'
$pages = get_pages($pagesArgs);

I know this because the WordPress docs are phenomenal. Check it:

This is a blueprint for every software project.

Default Usage
Params (with human-friendly explanations)
Return (way faster than inspecting in a debugger)
Example (contains multiple)
Source File (saves so much time if you want to read the code)
Related (similar functions, great for devs unfamiliar with the library)

Even the page is nicely formatted. WordPress deserves a hand. I know they had 10 years to get it right, but it’s still something to strive for.

Related: My buddy Alban tells of his sordid past with PHP.

Stop watching TV (everything is TV)

You think you’re a productive badass because you don’t watch TV. You didn’t have one in college and you never bought one after. Sure, you’ll curl up with your macbook for some netflix, but that takes up far less time than the widescreen does for the average Middle American.

Stop lying to yourself. You consume even more TV than Joe Sixpack. The trick is that the internet has separated the concept of TV from the medium of the television. It’s not 49.99 a month for cable. TV is any consumptive activity that gives you what you want and tells you who you are. And that’s what 99% of urls point to. This is not a conspiracy. This is supply and demand. The economy wants your labor and your money. You’re going to give it far more than that.


–Employed adults living in households with no children under age 18 engaged in leisure activities for 4.5 hours per day, an hour more than employed adults living with a child under age 6. [0]

Thanks, BLS. How much of that was TV?

–Watching TV was the leisure activity that occupied the most time (2.8 hours per day), accounting for about half of leisure time, on average, for those age 15 and over.

You’re not better than John Q. Public Access. Your 2.8 hours always begin with “http”.

I. This is TV for everyone:

Facebook is TV


Up top we have Exhibit A: outrage. This person has found something on the internet that she finds upsetting. Surprise. It’s from Gawker, a machine that chews up liberal arts degrees and spits out liberal outrage to the tune of $2m a day. Our friend’s outrage has not produced anything more than a remote control. She shared an article that was made just for her, cementing her own identity through consumption while encouraging others to do the same. Facebook/Gawker just told her who she is.

Don’t get cocky. She is you.

“But I don’t post mindless drivel from those blogs.”

Replace “Gawker” with “The Atlantic”. Uh oh.

Let’s move on to the second post, Exhibit B: Here’s an Imgur link to some gifs on a backdrop of banner ads. When you watch looped animations of furry animals, Facebook/Imgur has given your brain exactly what it wants; Kahneman’s System 2 remains dormant[1] not just for the 6.5 seconds it takes to watch the gifs, but the subsequent 30 minutes you’ll spend infinite-scrolling. Both companies’ investors are betting hard on the fact that it feels kind of nice when your brain is melting. Try not to drool on your keyboard.

“I’m not a sheeple! I don’t even click the ads!”

I believe you. But Facebook ads were never for you. They’re for your parents and FB shareholders. The sidebar ads are a distraction from the real ads, the snippets of content tailored just for you by companies you’ve never heard of. They don’t show up as banners. They’re dumped directly into your news feed by people you know. Facebook TV is far more insidious than television ever was because you can no longer go to the bathroom to skip the commercial. The content is the commercial and they’ve hired your mom as a sales rep.

II.  This is TV for men who will consume/are consuming/ have consumed college.


When you see a screen like this on your computer, you should close your eyes and hit ⌘-W. You will have avoided a careful construction of content that tells 18-25 atheist Tupac fans who they are. Reddit is to college guys what honey is to Pooh Bear. Your brain cannot resist the cesspool of interesting factoids, in-jokes, and “unpopular” opinions. You’re getting what you want.

He'll be here for a while

He’ll be here for a while

The real cost of Reddit TV is not the cash you’ll spend on identity-affirming products, but the opportunity cost of doing anything else at all. You’ve seen this happen to some of your college buddies. Reddit is a time-wasting badge of honor for underachieving English majors.

“I’d be successful if I got off Reddit, buckled down, and finished my screenplay. I’ve really started to flesh out the ideas.”

A few years ago the site became a kind of nerd shibboleth. In 2009 every CS major could name drop Reddit and wink at their peers for a little self affirmation. Today, students of all disciplines can join the fun for the small price of 2 hours per day and their personalities. Somewhere between the Imgur links and Neil DeGrasse Tyson memes the programmer-types changed the channel to Hacker News and were never heard from again.

III. This is TV for women of all ages.

Pinterest is TV


Half of the boxes tell you who you are (fashion, beauty, fitness) and the rest show you what you want (food). But the icing on the cake is the motivational in the bottom right.

Wear whatever you want.
Be yourself.

The dissonance here isn’t any greater than it is for the boys of Reddit or the masses of Facebook, but try to savor the juxtaposition.

Wear whatever you want (from this list of affiliate links)
Be yourself (because you’re worth it™)
Think (about working out later but just keep scrolling for now)

IV. The red pill

90% of people will probably never do anything meaningful because they’re glued to TV. This is good news for you because you know the score. Once Morpheus et al realized they were in The Matrix they started doing some rad shit. Stick to the plan and you’ll get superpowers in the form of 2.5 free hours a day.

1) Consolidate and minimize your consumption. Ok, you’re not going to live in a cave. You still have to act like you live in this decade. So use digests. Pick 3 niche things you really care about and sign up for the weekly newsletters[2]. And if you have to read something elsewhere, make sure it has paragraphs. Worried about general informedness? The Economist has an audio edition for your commute. Perspective gained by a one-week lag far outweighs the value of timeliness. And if anything 9/11-serious happens someone will text you.

2) Stop consuming all forms of TV.

Just quit. Go cold turkey and write about it on your blog. But you have to actually quit. Thinking that you have the power to quit is the same as not quitting.

3) Fill the void.

With remarkable self-control you now find yourself with spare hours every day. But now that you’re actually face-to-face with your creative endeavor, you’ll erect artificial barriers to entry in the form of “I need X before I can do Y.”

“I need to get my website working but I still haven’t found the right font.”

“I need to buy a synth and learn to play before I can start producing my own beats.”

“I need to write a meandering blog post about not wasting time before I start writing code.” (whoops)

If you have to kill time to wait for X you’re taking the blue pill. You don’t get to claim an unmet dependency when you have a device that can create almost anything.

Macbook TV
The macbook you’re reading this on is a ticket out of mediocrity. You can use it to write a novel, an app, or a death threat. Go ahead. Start a company, compose a symphony, or hack a bank across state lines. Whichever option you choose, try to enjoy the irony that the computer marketed to “creatives” is sold to the aspirational masses for use as a consumption device. It’s a Stradivarius. Don’t use it like a Big Gulp.

Last year I saw this interaction that has stayed in the back of my mind. Zach Weiner of SMBC fame was doing a Q&A session at UT. Here are two (roughly paraphrased) exchanges that I’ll never forget.

Q: “What webcomics do you read?”
A: “I don’t really read any. I mean, I read a few of my friends’ just to be polite, but when I started I didn’t read any. I felt like I would be derivative if I absorbed other people’s ideas.”

This is key. Consumption of similar media is unnecessary for creative production.

Q: “What do you do about writer’s block?”
A: “Writing is work. I sit down and churn out ideas, even if I don’t love them. The archetype of the troubled artist with ennui is bullshit.”

I wish I had a video of the guy asking the question. He was so smug that couldn’t see Weiner’s distaste for his attitude. Don’t be the guy that thinks he’s better than everyone what he knows (rather than what he does). This psychological condition is why Reddit feels so good. The million little facts, stories, and trends feed your ego, making you think you’re clever. But it’s 1am and all you’ve done is scroll.

V. Adios

Starting today (5/19/2013) you won’t catch me watching a Facebook newsfeed, a Twitter stream, a Pinterest board, Tumblr, Instagram, Reddit, Hacker News, Slashdot, Imgur, Google News, etc etc. There are still plenty of ways to get in touch. Facebook Messenger, Google Talk, Skype, Gmail, and Groupme remain legit. But if you ever see me click a Buzzfeed link, just give me the Lenny treatment. Mice-and-men style.

[0] BLS leisure info


[2] Hacker Newsletter and JavaScript Weekly

Update 9/8/2013: See also: Technology is Heroin