WordPress, Nginx and PHP-FPM

This is a post written originally back in 2012, a lot of things are of date.

This is my notes for setting up a VPS optimized for WordPress, with Nginx and PHP5-FPM. I’m setting up MySQL, W3 Total Cache, Git and a few other things. I assume that you already have a VPS with has an allocated a ip adress. Also, you must have a domain.

Nginx?

NGINX is the world’s most popular open source web server for high traffic sites, powering over 100 million properties. Nginx works differently than Apache, mainly with regard to how it handles threads. Nginx has grown in popularity since its release due to its light-weight resource utilization and its ability to scale easily on minimal hardware. Nginx excels at serving static content quickly and is designed to pass dynamic requests off to other software that is better suited for those purposes.

Read more

Configure and update your VPS

sudo apt-get install python-software-properties sudo apt-get update sudo apt-get upgrade

Install the Nano editor (or just use Vim)

sudo apt-get install nano

Configure hostname

nano /etc/hosts

127.0.0.1 localhost.localdomain localhost 127.0.0.1 myserver

hostname = the name on your VPS

Install Nginx, PHP and PHP5-FPM

sudo apt-get install nginx sudo apt-get install php5-cli php5-common php5-mysql php5-imagick php5-gd php5-dev sudo apt-get install php5-fpm php5-cgi php-pear php5-memcache php-apc

Start PHP-FPM

sudo service php5-fpm start

cd /etc/nginx/sites-enabled sudo ln -s ../sites-available/default default

Start Nginx

sudo service nginx start

You can now visit your domain mywebsite.com and see “Welcome to Nginx”

sudo rm default sudo service nginx stop sudo service php5-fpm stop

Remove the symlink igen and stop Nginx

Configure Nginx

cd /etc/nginx

Edit nginx.conf

nano nginx.conf

Add this (gist)

Change worker_processes and worker_connections to match your server. If your VPS has got 6 CPU cores, adjust worker_processes to 6. worker_connections till 6 * 1024 = 6144. Find out how many CPU cores by running cat /proc/cpuinfo

Go to /sites-avaliable

cd sites-available

Create a file called mywebsite.com

touch mywebsite.com nano mywebsite.com

Add this (gist)

Create the folder global inside the nginx folder

Text
cd /etc/nginx
sudo mkdir global
cd global

Create the file restrictions.conf

Text
touch restrictions.conf
nano restrictions.conf

Add this: (gist)

Create the file php5-fpm.conf inside the global directory

Text
touch php5-fpm.conf
nano php5-fpm.conf

Add this (gist)

Set up your site

Text
cd /etc/nginx/sites-enabled
sudo ln -s ../sites-available/mywebsite.com.se mywebsite.com

Go to the www folder

cd /var/www

Create a group

Text
sudo groupadd web

Add admin rights

Text
sudo usermod -a -G web YOURUSER

Add the group

Text
sudo chgrp web /var/www

Make the www directory writable

Text
sudo chmod -R 775 /var/www

Assign all files to the group

Text
sudo chmod g+s /var/www

Create a folder for your website

Text
mkdir mywebsite.com
cd mywebsite.com

Create a index.php and try out the configuration

Text
touch index.php
nano index.php

Add phpinfo(); and check so everything works

Start Nginx

Text
sudo service nginx start

Start PHP-FPM

Text
sudo service php5-fpm start

Great success!

Secure SSH

Text
Create a user
Text
adduser --home /home/name name

Add user as sudoer

Text
visudo

Add

Text
name ALL=(ALL) ALL

Turn off root login

Text
nano /etc/ssh/sshd_config

Add

Text
PermitRootLogin no
PasswordAuthentication no

Install MySQL

Text
sudo apt-get install mysql-server
sudo apt-get install php5-mysql

Create database

Text
mysqladmin -u root -p create databasnamn

Secure MySQL

Text
mysql_secure_installation

Log in

Text
mysql -u root -p

Create user

Text
CREATE USER 'anvnamn'@'localhost' IDENTIFIED BY 'c0MpLiCaTeDp@55w0rd';

Grant access

Text
GRANT ALL ON *.* TO 'anvnamn'@'localhost';

Logout from the MySQL shell

Text
exit

Manage the database

I prefer to use Sequel Pro . It is a fast, easy-to-use Mac database management application for working with MySQL databases. Simple and looks great. Sequel Pro

Install WordPress

This is outdated. You should use WP-CLI instead.

Istall wget

Text
sudo bash
apt-get update
apt-get -f install
apt-get install wget

Download WordPress

Text
wget http://sv.wordpress.org/wordpress-4.2.2-sv_SE.tar.gz
tar xfz wordpress-4.1-sv_SE.tar.gz
mv wordpress/* ./
rmdir ./wordpress/
rm -f wordpress-3.9.1-sv_SE.tar.gz
mv wp-config-sample.php wp-config.php

Edit wp-config add your credentials and settings

nano wp-config.php

Or use my little bash script wp-installer

Install cURL

sudo apt-get install curl

Install WP-CLI

WP-CLI is a set of command-line tools for managing WordPress installations. You can update plugins, set up multisite installs and much more, without using a web browser.

First, download wp-cli.phar using wget or curl. For example

Text
curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar

Then, check if it works:

Text
php wp-cli.phar --info

To be able to type just wp, instead of php wp-cli.phar, you need to make the file executable and move it to somewhere in your PATH. For example:

Text
chmod +x wp-cli.phar
sudo mv wp-cli.phar /usr/local/bin/wp

No try wp --info

Bonus: Add Tab completions.

Setup SSH-keys

We need to connect to the server without using password every time:

Text
mkdir ~/.ssh
chmod 700 ~/.ssh
ssh-keygen -t rsa

Own your .ssh folder (for user with rootaccess)

Text
cd ~
sudo chown name .ssh

Copy keys to the server:

Text
cat ~/.ssh/id_rsa.pub | ssh user@dindoman.se 'cat - >> ~/.ssh/authorized_keys'

Set correct access

Text
chmod 600 ~/.ssh/authorized_keys && chmod 700 ~/.ssh/

Install Git

apt-get install git-core

Add the git user

Text
adduser git
su git
cd /home/git
mkdir .ssh
chmod 700 .ssh
cd .ssh
touch authorized_keys

Test

Text
ssh git@mywebsite.com

Add remote git repo

Text
git remote add origin git@mywebsite.com.se/var/www/mywebsite.com

Solve the git objects access rights

Text
cd repository.git
sudo chmod -R g+ws *
sudo chgrp -R mygroup *
git config core.sharedRepository true
sudo chown -R git:git .git/

Set git user as sudoer

Text
visudo
git ALL=(ALL) ALL

W3 Total Cache

Text
touch /etc/nginx/sites-available/mywebsite.com

Add

Text
include global/wordpress-w3-total-cache.conf;

Create the w3 settings file

Text
touch /etc/nginx/global/wordpress-w3-total-cache.conf
Text
nano /etc/nginx/global/wordpress-w3-total-cache.conf

Add this (gist)

Also create nginx.conf inside /var/ww/mywebsite.com

Text
touch nginx.conf
nano nginx.conf

Add: (gist)

Change allowed maximum file size

Text
nano /etc/nginx/sites-available/default

Add for example:

Text
client_max_body_size 30M;

Edit php.ini

Text
nano /etc/php5/fpm/php.ini

Under File Uploads, change to:

Text
upload_max_filesize = 30M;

Reload PHP-FPM and Nginx

Text
service php5-fpm reload
service nginx reload

Read more

Add correct MIME-type for SVG (.svg)

Edit /etc/nginx/mime.types

Text
nano/etc/nginx/mime.types
image/svg+xml svg svgz;

Add correct mime-types for webfonts

if you use webfonts, Nginx can need a helping hand serving the correct mime-types, instead of just the default application/octet-stream. Edit /etc/nginx/mime.types

Text
application/vnd.ms-fontobject eot;
application/x-font-ttfttf;
font/opentype ott;
application/font-woff woff;

Support more file formats

Allow .eps files to be uploaded in wp-admin

Text
add_filter('upload_mimes', 'website_upload_mimes');

function website_upload_mimes ( $existing_mimes=array() ) {

// Add *.EPS files to Media upload
$existing_mimes['eps'] = 'application/postscript';

return $existing_mimes;
}

First 5 minutes on a server

Update. If you use Ubuntu 12 och PHP 5.4+, check out:

Fix locale issues

Shell
locale-gen en_US en_US.UTF-8 hu_HU hu_HU.UTF-8
dpkg-reconfigure locales

Did you enjoy this post?