Monday, 5 August 2019
I thought that I would share my experience in pushing up a Node.js application to a Digital Ocean droplet via the amazing Dokku PaaS.
Dokku is like an ideal mashup of the powers of Docker and the ease of use the of Heroku's Git deployment workflow that everyone knows and loves.
First off, you're going to want to sign up to Digital Ocean if you haven't already. Once that's all done and dusted, create a new droplet choosing the Dokku image from their marketplace of prebuilt images:
I would choose the lowest specs although this varies dependent on your use case. I went for the $5 a month option.
Dokku has a web setup UI that can be accessed by visiting your Droplet IP address in a web browser (e.g. entering
http://0.0.0.0 into the address bar). In the setup process for the droplet you will need to setup these options:
1.) Virtual hosts enabled, meaning that you can push multiple apps to a different subdomain on your dokku droplet.
2.) SSH key configuration, you will need to copy your SSH key from your local dev rig to the clipboard using
pbcopy < ~/.ssh/id_rsa.pub
Once the droplet has been created and has finished provisioning, you can login to the droplet via SSH (
0.0.0.0 is just a placeholder, substitute with the droplet's IP address as it is shown on the Droplet's dashboard page on Digital Ocean):
Once you are in the console, you need to create the Dokku app on your droplet which is going to manage deployments for your local git repo on the server. You can name the app anything you want (I chose
myapp below) - just keep a note of it as you will use this in later steps:
Last login: Tue Apr 2 14:48:10 2019 from 184.108.40.206 root@ajbcouk:~# dokku apps:create myapp -----> Creating myapp... done
Back in your local command line environment, you now need to navigate to the git repository of the app you want to deploy and add the Dokku droplet as a git remote so you can push to it:
git remote add dokku firstname.lastname@example.org:myapp
Be sure to replace
0.0.0.0 with your Droplet's IP address and
myapp with the app name you choose when running
dokku apps:create myapp above.
Once this is done, you should see the Dokku remote in your list of git remotes:
➜ ajb-next git:(master) git remote -v dokku email@example.com:myapp (fetch) dokku firstname.lastname@example.org:myapp (push)
Once this step has been completed, you need to decide on whether to go down the
Dockerfile route or whether to rely on Dokku's Heroku interoperability to make use of standard Heroku buildpacks like Heroku Node and Heroku Rails.
If you don't specify a
Dockerfile then Dokku will attempt to build your app with a buildpack it judges your application to need. I have chosen the
Dockerfile approach. My app is a simple Node.js app so it's not too complex:
FROM node:8 ENV appdir /src WORKDIR $appdir COPY package.json yarn.lock ./ RUN yarn --pure-lockfile COPY . . EXPOSE 80 CMD ["yarn", "start"]
If you haven't yet committed anything, then just run
git add . or similar and commit the changes using
git commit -m "My message" and then push to the Dokku git remote as below:
➜ ajb-next git:(master) git push dokku master perl: warning: Setting locale failed. perl: warning: Please check that your locale settings: LANGUAGE = (unset), LC_ALL = (unset), LC_CTYPE = "en_GB.UTF-8", LANG = "C.UTF-8" are supported and installed on your system. perl: warning: Falling back to a fallback locale ("C.UTF-8"). Enumerating objects: 5, done. Counting objects: 100% (5/5), done. Delta compression using up to 4 threads Compressing objects: 100% (3/3), done. Writing objects: 100% (3/3), 342 bytes | 342.00 KiB/s, done. Total 3 (delta 2), reused 0 (delta 0) -----> Cleaning up... -----> etc
Dokku will attempt to deploy your application either via the
Dockerfile you have specified or the automatic buildpack detection process.
I use Cloudflare as a DNS provider, so getting my new Digital Ocean droplet to exist on a subdomain was as easy as adding an
A record for the subdomain of my choosing to point to the Droplet IP.
You can always check which ports are exposed publicly and which Docker containers they relate to by running:
dokku proxy:ports myapp # Output -----> Port mappings for myapp -----> scheme host port container port http 80 5000