There’s a lot to love about Heroku. Servers spin up instantly. Code deployments are quick. You can rollback to any old version of your application in just one click.
And much, much more.
But there’s a lot I don’t like about Heroku for Node.js web applications
By default it runs npm install to install dependencies as part of every deploy. Although it has some magic to cache those dependencies and the NPM registry is a lot more reliable than it used it be this still introduces some risk that if npm install can’t run, you won’t be able to deploy your app.
Running your build process on Heroku turns out to be quite difficult. Often build processes rely on a lot of tools — SASS, for example, relies on Ruby. If you run your build process on Heroku you’ll end up installing a lot of tools onto your web server that will only ever get used once, when the site is deployed. This slows down your deploy and makes it more fragile.
Heroku actually supports two mechanisms for deploying code. You can either use Heroku toolbelt and (typically) typing
git push heroku or they now also have a new API that can be used for deployments.
Unfortunately that new API is very sensitive to the format of the applications you give it to run. Because of this I’ve written a small wrapper around that API that can be dropped into any Node.js project which means that the code that is deployed onto Heroku no longer needs to be the same code that is checked into git. I’ve called it Haikro.
./node_modules/.bin/haikro build deploy \
I’ve tried my best not to reinvent too much and so pretty much everything about how you write Node.js apps for deploying via git push heroku should work for Haikro too, for example:-
To specify a particular version of Node.js add an ‘engines.node’ property to your package.json file with the semver of your desired Node.js version:-
Also Procfiles for web nodes will continue to work (but not yet for worker nodes):-
web: node server/app.js
This means you can pre-download your dependencies and run your build steps locally or as part of your Continuous Integration process (I’ve tested Codeship, Travis and CircleCI) and then all Heroku needs to do is run your application.