Deploy Ghost using Dokku
Tags: ghost, dokku, tutorial
Published: 2022-06-03 09:53:10

I started using [Ghost](https://ghost.org) as a headless cms for my [personal website](https://bitkidd.dev) and it works like a charm, but I had to spend some time to try and deploy it using [Dokku](https://dokku.com), that's what I am going to write about.

Dokku, oh, it is my favorite self-hosted deployment software for personal and sometimes commercial needs. It has its flaws but overall it works in most situations and allows me to save some money, so I use it for my pet-projects and for my website too.

Before we start, I assume you've already installed [Dokku](https://dokku.com) on your server, configured all the things properly, installed [dokku-mysql](https://github.com/dokku/dokku-mysql), created a new database (ex: **ghost-db**), created a new app for Ghost, let's call it simply **ghost** and linked them.

As of **v0.24.0** Dokku allows to deploy Docker images using a straightforward command, before this it was a nightmare with tagging.

    dokku git:from-image node-js-app dokku/node-js-getting-started:latest

So, **dokku git:from-image** is exactly what we need.

### Step 1\. Deploy Ghost image

We are going to use Docker Ghost image that can be found [here](https://hub.docker.com/_/ghost/). You can use any of the tags, but it is fine to use **:latest** for initial deployment.

    dokku git:from-image ghost ghost:latest

This will build your app using the image you provided and then deploy it using your Dokku settings. By the end of the process you will have a working Ghost instance without any persistance and wrong public ports.

### Step 2\. Dealing with ports

Here we are going to make Ghost app public by adding some new ports and removing those that we don't need.

    dokku proxy:ports-add ghost http:80:2368
    dokku proxy:ports-remove ghost http:2368:2368

By the end of this step your Ghost app should now be accessible via a domain you provided initially to Dokku or via port mapping.

### Step 3\. Persist it

Docker images do not keep any data between restarts, that's why we should provide some persistant volumes to it. Dokku allows us to do this easily via **storage:mount** command.

    dokku storage:ensure-directory ghost
    dokku storage:mount /var/lib/dokku/data/storage/ghost:/var/lib/ghost/content
    dokku ps:rebuild ghost

In this step we create a new folder **ghost** in a special place where Dokku docs suggests us to keep persisted data, then we use our new folder **/var/lib/dokku/data/storage/ghost** to keep Ghost data from docker image folder **/var/lib/ghost/content**. This way everything that Ghost creates and keeps in this **content** folder will be persisted between reloads.

### Step 4\. Database

Ghost can work even without a separate database, using a SQLite and keeping it on the disk, I don't really like it but if you are okay with this, _then skip this step_. Before we even started, you already installed dokku-mysql and created a database for Ghost, we will need it here.

    dokku config:set \
    	database__client=mysql \
        database__connection__database=<YOUR_DATABASE_NAME> \
        database__connection__host=<YOUR_DATABASE_HOST> \
        database__connection__password=<YOUR_DATABASE_PASSWORD> \
        database__connection__port=<YOUR_DATABASE_PORT> \
        database__connection__user=mysql

In this step we provide some essential database configuration params to the Ghost app, as you set them, Dokku will restart it and it should then work using mysql database.

### Step 5\. Domain

One of the main things we should do, is to add a domain to our app, Dokku has some useful commands for this.

    dokku domains:add ghost my.ghost.website
    dokku config:set ghost url=http://my.ghost.website

### Step 6\. SSL certificate

You need SSL certificate for your website. With Dokku you can add it in several ways, using official [Let's Encypt](https://github.com/dokku/dokku-letsencrypt) plugin, or using your own certificate, or using a [Cloudflare SSL](https://bitkidd.dev/posts/use-cloudflare-ssl-certificates-with-dokku). Any of these do, but don't neglect this step.

Just don't forget to change your website url in configs.

    dokku config:set ghost url=https://my.ghost.website

That's it, by now you have a working website powered by Ghost and deployed using Dokku on your own server for little to no money 🪄🦄✨.