Setting up Ghost on a Debian VPS with Apache2 step by step

I like recursivity. I learnt to install Ghost just to be able to write about how to install Ghost. So, let’s get on with it. As stated in the official installation guide, Ghost requires the latest stable version of Node.js. At this moment, Ghost recommends to install Node.js 0.10.x and npm 1.4.21. One important thing you need to know is that only even versions of Node.js are stable. For those of you who haven’t used Node.js before, it’s a server-side runtime environment, and npm its package manager. To make an analogy, Node.js is like PHP and npm is like PEAR, but in javascript!

Before anything else: bash, g++, curl, libssl-dev, apache2-utils and git

Before we can start, it would be nice to make sure we have the necessary dependencies set up.

A good start is to make sure you are using bash as shell. Using /bin/sh brought me some unexpected problems.

echo $SHELL

should return the bash shell


If it’s not, you can change shell to bash using:

chsh -s /bin/bash


echo $SHELL

to double check.

The necessary dependencies are a c++ compiler, we will use g++, curl to handle downloads, libssl-dev for SSL, apache2-utils and git, for source code management.

You can install them all with:

sudo apt-get install g++ curl libssl-dev apache2-utils git-core

Installing NVM

There are several ways to install Node.js, but if you want to get rid of any problems and be able to use Ghost asap (I wasn’t that smart!), use NVM (Node Version Manager). NVM lets you to easily manage all your node installations and change node versions. This is a good read in case you are not convinced.

To install NVM use:

curl | bash

Check that everything went alright with:

nvm -v

The script simply clones the repository into ~/.nvm and adds the source line to your profile ~/.bash_profile.

Installing Node.js

Node.js Logo

We will follow recommendation and install Node.js 0.10.30 with:

nvm install 0.10.30

Check it was successfully installed with:

nvm list

To set a default Node version to be used in any new shell, use the alias 'default':

nvm alias default v0.10.30

Check the changes:

nvm list

node –v

should now return v0.10.30.

Installing npm

npm is the node package manager and to install it we need to execute:

curl | bash

Check npm is installed with:

npm -v

Installing Ghost

The Ghost Logo

Yay! We finally got there. From your user home, download the latest Ghost release with:

curl -L -o

Extract the archive into a ghost folder with:

unzip -uo -d ghost

Now enter that folder with:

cd ghost

and install Ghost using:

npm install --production

You can now start Ghost in development mode:

npm start

Ghost will be running on However, we still need to configure Apache2 to be able to access it from the browser.

Running Ghost forever in production

The previously used method to start Ghost will immediately shut it off after closing the SSH session. It is useful for development but that’s not what we want when we need the blog to be up 24/7/365. Thus, we need to run Ghost as a service. The official deployment guide presents several packages to do this. We will use the simplest: Forever. With Forever we can run Ghost as a background task and it takes care of restarting the node process if it crashes. However, it is important to keep in mind that Forever must be executed again manually after a server reboot.

To install Forever simply:

npm install forever –g

You can now start Ghost in production environment from the ghost home folder using:

NODE_ENV=production forever start index.js

You can check the currently running tasks in Forever with:

forever list

To stop Ghost just:

forever stop index.js

Configuring Apache

At this point, all we need is to make our Ghost blog accessible on port 80 instead of the default 2368. The guys at All About Ghost say we can accomplish this by using Apache to proxy all the requests for port 80 to 2368.

To begin with, install Apache2 if you don’t have it yet:

apt-get install -y apache2

Create a config file for your new blog with:

nano /etc/apache2/sites-enabled/blog.conf

and paste the following config, adapting it to your own ServerName and ServerAlias. You can find the config for this blog here:

NameVirtualHost *:80
<VirtualHost *:80> ServerName ServerAlias ProxyRequests off ProxyPass / ProxyPassReverse / http:/ </VirtualHost>

Now, enable the proxy modules for apache:

sudo a2enmod proxy proxy_http

and finally restart Apache to apply the changes:

sudo service apache2 restart

You should now be able to access your ghost blog via your domain name, on port 80, through Apache to port 2368. On /ghost you should be able to access the control panel.

Before proceeding, and in case you had other websites running on Apache2 before, make sure that these are working. In my case they stopped working and had to change the configured VirtualHosts from

<VirtualHost *>


<VirtualHost *:80>

Configuring Ghost

The official guide tells us that after running Ghost for first time a config.js will be created. If you don’t want to run Ghost yet, then copy config.example.js into config.js to apply your changes. There are several configuration options that I won’t cover in this post, but basically, to get started you only need to set the public url for your blog, so that all the auto-generated paths work properly.

From the Ghost folder you can do so with:

nano config.js

and edit the production url field like I did for this blog:

url: ''

Ghost strongly recommends that you configure the mail settings too, so that if you forget your password you can recover it. For once, I ignored Ghost’s recommendation. If I forget my password that will mean I have bigger concerns :P You can read about how to do it with Mailgun here.

Installing a theme

By default, Ghost comes with the Casper theme. It is already very nice looking, like everything in Ghost I guess! However, one might want to change the theme. To do so is very easy.

First, choose your desired theme from the Ghost Marketplace. I know I know, it’s very hard to decide! For this guide we will use Seth Lilly’s Vapor theme. It’s free!!

If you are interested, I did my own variation of the Vapor theme which is mostly an adaptation of Elena Kolevska’s variation. It includes some nice features like prism.js for code syntax highlighting and disqus for easing the comments management. It is the theme being used in this very blog!

Let’s stick with the original for now.

First get to the themes folder with:

cd /var/www/ghost/content/themes

Now, clone the theme repository using:

git clone

Time to restart Ghost! If you used the Forever tool, just go with:

forever stop index.js
NODE_ENV=production forever start index.js

From the browser, access the control panel, http://yourdomain/ghost, go to the ‘Settings’ tab and select the new theme from the dropdown menu. You should now see the new theme applied to the blog!!

Few words about the workflow

It is quite possible that you will make your own modifications to any theme you feel like using. You can now edit your theme from local, push it to the repository and apply the changes to the live blog by simply pulling the changes from the repository while on the theme folder with:

git pull

Final words

You made it this far? Great job! High five! I hope this guide helped you to easily install ghost. I have tried to link to all the resources I used myself. If you have any issues or need alternatives you will probably find anything you need in either the official guide for self-hosted ghost or the epic amount of resources for dev’s that Andy Boutte and David Balderston have put together under All About Ghost.

Good blogging!

comments powered by Disqus