Thomas Fuchs
Hi, I'm Thomas Fuchs. I'm the author of Zepto.js, of, and I'm a Ruby on Rails core alumnus. With Amy Hoy I'm building cheerful software, like Freckle Time Tracking and Every Time Zone and write books like
   Want me to speak at your conference? Contact me!

How to not write a letter to your paying customers

July 7th, 2013

Yesterday, I received an email from Boxee, which was recently acquired by Samsung. It’s one of the worst written emails from a company that I ever received (and I get plenty of email!).

Let’s have a look at what’s wrong with it.

Subject: Boxee team to join Samsung

Well, that’s informative enough but it really doesn’t say why I should care. Well, reading on…

We’re pleased to announce that the Boxee team will be joining Samsung.

Thanks for not saying hi first. Makes me feel really well taken care of. And great that you’re pleased. I still don’t care.

Samsung is the #1 consumer electronics company in the world. They produce all of the screens we watch entertainment on – TVs, laptops, phones, and tablets.

Go Samsung. I still have no clue why I should care, tho.

We’re excited to collaborate with Samsung on how each of these devices can deliver a more integrated TV experience.

What does that even mean? Exactly, it means nothing, except that likely they won’t support the device I BOUGHT from them anymore.

We’re working behind the scenes to ensure there’s minimal impact to your Boxee Box during this process.

TL;DR: We’ll sell not caring, supporting or doing anything with our existing customers as “minimal impact”. Those stupid idiots should have known what they’re getting themselves into. #lolcustomers

The Boxee Box holds a special place in our heart as the first device we built. It was the first living room device to have a keyboard on the back of the remote. It was also the first XBMC-based set top box to be sold at major retailers. It’s the device that really launched Boxee on the world stage, and we want to thank you for being a part of our journey.

Blah, Blah, part of our journey, blah, blah. Note how they’re talking about the product in the past tense. I bought a product from you that barely works and now you’re saying to go fuck myself. Awesome.

Team Boxee

Boxee Customer

Why don’t they just say that their business didn’t work out and they have to close it down and go work for Samsung? I’d be sad for them and understand. Why lie to their customers? Does that make them feel better? Do the VCs require it from them?

Metrics you should actually track in your SaaS business—and how

June 13th, 2013

If you run a business of any kind, it’s hard to get lost in the ocean of data available to you.

What should you track? And how can you act on it? My presentation from BaconBiz Conf in May will help you get started and contains actual actionable advice on how to track data and then act upon what you learn from it.

Bonus: you’ll learn how to produce smooth trend charts that give you the information you need without the clutter!

All the data in the presentation is taken from Freckle Time Tracking (which is the world’s bestest time tracking app, just so you know!).

BY THE WAY, I’m working on an ebook on SaaS metrics (and some JavaScript magic!)—Interested? Sign up for my mailing list!

3 new HTTP headers that we actually need

June 9th, 2013

The World Wide Web has been one of the greatest revolutions in history in how we humans access information. Sadly, the protocol used for transmission of this information (HTTP) lacks an understanding of humans, with maybe the sole exception being headers about preferred languages. But not all humans are the same and not all internet connections and computers are the same either.

“User agents” should be just that, agents of the users, acting in their best interest. Here’s three suggestions to make HTTP better for us puny bags of water:

User-Tech-Savvyness-Score, a new HTTP header with number in the range of 0 (Your Mom) to 1 (Linus Torvalds) that is transmitted from the user agent to the server. If it’s not there, assume the user is not savvy. Browsers could offer this in their settings. A high score would indicate that users know the jargon and the workings of the intertubes—and user interfaces can reflect that (for example, no need to explain what a URL is for the millionth time).

CPU-Utilization, a new HTTP header that provides an average of CPU load over the last minute or so—ideal to avoid burned laps by those auto-loading videos and Canvas visualizations.

Bandwidth-Average, a new HTTP header that gives an average of the network bandwidth that was available to the browser in the last few minutes (in bits/s), so we can finally deliver assets that are more tailored to the user. How awesome would it be if we can easily decide if we should preload videos or maybe not load those custom fonts and help improve user sanity.

I was going to propose User-Likes-Autoplayed-Background-Music, but we all know the answer to that.

In any case, chances that these headers get implemented are slim—my point is to not forget that your content is consumed by human beings.

Be nice by building fast-loading, good-looking, usable sites. Don’t do on your site what you don’t want to be done to you on sites you visit.

Embedding Canvas and SVG charts in emails

April 30th, 2013

In our app Freckle Time Tracking we’re sending out weekly reports to users by email, reporting to them what they achieved last week.

Our emails not only include a report, listing all entries they logged, but also our “Mini-Pulse”, a graphical representation of how much they worked for each project.

Here’s how a typical email we send out looks like:

Freckle Time Tracking weekly report

Now, generating a table and styling it for the HTML email is (relatively) easy, and beyond the scope of this article, but let’s have look at the charts in the email. We already generate the Mini-Pulse graph in our web app—we use an ancient version of Raphael.js to generate SVG, and this gets the job done nicely (SVG works on practically every modern browser, and Raphael falls back to VML on older Internet Explorer versions). Of course, you could use Canvas or any other HTML supported by WebKit just as well.

This is all great in your web browser, but not for emails. First off, obviously, JavaScript
is disabled in HTML emails, so we can’t use that to generate the SVG on the fly; moreover
SVG only works in a handful of email clients.

The only image formats that reliably work in HTML emails are GIF, PNG and JPEG, which means we have to dynamically generate such an image containing the charts and refer to it from the email.

There’s two possible ways to do this:

  1. Reimplement the logic and rendering with a tool specifically made for generating chart images
  2. Reuse the existing JavaScript/SVG code in a headless web browser and make “screenshots”

We chose to reuse the code we have, so we can easily adapt and extend both the web app and the HTML emails in the future (plus no need to learn yet another tool!).

A great way to create screenshots of the graphs is to use PhantomJS, which is a headless WebKit with an API that has support for taking screenshots.

We also have the following requirements for our report emails:

  • Don’t generate the Mini-Pulse if the email is never opened, to conserve server resources
  • Cache the generated image once the email was opened once
  • Securely serve the image and use encrypted URLs with embedded authentication (the user the email was sent to may no longer have permission to access Freckle at the time the email is opened)
  • Charts should be retinafied (your HTML emails are retinafied, are they?)
  • File size of image should be small so it loads fast on mobile email clients

To fulfill these requirements, here’s what happens when a user opens an email that has a chart embedded:

  1. HTML email is shown
  2. Email client or browser accesses URL in the form of
  3. If there’s a cached version of the image serve it and go to step 10, otherwise continue to step 4
  4. Rails app decrypts account ID, user ID, chart type and date range from the given encrypted URL*
  5. Rails app calls internal PhantomJS web service with a URL to call to generate the chart
  6. PhantomJS web service calls the Freckle Rails app internally
  7. Rails app serves Raphael.js, and our chart generation code and the data needed for it. (We use a special, stripped-down layout that only serves the chart and doubles resolution on everything to simulate rendering on a high-density screen (a feature that Raphael.js doesn’t yet directly support).
  8. PhantomJS renders the page
  9. PhantomJS returns a PNG to Rails (the call from step 4)
  10. Rails returns the PNG and caches it into a file (Rails page caching)
  11. Email client or web browser renders the PNG

All this sounds pretty complex, but it’s actually implemented in just about a hundred lines of code.

There’s a few tricky things you have to deal with when installing Phantom.js on a Linux server, such as adding fonts that may not be part of your default Linux server setup, but it’s pretty easy to get going. For Ubuntu 10.04, you can check out this gist with instructions on getting decent rendering quality.

*To accommodate passing parameters along from an HTML email to our Rails app, I’ve released URLcrypt, an open-source, MIT-licensed Ruby library for ‘elegant’ encrypted URLs. Alternatively, you could also use a table the holds tokens, but I find encrypting the account/user id information a more scalable solution.

Zepto 1.0

March 4th, 2013

Party like it’s one-oh! Zepto, the jQuery-compatible JavaScript micro-library for modern browsers, is now available in version 1.0.

Looking back at the first release, back in October 2010, Zepto has come a long way. It’s now compatible with all modern browsers (except Internet Explorer, and yes, it’s easy to fall back to jQuery) and supports complex frameworks like Twitter Bootstrap.

You can grab Zepto at, and contribute via the GitHub repository.

Notable additions and changes in V1.0

  • Zepto is now compatible with Twitter Bootstrap
  • Portable, completely new node.js-based build system
  • Fully automated tests with PhantomJS and Travis CI
  • Removed touch module from default distribution (you can add with our easy-to-use build system, or just load it in addition)

There’s many more additions and bug fixes—see the detailed change log on the Zepto site.

We’re already planning V1.1, for which we will look mostly into code refinements and performance improvements (Zepto is already pretty speedy, as it keeps the loading and parsing time of your site low, especially on mobile devices).

Super-special thanks to all our contributors. You’re the best! :)

Client-side MVC is not a silver bullet

February 26th, 2013

This is an edited repost of a comment of mine on Amy’s blog post about why we shut down Charm.

Charm, as it is, is using Backbone.js, Underscore.js and Zepto on the front-end, and Rails 2.3, Postgres, memcached, redis, resque, and for websockets Sinatra, and a few other things. The front-end is communicating with the back-end via a JSON API.

I’ve come to the realization that this much client-side processing and decoupling is detrimental to both the speed of development, and application performance (a ton of JavaScript has to be loaded and evaluated each time you fire up the app). It’s better to let the server handle HTML rendering and minimize the use of JavaScript on the client. You can still have fast and highly interactive applications, as the new Basecamp shows—letting the server handle most stuff doesn’t mean that you have to cut back on cool front-end features and user friendliness.

I argue that all these newfangled libraries are actually detrimental to the user experience in some ways, as they lock you into certain patterns (it’s hard do to things the authors didn’t anticipate) and if you use something like Ember (which we didn’t), it’s even worse as all applications using it practically look the same (many people choose using Twitter’s Bootstrap library, for example).

We’ve spend a lot of time getting Backbone to work properly, and the ease-of-use quickly deteriorates when your models get more complex. It’s a great choice for simple stuff, but email is far from simple. We also had to add yet an other extra layer of processing to generate “ViewModels” on the server because the normal Rails serialization of objects wouldn’t cut it.

What you end up with is building a layer cake that doesn’t add any value and slows down development. Especially when you’re starting out and need to stay flexible you don’t want to have too much code around—and Rails is great for that, but… adding a JSON API layer and basically a second application that runs on the client is annihilating this advantage for you.

All in all, my current recommendation for SaaS-type web apps is: Rails 2.3 (or Rails 3.2 if you prefer), a Postgres database, as much HTML generation on the server as possible and augment that with RJS (Rails’ mechanism to push JavaScript snippets to the client that get eval’d). This allows for direct re-use of server-side templates, and it’s simple, and works well. As an added bonus, keeping things on the server allow for much better error and performance monitoring and thus quicker turnaround for fixes. There’s also a lot of great stuff in this direction coming up in Rails 4 (like Turbolinks, a sort-of-successor to PJAX, which is a handy replacement for RJS if you don’t like it).

Alas, keep it simple and don’t repeat yourself.

Menubar productivity

February 23rd, 2013

OS X is awesome and that’s why we (neckbeard-less?) developers love it. Of course not everything is perfect, and one area of contention is the menu bar. There tends to be a never-ending supply of icons that fill it up and destroy its usefulness due to information overload.

There’s even tools that help you organize your menu bar, but I think that’s just fighting symptoms and not a permanent solution. Anyway, these tools are not for me, and I’ve decided to put my menu bar on a diet.

Here is what I currently use:

Screen Shot 2013-02-23 at 10.01.32 AM

Icons, from left to right, and why I use them:

  • Dropbox—so I see if stuff is synced. I use the black & white icon.
  • gfxCardStatus—so I see which graphics card my MacBook Pro uses, and to force it into using discrete graphics if browsers start to have graphical glitches, which is unfortunately quite often.
  • Hackpad—we do most internal brainstorming and copywriting on Hackpad. (Hey Hackpad, update your icon for my retina screen!)
  • Little Snitch—hovering over the icon shows Little Snitch’s nifty network monitor.
  • iStat Menus 4 CPU monitor—helpful during development and has shortcuts to launch Activity Monitor and other tools.
  • Time Machine—I like to see that it’s doing stuff when I have my backup drive connected at the office.
  • Keyboard & Character Viewer—I use OS X’s Character Viewer tool ⓐⓛⓛ ⓣⓗⓔ ⓣⓘⓜⓔ.
  • Bluetooth—useful at the office for my external keyboard, mouse and trackpad.
  • Wi-Fi—essential.
  • iStat Menus 4 battery—more info than OS X’s default icon.
  • Volume control—I use the keyboard to change the volume, but option-clicking the icon allows you to quickly set input and output devices.
  • iStat Menus 4 clock—I like the “fuzzy clock” and the dark grey calendar icon.

And that’s it. YMMV.

Running a SaaS? Here are some services you’ll find useful

February 16th, 2013

This December, our Time Tracking app Freckle will turn five. I’ve learned a lot about running a SaaS over these years, from making the right business decisions to choosing the technology to go with them.

The single most important thing you have to do as a business is make money. You need to pay your bills and put food on the table. At the same time you don’t want to compromise what you’ve set out for, in our case building the best time tracking tool there is and making it fun and awesome.

It follows that you need to have the most time available to actually talk to customers, refine the product and add awesome features—without losing the focus on what you’ve set out for.

In other words, you want to minimize time spend on things that other people probably know more about, including obvious things like taxes and accounting, but also keeping a SaaS up and running.

Here’s some tools we happily pay money for to keep some of the work of our backs:

  • Travis Pro for continuous integration. We used to run our own CI server, no more. One more thing we don’t have to keep running
  • Postmark sends our transactional email. No need for us to run our own mail server plus we know we can rely on deliverability. A must if your app sends mail.
  • Honeybadger for error monitoring & tracking
  • DocRaptor, a hosted version of PrinceXML, for converting HTML to PDFs. We literally implemented PDF downloads for invoices in one hour of coding with it (that includes writing tests and all).
  • keeps a tab on our logfiles, and provides instant search in case we encounter an issue. Much faster to quickly locate logs as you can view logs of the same time period across servers combined into one view.
  • Dome9 provides a SaaS firewall solution so we don’t have to mess with iptables or other weird things manually. They have an iPhone app to on-demand open up ports we need to administrate our servers.
  • Webmon and Pingdom allows us to monitor world-wide service availability and response time, as well as see if our DNS resolves globally. Pingdom also provides our status website without further configuration necessary (it took 5 minutes to set up).
  • Dead Man’s Snitch emails you when periodical tasks (cronjobs) aren’t running.
  • PagerDuty collects alerts from various services and gives us a central place from where to distribute alerts by text message and emails. This saves time by not having to configure all monitoring services separately.
  • Tinfoil and Trustwave do security scans of our infrastructure, and tell us when it’s time to install security updates.
  • KISSmetrics for metrics and event tracking and for sending out on-boarding emails, as well as emails about features.

If there’s someone that can do it for you (probably better than you can) for a price that makes sense, then you’d be stupid to build it yourself (and by the way, this list is not exhaustive, there’s even more services we use).

There’s a thriving ecosystem of apps and services that help you running your SaaS—make good use of it!

Why and how to not use hover styles on touch devices

January 26th, 2013

ipadButtons that show only on hovering over an area with the mouse are a great (if controversial) way to declutter user interfaces on traditional desktops where users have a mouse or trackpad. On mobile devices (phones and tablets), users use their finger instead, and there’s no more way to just hover over an element on a webpage—hovering and “clicking” are invoked by the same action: tapping.

Mobile browsers solve this issue by having the first tap invoking the hover style of an element and, if applicable, the second tap invoking any “click” events. Because of the need to discern swipes and taps, there’s a noticeable delay in browser response time. What this adds up to is that when you have both a :hover style and a onclick event on, say, a contained button in the :hover area, users end up spending the better part of a second trying to invoke the “click” on the button (300ms for the hover tap, 300ms for the click tap, and extra time for lifting the finger in-between).

The easiest way to deal with this is simple: don’t use :hover on touch-enabled devices.

Here’s one way I solved this in Freckle Time Tracking:

  1. I use Zepto’s detect module to see if I’m on a tablet or phone (you can use this module independently of Zepto, it doesn’t have dependencies on it).
  2. If it’s a tablet or phone, I add a “no-hover” CSS class to the BODY element
  3. I disable any :hover styles with selectors that use .... You actually don’t have to redefine the :hover rule, just make sure the normal rule and the :hover rule contain the same CSS property settings (like visibility:visible)

Now, my reason for not feature-testing (sue me!) for support of touch events and instead using browser sniffing is that 1) historically detection of touch events has been unreliable, 2) there are hybrid browsers and devices that support both touch and normal mouse events, and 3) it’s faster.

Update Jan 26, 7:50pm ET: Here are two more variants on this, the first one is from Thijs van der Vossen, and is a short JavaScript snippet that you can inline in your HEAD element. It adds multiple classes to HTML, depending on the environment it’s run in. The second variation is a CoffeeScript function to automatically remove :hover rules from Mislav Marohnić (assumes a modern, properly DOM-compatible browser).

The ultimate “target retina screens” media query

November 28th, 2012

There now is an abundance of devices with some sort of high-density display, from MacBook Pros to iPads, from Windows Surface tablets to all kinds of mobile phones.

All of these devices have one thing in common: In web browsers (that support the high-density screen correctly) one CSS pixel is not equal to a physical screen pixel.

In terms of CSS, to specifically target this group of devices, unfortunately there’s no easy way to say “apply this set of rules to all devices where physical pixels are not equal to CSS pixels”. Instead you have to fight through a whole forest of media query rules.

Here’s the set that I use on my sites:

@media (min--moz-device-pixel-ratio: 1.5),
       (-o-min-device-pixel-ratio: 3/2),
       (-webkit-min-device-pixel-ratio: 1.5),
       (min-device-pixel-ratio: 1.5),
       (min-resolution: 144dpi),
       (min-resolution: 1.5dppx) {

/* Retina rules! */


This is tested on all browsers I could get ahold of, on real Retina and non-retina displays, and should be future-proof as well. We use this specific query in production on Freckle Time Tracking (Sorry, marketing site is not retinafied yet!)—and it works well!

Specifically, it supports Safari, Chrome, Firefox (Note: Firefox doesn’t really support Retina screens at all yet) and Internet Explorer 9 and 10 (IE has great Retina support, actually!).*

I’d love to hear corrections and suggestions about this, please use the gist.

*Before you ask, I suppose it supports Opera as well, but I don’t test on Opera. It’s a long story.

Want to make your websites all ready for the smorgasbord of screen resolutions and densities? Fear not—my latest ebook Retinafy your web sites & apps now will guide you through the jungle! Learn how to deal with all this in 30 minutes reading, and have your site all shiny by tomorrow!