Code for this chapter available in the master
branch of the JS-Stack-Boilerplate repository.
In this chapter, I integrate our app with third-party services. These services offer free and paid plans. It is a bit controversial to use such services in a tutorial that relies exclusively on community-driven and free open source tools, which is why I maintain 2 different branches of the JS-Stack-Boilerplate repository, master
and master-no-services
.
💡 Travis CI is a popular continuous integration platform, free for open source projects.
If your project is hosted publicly on Github, integrating Travis is very simple. First, authenticate with your Github account on Travis, and add your repository.
- Then, create a
.travis.yml
file containing:
language: node_js
node_js: node
script: yarn test && yarn prod:build
Travis will detect automatically that you use Yarn because you have a yarn.lock
file. Every time you push code to your Github repository, it will run yarn test && yarn prod:build
. If nothing goes wrong, you should get a green build.
💡 Coveralls is a service that gives you a history and statistics of your test coverage.
If your project is open-source on Github and compatible with Coveralls' supported Continuous Integration services, the only thing you need to do is to pipe the coverage file generated by Jest to the coveralls
binary.
-
Run
yarn add --dev coveralls
-
Edit your
.travis.yml
'sscript
instruction like so:
script: yarn test && yarn prod:build && cat ./coverage/lcov.info | ./node_modules/coveralls/bin/coveralls.js
Now, every time Travis will build, it will automatically submit your Jest test coverage data to Coveralls.
Is everything green on Travis and Coveralls? Great, show it off to the world with shiny badges!
You can use the code provided by Travis or Coveralls directly, or use shields.io to homogenize or customize your badges. Let's use shields.io here.
- Create or edit your
README.md
like so:
[![Build Status](https://img.shields.io/travis/GITHUB-USERNAME/GITHUB-REPO.svg?style=flat-square)](https://travis-ci.org/GITHUB-USERNAME/GITHUB-REPO)
[![Coverage Status](https://img.shields.io/coveralls/GITHUB-USERNAME/GITHUB-REPO.svg?style=flat-square)](https://coveralls.io/github/GITHUB-USERNAME/GITHUB-REPO?branch=master)
Of course, replace GITHUB-USERNAME/GITHUB-REPO
by your actual Github username and repository name.
💡 Heroku is a PaaS to deploy to. It takes care of infrastructure details, so you can focus on developing your app without worrying about what happens behind the scenes.
This tutorial is not sponsored in any way by Heroku, but Heroku being one hell of a platform, I am going to show you how to deploy your app to it. Yep, that's the kind of free love you get when you build a great product.
Note: I might add an AWS section in this chapter later, but one thing at a time.
-
If that's not the done yet, install the Heroku CLI and log in.
-
Go to your Heroku Dashboard and create 2 apps, one called
your-project
and one calledyour-project-staging
for instance.
We are going to let Heroku take care of transpiling our ES6/Flow code with Babel, and generate client bundles with Webpack. But since these are devDependencies
, Yarn won't install them in a production environment like Heroku. Let's change this behavior with the NPM_CONFIG_PRODUCTION
env variable.
-
In both apps, under Settings > Config Variables, add
NPM_CONFIG_PRODUCTION
set tofalse
. -
Create a Pipeline, and grant Heroku access to your Github.
-
Add both apps to the pipeline, make the staging one auto-deploy on changes in
master
, and enable Review Apps.
Alright, let's prepare our project for a deployment to Heroku.
- Create a
.env
file containing:
NODE_ENV='production'
PORT='8000'
That's in this file that you should put your local-only variables and secret variables. Don't commit it to a public repository if your project is private.
-
Add
/.env
to your.gitignore
-
Create a
Procfile
file containing:
web: node lib/server
That's where we specify the entry point of our server.
We are not going to use PM2 anymore, we'll use heroku local
instead to run in production mode locally.
-
Run
yarn remove pm2
-
Edit your
prod:start
script inpackage.json
:
"prod:start": "heroku local",
- Remove
prod:stop
frompackage.json
. We don't need it anymore sinceheroku local
is a hanging process that we can kill with Ctrl+C, unlikepm2 start
.
🏁 Run yarn prod:build
and yarn prod:start
. It should start your server and show you the logs.
- Add the following line to your
scripts
inpackage.json
:
"heroku-postbuild": "yarn prod:build",
heroku-postbuild
is a task that will be run every time you deploy an app to Heroku.
You will also probably want to specify a specific version of Node or Yarn for Heroku to use.
- Add this to your
package.json
:
"engines": {
"node": "7.x",
"yarn": "0.20.3"
},
- Create an
app.json
file containing:
{
"env": {
"NPM_CONFIG_PRODUCTION": "false"
}
}
This is for your Review Apps to use.
You should now be all set to use Heroku Pipeline deployments.
🏁 Create a new git branch, make changes and open a Github Pull Request to instantiate a Review App. Check your changes on the Review App URL, and if everything looks good, merge your Pull Request with master
on Github. A few minutes later, your staging app should have been automatically deployed. Check your changes on the staging app URL, and if everything still looks good, promote staging to production.
You are done! Congratulations if you finished this entire tutorial starting from scratch.
You deserve this emoji medal: 🏅
Back to the previous section or the table of contents.