Setup Ghost with Nginx Proxy Manager
I've been on a quest to rebuild a blog/documentation website for a few months. I've settled on Ghost for the time being, but have played around with a few other SSGs like Hugo and Gatsby.
This article will walk you through the process of setting up Ghost behind Nginx Proxy Manager. This article also assumes the following
- You're spinning this up on a headless linux server (i.e. not Docker)
- You are using Nginx as the webserver for Ghost
- The server is fresh and hasn't been configured for another CMS or web framework.
- You have Nginx Proxy Manager up and running with certs ready to go.
Step 1
Create a new user
If you haven't create a new user yet for the server then do so now.
ssh username@server_ip
adduser <username>
Do not user Ghost as the username. This can cause issues with the CLI I believe.
Now we need to add this user to supergroup so that we can utilize some admin functionality on the server.
usermod -AD sudo <username from above>
Feel free to exit out of this shell and ssh in using the new user you created, or just run:
su - <username>
Step 2
Update and configure the OS
Whenever you spin up a new server it's important to update it fully. To achieve this run:
sudo apt update && apt upgrade -y
Install Nginx
Nginx will be the software we use as our web server. It can also be used as a reverse proxy, load balance , and more!
sudo apt install nginx
Install and configure MySQL
We need a database to store site information. For this tutorial we will use MySQL.
sudo apt install mysql-server
By default there is no password for the root account. We should fix this, and also add a user and database specific to our Ghost site. Run the following commands to get everything setup.
Login as database user root.
sudo mysql
Create a password for the root account.
ALTER USER 'root'@'localhost' IDENTIFIED WITH mysql_native_password BY '<enter_new_password_here';
Exit mysql and then log back in using the newly created password.
EXIT;
mysql -u root -p
Create a database and give it a name.
CREATE DATABASE <database_name_here> DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;
Create a user.
CREATE USER '<username_here>'@'%' IDENTIFIED WITH mysql_native_password BY 'password_for_user_here';
Flush the privileges and exit.
FLUSH PRIVILEGES;
EXIT;
Install Node.js and NPM
NPM in this context refers to the Javascript package manager and NOT Nginx Proxy Manager.
Add APT repo.
curl -sL https://deb.nodesource.com/setup_18.x | sudo -E bash
Install NodeJS
sudo apt install -y nodejs
Install NPM if it wasn't installed with nodejs
Check if NPM is installed.
npm -version
If it returns a version it's installed. If it doesn't then run:
apt install -y npm
Install Ghost CLI
Installing the Ghost CLI uses NPM.
sudo npm install ghost-cli@latest -g
Step 3
Setup Ghost
First thing we need to do is setup the folder that will house all of our website files. Create a folder and give it a name. I named mine kirkenjerk.io, but you can call yours whatever you like.
sudo mkdir -p /var/www/html/<sitename>
Lets set the owner and change the permissions on the folder to what Ghost expects. Change the username to the one we created in Step 1.
sudo chown <username>:<username> /var/www/html/<sitename>
sudo chmod 775 /var/www/html/<sitename>
Change the current directory to the newly created folder.
/var/www/html/<sitename>
Install Ghost
If everything has been done correctly up to this point then all we need to do is run"
ghost install
During the install you will be asked a series of questions. I've copied them from Ghosts documentation, and put them below.
Blog URL - Provide the url your site will be available at
Enter the exact URL your publication will be available at and include the protocol for HTTP or HTTPS. For example, https://example.com
. If you use HTTPS, Ghost-CLI will offer to set up SSL for you. Using IP addresses will cause errors.
MySQL Hostname - Provide this from Step 2
This determines where your MySQL database can be accessed from. When MySQL is installed on the same server, use localhost
(press Enter to use the default value). If MySQL is installed on another server, enter the name manually.
MySQL Username/Password - Provide this from Step 2
Enter in the username and password we created in Step 2. Otherwise, enter root
. Then supply the password for your user.
Ghost database name - Provide this from Step 2
Enter the name of your database created in Step 2. It will be automatically set up for you, unless you’re using a non-root MySQL user/pass. In that case the database must already exist and have the correct permissions.
Set up a ghost MySQL user? (Recommended) - Enter No
If you provided your root MySQL user, Ghost-CLI can create a custom MySQL user that can only access/edit your new Ghost database and nothing else.
Set up NGINX? (Recommended) - Enter Yes
Sets NGINX up automatically enabling your site to be viewed by the outside world. We will need to tweak the configuration afterwards.
Set up SSL? (Recommended) - Enter No
We will be using Nginx Proxy Manager to provide SSL for our site, we can enter no for this now
Set up systemd? (Recommended) - Enter Yes
systemd
is the recommended process manager tool to keep Ghost running smoothly. We recommend choosingyes
but it’s possible to set up your own process management.
Start Ghost? - Enter Yes
Choosing yes
runs Ghost, and makes your site work.
Step 4
Tweak Nginx Configs
The default configuration from Ghost works, but also causes some issues if we run the site behind Nginx Proxy Manager. To fix the issue we need to edit the Nginx config for the site. This is located at /etc/nginx/sites-available/sitename.conf.
Using your favorite editor open up the config. Change the following line from:
proxy_set_header X-Forwarded-Proto $scheme;
To:
proxy_set_header X-Forwarded-Proto https;
As the Ghost documentation explains:
Your proxy will handle SSL termination and proxy to Ghost using http. To tell Ghost that the requests coming into the proxy are secure, set thex-forwarded-proto
header tohttps
. Without this, Ghost will think the requests are insecure, attempt to redirect to the https version of a URL and cause an infinite redirect loop.
Create the config in Nginx Proxy Manager
With the server up and running, we can now create the proxy config in Nginx Proxy Manager.
Create the entry, and set the domain to the site URL you entered in during the ghost install command. Then set the protocol to HTTP and the forward hostname/ip to the IP of your server. The forward port should be port 80.
I enable Cache Assets, Block Common Exploits, and Websockets support as well. Under the SSL tab select the SSL cert you want to use (I created one specifically for this domain instead of using my wildcard cert). Enable Force SSL and click save.
That should be it. Type your domain into your address bar followed by /ghost, and if everything was done correctly, you should be prompted to create an account. From there you can log in and begin setting up your site.