This tutorial provides a practical guide for Docker WordPress production deployment. You will learn how to deploy automatically WordPress on line using docker compose.
The installation tool kit include:
- Nginx server, reverse-proxy and letsencrypt for HTTPS certificates
- WordPress files
- MariaDB/MySQL used for WordPress database
- phpMyAdmin interface to connect to your MySQL database
- WP-Cli: WordPress Command Line Interface
- Makefile directives for automatization.
Contents:
- Prerequisites
- Step 1. Create websites directories
- Step 2. Download a nginx-proxy web server template for hosting multiple websites on the same server
- Step 3. Download a WordPress docker-compose template
- Step 4. Inspect your web directory
- Step 5. Edit the WordPress Docker setup environment variables
- Step 6. Edit the docker-compose configuration file
- Step 7. Run the nginx reverse proxy
- Step 8. Allow users to post large documents or images
- Step 9. Install WordPress using docker compose
- Step 10. Access to your website
- Shutdown and cleanup
- Summary
Prerequisites
- Read this: WordPress Local Development Using Docker Compose
- Read also this: How to Host Multiple HTTPS Websites on One Server
- Git, docker and docker-compose are installed on your server
- Your host must be publicly reachable on both port
80
and443
. Check your firewall rules to make sure that these ports are open. - Create a website directory and set up proper permissions. In this tutorial, we’ll assume that the web directory is at
/srv/www
- Create domains and subdomains:
- One for your WordPress website:
www.example.com
- One to access your word press database via phpMyadmin:
sql.eample.com
- One for your WordPress website:
Step 1. Create websites directories
Read more: Create a website directory and set up proper permissions
# 0. settings
web_dir=/srv/www
myusername=kassambara
# 1. Create the website directory
sudo mkdir -p $web_dir
# 2. set your user as the owner
sudo chown -R $myusername $web_dir
# 3. set the web server as the group owner
sudo chgrp -R www-data $web_dir
# 4. 755 permissions for everything
sudo chmod -R 755 $web_dir
# 5. New files and folders inherit
# group ownership from the parent folder
chmod g+s $web_dir
Step 2. Download a nginx-proxy web server template for hosting multiple websites on the same server
# Download a nginx-proxy template
web_dir=/srv/www
git clone https://github.com/kassambara/nginx-multiple-https-websites-on-one-server $web_dir
# Update nginx.tmpl: Nginx configuration file template
rm -rf $web_dir/nginx-proxy/nginx.tmpl
curl -s https://raw.githubusercontent.com/jwilder/nginx-proxy/master/nginx.tmpl> $web_dir/nginx-proxy/nginx.tmpl
# Remove unnecessary files and folders
cd $web_dir
rm -rf your-website-one.com your-website-two.com README.Rmd .gitignore .Rbuildignore .git
The downloaded nginx-proxy
folder contains a docker-compose.yml
file. This will launch three services:
nginx
: the nginx-reverse proxy, uses the default nginx image. The label is needed so that the letsencrypt container knows which nginx proxy container to use.nginx-gen
: uses the jwilder/docker-gen image. Its command instruction will render a nginx configuration (based on nginx.tmpl) for each website / container added to the network.nginx-letsencrypt
: generates and renew the HTTPS certificates. Read more: How to Host Multiple HTTPS Websites on One Server.
All these services are bound to the nginx-proxy
network.
Step 3. Download a WordPress docker-compose template
Download a template from Github at: kassambara/wordpress-docker-compose
# Download a WordPress docker-compose template and
# put it in a folder with the same name as your domain name
your_domain_name=www.example.com
cd $web_dir
git clone https://github.com/kassambara/wordpress-docker-compose $your_domain_name
# Change the online docker-compose file name
cd $your_domain_name
mv docker-compose-onlinehost.yml docker-compose.yml
# Remove unnecessary files and folders
rm -rf .git .gitignore
Template directory tree:
www/www.example.com
├── LICENSE
├── Makefile
├── README.md
├── config
│ └── php.conf.ini
├── docker-compose.yml
├── mysql
├── wordpress
├── wp-auto-config.yml
└── wpcli
├── Dockerfile
├── Makefile
└── entrypoint.sh
Essential folders:
- mysql: MySQL database files for MariaDB
- wordpress: WordPress web files
- wpcli contains a Dockerfile example to build WordPress CLI.
Essential files:
- setup-onlinehost.sh: Automatically set online production environment variables.
- .env file: contain the environment variables required for the wordpress installation
- docker-compose.yml: WordPress docker compose application services
- Makefile: Set of simple bash command lines to build, install and configure WordPress, as well as, to start and stop the docker containers.
Step 4. Inspect your web directory
Your web directory should look like this:
www
├── README.md
├── nginx-proxy
│ ├── certs
│ ├── conf.d
│ ├── docker-compose.yml
│ ├── html
│ ├── nginx.tmpl
│ └── vhost.d
└── www.example.com
├── LICENSE
├── Makefile
├── README.md
├── config
├── docker-compose.yml
├── mysql
├── wordpress
├── wp-auto-config.yml
└── wpcli
Step 5. Edit the WordPress Docker setup environment variables
# 1. Open the setup file
nano $web_dir/$your_domain_name/setup-onlinehost.sh
# 2. Change these settings as you want
project_name="wordpress"
user_name="wordpress"
pass_word="wordpress"
email="your-email@example.com"
website_title="My Blog"
website_url="https://www.example.com"
phmyadmin_url="sql.example.com"
env_file=".env"
compose_file="docker-compose.yml"
# 3. Execute:
chmod +x setup-onlinehost.sh && ./setup-onlinehost.sh
An automatically updated .env
file is available to easily set docker-compose variables without having to modify too much the docker-compose.yml
configuration file itself.
Open the .env
file and update the contents if you want. In our example, the file is located at www/www.example.com/.env
# Open the file
nano $web_dir/$your_domain_name/.env
Contents:
# 1/ Project name -------------------------------------------------
# Must be lower-case, no spaces and no invalid path chars.
# Will be used also as the WP database name
COMPOSE_PROJECT_NAME=wordpress
# 2/ Database user and password -----------------------------------------
# Set non-root database user if wanted (optional)
DATABASE_PASSWORD=password
DATABASE_USER=root
# 3/ For wordpress auto-install and auto-configuration -------------------
WORDPRESS_WEBSITE_TITLE="My Blog"
# URL: Use this for localhost
WORDPRESS_WEBSITE_URL="https://www.example.com"
WORDPRESS_WEBSITE_URL_WITHOUT_HTTP="www.example.com"
WORDPRESS_WEBSITE_POST_URL_STRUCTURE="/blog/%postname%/"
# Website admin identification. Specify a strong password
WORDPRESS_ADMIN_USER="wordpress"
WORDPRESS_ADMIN_PASSWORD="wordpress"
WORDPRESS_ADMIN_EMAIL="your-email@example.com"
# 4/ Software versions -----------------------------------------------
WORDPRESS_VERSION=latest
MARIADB_VERSION=latest
# 5/ Ports: Can be changed -------------------------------------------
PHPMYADMIN_PORT=8080
# 6/ Volumes on host --------------------------------------------------
WORDPRESS_DATA_DIR=./wordpress
# 7/ Healthcheck availability of host services (mysql and woordpress server)
# Waiting time in second
WAIT_BEFORE_HOSTS=5
WAIT_AFTER_HOSTS=5
WAIT_HOSTS_TIMEOUT=300
WAIT_SLEEP_INTERVAL=60
WAIT_HOST_CONNECT_TIMEOUT=5
# 8/ Used only in online deployement ---------------------------------
WORDPRESS_WEBSITE_URL_WITHOUT_WWW=example.com
PHPMYADMIN_WEBSITE_URL_WITHOUT_HTTP=sql.example.com
Click here to inspect the content of configuration files
Step 6. Edit the docker-compose configuration file
Inspect and update the$web_dir/$your_domain_name/docker-compose.yml
file if you want. It contains a container that redirect non-www to www (recommended). If you don’t want this behaviour, just remove the container.
....
# Redirect non-www to www
redirectnonwww:
image: cusspvz/redirect
container_name: ${COMPOSE_PROJECT_NAME}_redirectnonwww
restart: always
environment:
- VIRTUAL_HOST=${WORDPRESS_WEBSITE_URL_WITHOUT_WWW}
- HTTPS_METHOD=noredirect
- LETSENCRYPT_HOST=${WORDPRESS_WEBSITE_URL_WITHOUT_WWW}
- LETSENCRYPT_EMAIL=${WORDPRESS_ADMIN_EMAIL}
- REDIRECT=${WORDPRESS_WEBSITE_URL}
# CHANGE THE REDIRECT URL
- REDIRECT=https://www.example.com
- WORKER_CONNECTIONS=1024
networks:
- ${COMPOSE_PROJECT_NAME}_default
- nginx-proxy
.....
Step 7. Run the nginx reverse proxy
# 1. Create the docker network. Do this once
docker network create nginx-proxy
# 2. Create the reverse proxy with the
# nginx, nginx-gen and nginx-letsencrypt containers
cd $web_dir/nginx-proxy/
docker-compose up -d
Step 8. Allow users to post large documents or images
In the Nginx configuration file, you need also to increase client_max_body_size
to allow users to post large documents. You can add for example the line client_max_body_size 64M;
in the server{} directive.
# 1. Create a configuration file for your domain
# in the nginx-proxy vhost folder
nano $web_dir/nginx-proxy/vhost.d/$your_domain_name
# 2. Add this to allow the upload of 64M
client_max_body_size 64M;
One single command to do the above operation:
echo 'client_max_body_size 64M;' > nano $web_dir/nginx-proxy/vhost.d/$your_domain_name
Step 9. Install WordPress using docker compose
Two methods are available for installing and configuring your WordPress web site:
- Automatic installation + manual configuration
- Automatic installation + automatic configuration
Method 1. Automatic installation + manual configuration
Automatic installation of WordPress in docker
Three lines of docker-compose
commands:
- Build docker application images
- Start wordpress installation in detached mode
- (Health)Check the availability of WordPress docker services
Go into your domaine name folder and type this:
cd $your_domain_name
docker-compose build
docker-compose up -d
docker-compose run --rm healthcheck
Explaining the different docker compose options:
-d
: start containers in detached options--rm
: remove containers when stopped
Alternatively, you can also use the following make
shortcut commands. Easy to use on Unix operating systems (MAC and Linux)
cd $your_domain_name
make install
Console logs look like this:
Manual WordPress configuration
Navigate your browser to www.example.com and follow the installation prompts
- Set WordPress language
- Create an administrative user
- Success
- Log in as the administrative user
- Admin dashboard
Method 2. Automatic installation and configuration
Before, re-trying the installation, first clean up everything as follow:
docker-compose down
rm -rf mysql/* wordpress/*
The following docker-compose
or make
commands can be used to automatically install and configure wordpress.
Using the docker-compose
commands.
# Build docker images and start up wordpress
docker-compose up -d --build
# Automatic wordpress configuration
docker-compose -f docker-compose.yml -f wp-auto-config.yml run --rm wp-auto-config
Using the make
commands. For Unix systems (MAC and Linux) users:
make autoinstall
Step 10. Access to your website
- Visit your wordpress website at www.example.com. Default identification for admin (www.example.com/wp-login.php):
Username: wordpress
andPassword: wordpress
Once your site is running you can begin to create and publish any content you’d like in your WordPress instance.
- Visit your database via phpMyAdmin at http://sql.example.com
Username: root
andPassword: password
Shutdown and cleanup
This section present useful set of commands to know.
- Shutdown WordPress docker containers and dependencies. The command
docker-compose down
removes the containers and default network, but preserves your WordPress database.
# Stop and remove containers
docker-compose down
- (Re)start WordPress docker compose containers
docker-compose up -d
- Reset or reinitialize everything
- Stop and remove containers
- Remove related wordpress and mysql installed files
docker-compose down
rm -rf mysql/* wordpress/*
Note that, instead of using the above docker-compose
commands, you can also use easily the following make
shortcut command lines if you have Unix systems (MAC / Linux).
# Build, and start the wordpress website
make start
# Stop and remove wordpress docker containers
make down
# Reset everything
make reset
Summary
This tutorial provides a practical guide for Docker WordPress production deployment.
Recommended for you
This section contains best data science and self-development resources to help you on your path.
Coursera - Online Courses and Specialization
Data science
- Course: Machine Learning: Master the Fundamentals by Stanford
- Specialization: Data Science by Johns Hopkins University
- Specialization: Python for Everybody by University of Michigan
- Courses: Build Skills for a Top Job in any Industry by Coursera
- Specialization: Master Machine Learning Fundamentals by University of Washington
- Specialization: Statistics with R by Duke University
- Specialization: Software Development in R by Johns Hopkins University
- Specialization: Genomic Data Science by Johns Hopkins University
Popular Courses Launched in 2020
- Google IT Automation with Python by Google
- AI for Medicine by deeplearning.ai
- Epidemiology in Public Health Practice by Johns Hopkins University
- AWS Fundamentals by Amazon Web Services
Trending Courses
- The Science of Well-Being by Yale University
- Google IT Support Professional by Google
- Python for Everybody by University of Michigan
- IBM Data Science Professional Certificate by IBM
- Business Foundations by University of Pennsylvania
- Introduction to Psychology by Yale University
- Excel Skills for Business by Macquarie University
- Psychological First Aid by Johns Hopkins University
- Graphic Design by Cal Arts
Amazon FBA
Amazing Selling Machine
Books - Data Science
Our Books
- Practical Guide to Cluster Analysis in R by A. Kassambara (Datanovia)
- Practical Guide To Principal Component Methods in R by A. Kassambara (Datanovia)
- Machine Learning Essentials: Practical Guide in R by A. Kassambara (Datanovia)
- R Graphics Essentials for Great Data Visualization by A. Kassambara (Datanovia)
- GGPlot2 Essentials for Great Data Visualization in R by A. Kassambara (Datanovia)
- Network Analysis and Visualization in R by A. Kassambara (Datanovia)
- Practical Statistics in R for Comparing Groups: Numerical Variables by A. Kassambara (Datanovia)
- Inter-Rater Reliability Essentials: Practical Guide in R by A. Kassambara (Datanovia)
Others
- R for Data Science: Import, Tidy, Transform, Visualize, and Model Data by Hadley Wickham & Garrett Grolemund
- Hands-On Machine Learning with Scikit-Learn, Keras, and TensorFlow: Concepts, Tools, and Techniques to Build Intelligent Systems by Aurelien Géron
- Practical Statistics for Data Scientists: 50 Essential Concepts by Peter Bruce & Andrew Bruce
- Hands-On Programming with R: Write Your Own Functions And Simulations by Garrett Grolemund & Hadley Wickham
- An Introduction to Statistical Learning: with Applications in R by Gareth James et al.
- Deep Learning with R by François Chollet & J.J. Allaire
- Deep Learning with Python by François Chollet
Version: Français
Hello, I am trying set up wordpress on docker for my domain name.
I did all steps but I receive blank screen on web site. In step 9 it says “wordpress: 80 now available” instead of “nginx: 80 now available”. I need your help.
This was an awesome tutorial….. Much appreciated!!
fantastic. how can I force to remove www?
You are the BEST!!! All I had to do was keep clicking to find the thing I need. Thanks a million 🙂
Thank you so much for the positive feedback, highly appreciated!
Some remarks:
Projekt_name must be set to “wordpress”
Quotation marks should be added in value of WORDPRESS_WEBSITE_URL_WITHOUT_HTTP in .env.
First REDIRECT in docker-compose.yml in redirectnonwww needs to be commented out, because of duplicate error.
This is not working. The browser always says that it can’t trust my certificate. I don’t know what else to do here.
I spent the entire night trying to figure out how to deploy.
This works for http, but https doesn’t work at all.
I created this script to maker easier all the process.
#!/bin/bash
web_dir=/src/www
myusername=root
domain_name=domain.subdomain.com
genoteca_folder=/src/www/$domain_name
nginx_proxy_repo=https://github.com/kassambara/nginx-multiple-https-websites-on-one-server
nginx_folder=/src/www/nginx-multiple-https-websites-on-one-server/nginx-proxy
final_nginx_folder=/src/www/nginx-proxy
echo —INSTALL REQUIRED COMPONENTS—-
sudo apt update
sudo apt install apt-transport-https ca-certificates curl software-properties-common
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add –
sudo add-apt-repository “deb [arch=amd64] https://download.docker.com/linux/ubuntu focal stable”
sudo apt update
apt-cache policy docker-ce
sudo apt install docker-ce docker-compose git
sudo systemctl status docker
echo —CREATE AND GIVE PERMISSIONS TO WEBSITES DIR—-
sudo mkdir -p $web_dir
# 2. set your user as the owner
sudo chown -R $myusername $web_dir
# 3. set the web server as the group owner
sudo chgrp -R www-data $web_dir
# 4. 755 permissions for everything
sudo chmod -R 755 $web_dir
# 5. New files and folders inherit
# group ownership from the parent folder
chmod g+s $web_dir
echo —INSTALL NGINX PROXY—-
git clone $nginx_proxy_repo $web_dir
rm -rf $web_dir/nginx-proxy/nginx.tmpl
curl -s https://raw.githubusercontent.com/jwilder/nginx-proxy/master/nginx.tmpl > $web_dir/nginx-proxy/nginx.tmpl
cd $web_dir
rm -rf your-website-one.com your-website-two.com README.Rmd .gitignore .Rbuildignore .git README.md
echo —INSTALL WORDPRESS—-
cd $web_dir
git clone https://github.com/kassambara/wordpress-docker-compose $domain_name
echo —CONFIGURE DOCKER COMPOSE FOR ONLINEHOST—-
cd $genoteca_folder
mv docker-compose-onlinehost.yml docker-compose.yml
echo —FINAL TOUCHES—-
cd $genoteca_folder
vi ./setup-onlinehost.sh
chmod +x setup-onlinehost.sh && ./setup-onlinehost.sh
vi .env
vi docker-compose.yml
cd $final_nginx_folder
cd vhost.d
echo “client_max_body_size 64M;” > $domain_name
cd $final_nginx_folder
docker network create nginx-proxy
docker-compose up -d
cd $genoteca_folder
docker-compose up -d –build
docker-compose -f docker-compose.yml -f wp-auto-config.yml run –rm wp-auto-config
I don’t do the non-www to www. I remove the container from the docker-compose.yml