You've built your web app, and now you're ready to unleash it upon the world and scale into the stratosphere!
The most recent version of this tutorial is now available on YouTube.
It's this final hurdle of deployment that can leave a lot of developers reaching for the aspirin.
Should I use AWS or Digital Ocean?
What the heck is Docker?
Won't my pipeline freeze in winter?
With so many options available, deploying a web app can often feel like you need a PhD in dev-ops to get your app into the hands of your customers.
If you're anything like me, I've never used Docker, and I don't want to spend weeks climbing an elastic beanstalk. I want to focus on writing code without worrying about the underlying architecture.
What We're Going to Cover
- Creating a Heroku account
- Creating a development pipeline
- Installing the Heroku CLI
- Configuring your Heroku app (database, SSL, domain, env vars)
- Setting up your Node.js app for Heroku
- Deploying your application
If you're new to this, it should take you around 30 minutes to follow this tutorial and get your app up and running. Don't worry – it's pretty easy!
Why Heroku?
Now, before I brainwash you with the awesomeness of Heroku - I appreciate that it's not for everyone. If you're confident managing AWS in production, then you should do that.
However, if you're like me and you want to click a few buttons on a UI and have your app deployed in a few minutes, Heroku will eliminate most of the pain associated with deployment.
You may end up paying a little more than you would if you used a self-managed solution, but in my opinion, a few extra dollars is well spent if it saves time and headache and enables me to focus on more important tasks like delivering customer value.
Heroku also have an excellent support team that can help you if something goes wrong - so you're not on your own.
How Much Does Heroku Cost?
You can run a production app on Heroku for as little as $7/mo on the hobby plan. There is also a free tier, but this should only be used for experimentation as it has limitations that you don't want in production.
If you're starting out $7/mo will be fine, then you can move onto the $25/mo tier and beyond when you need more juice.
Again, this may be slightly more expensive than other options, but there is a considerable amount of convenience offered with Heroku with a very small learning curve.
OK, let's jump into the tutorial.
1. Create a Heroku Account
Head on over to Heroku and create an account.
That's it; your app is deployed!
I jest! :)
2. Create a Pipeline
On your Heroku dashboard you will see a button called New which reveals two options:
- Create a new app
- Create a new pipeline
You can create a single app and push your local build to it, but this would be extremely dangerous, and we're all professionals here, so what we're going to do is set up two apps within a pipeline:
- Staging app
- Production app
So the flow is:
Develop your app locally -> push to staging for testing -> push to production -> get rich.
The pipeline will enable you to push new features to a staging environment where testers can test everything is working before you push it out to every customer.
Go ahead and give your pipeline a name.
You can also connect your Github repo here - which we'll use for deploying later on.
Hit Create Pipeline and Heroku will set up a pipeline with placeholders for your staging and production apps for you.
Click Add App then Create New App to add a new app to each stage of your pipeline.
When creating an app, you need to give it a unique name and select the location closest to your customers (the USA or Europe).
3. Install the Heroku CLI
Before we proceed, it's a good idea to install the Heroku CLI - this will enable you to manage your Heroku apps locally from a terminal. There are a few ways to install this, so please refer to the docs.
4. Configure Your Heroku Apps
Now, you need to configure both of the applications that you just have created. If you click on the application name, you'll see the dashboard for that application.
On this screen, you can do a lot of stuff very easily and quickly.
Choose a Dyno
The first thing you'll need to do is to select a dyno formation by clicking on Configure Dynos and then Change Dyno type. The dyno type will set the pricing tier for the application.
As I mentioned previously, you'll want to at least use the $7/mo dyno for your production app. For staging, you can get away with the free tier, but your app will be slow and won't have SSL.
Install Add-ons
You can install lots of third-party features to your application via your dashboard, but to get started you need just two:
- ClearDB MySQL (or your chosen database service)
- Autobus (free daily database backups for when you screw things up)
With ClearDB you get 5mb of free space (which is quite a bit depending on what you're doing) and then you can scale up as your needs develop, starting from $10/mo.
Of course, you don't need to use ClearDB, you could use another service like Amazon RDS, but I like to keep things simple and in one place.
Once you've installed a database, you can get the URL and credentials using the Heroku CLI tool that you just installed by running the following in terminal:
heroku config | grep CLEARDB_DATABASE_URL
Deployment Settings
Next, tap the Deploy tab, and you should see your connected Github account. Select the branch (or create a new one) that you want to use for deploying to Heroku and click Enable automatic deploys.
Configure env Vars
If you're not familiar with ENV vars - these are simple variables that are specific to the server environment.
Your Node.js application will be loading different configuration settings based on these variables.
For example, in your staging environment, you will want to load your Stripe test keys for testing, and then in the production environment, load the live keys to accept real payments.
The same principle applies to your database - one for testing and one for production, this ensures that you don't accidentally mess up your customer's data while you're developing new features.
The Gravity SaaS boilerplate will handle this for you if you don't fancy the headache.
Next, tap on the Settings tab and navigate to the second section called Config Vars and click Reveal Config Vars.
You'll see the URL for the database that you just have created here, and you'll want to create a NODE_ENV var and set it to development on your staging app, and a var with the same name set to production on your production app.
Add any other variables here that your application uses - API keys, secrets etc.
Create an SSL Certificate & Set the Domain
The next section will enable you to create an SSL certificate (paid dynos only) - you'll need this in production.
Setting this up takes about two seconds. Can you now see why Heroku is such a great choice? Everything is so easy!
Finally, add your domain in the next section, and Heroku will give you a DNS target.
You'll need to create a new ANAME record in your domain control panel and point it to this target. If your domain provider doesn't support ANAME records, you can use a DNS service like Cloudflare or one of the free alternatives.
You need to complete all of these steps for both your staging and production applications.
5. Configure Your Node & React App for Deployment
For simplicity and to keep costs down, let's assume that you're going to deploy each artefact - your server, API and client to one Heroku app.
For smaller applications – and if this is your first deployment - this is fine. As your application scales, you'll want to deploy these artefacts separately - the process is the same as the one outlined in this article, except you need to create more Heroku apps for each artefact.
Your application structure is likely to look something like this:
Confused? Watch my video on web app architecture.
Add the Heroku Post-build Command
Add the following line to the scripts section of your package.json. This command is run after your application is deployed and instructs Heroku to build the React client to serve the static files for you.
"heroku-postbuild": "cd client && npm install && npm run build"
Add the React Routes
Inside the server.js file, you'll need to add the routes for serving the static build, like this:
app.use(express.static(path.join(__dirname, 'client/build')));
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname + '/client/build/index.html'))
});
6. Deploy Your Application
Finally, the fun part, time to deploy your app!
You simply commit your application and push it to the relevant branch connected to your Heroku staging server.
That's it! Heroku will detect that you're using Node.js, install the relevant build back and build your application.
You can watch the build log in the Heroku dashboard of your app, or in terminal b running:
heroku logs --tail
You'll be notified once your app has been successfully deployed - or if there are any errors that you need to fix.
You can also set Heroku as a Git remote, and deploy that way instead of connecting your Github account.
7. Push to Production
Once you have tested your application on your staging server, you can click the 'Promote to Production' button on your pipeline dashboard to push your application into the hands of your customers.
That's an App, Folks
There you have it – your application deployed and running in less than 30 minutes and not an aspirin bottle in sight.
Need help with something? Get in touch.