Use Nginx to run your Drupal site

Type: Tutorial Difficulty: Intermediate

I have a fresh website based on Apache+PHP5 to be converted into Nginx and PHP5-FastCGI. What can I do?

Stage 1 CGI version of PHP5

Nginx only supports CGI version of PHP5 (not the Apache module). In FastCGI mode, PHP5 runs like a server that forks out a number of children to handle incoming requests. This number is indicated in the start-up script. It can be any number where necessary. Of course, we would not blow up our servers, so memory_limit*number of PHP children < available memory.

In Debian/Ubuntu systems, we can simply install php5-cgi in one line:

1
root@domU:~# apt-get install php5-cgi

This will install the CGI version of PHP5 that includes FastCGI support. Any modern Linux distribution would come with such a similar package management system. After installation, run the following command to confirm that PHP has FastCGI enabled.

1
2
3
4
root@domU:~# php5-cgi -v
PHP 5.2.4-2ubuntu5.5 with Suhosin-Patch 0.9.6.2 (cgi-fcgi) (built: Feb 11 2009 20:01:54)
Copyright (c) 1997-2007 The PHP Group
Zend Engine v2.2.0, Copyright (c) 1998-2007 Zend Technologies

Stage 2 Spawn the FastCGI server

PHP5-CGI binary supports to serve up as a FastCGI server. However, setting up the environment is complicated with PHP5-CGI binary. Instead, we can use a general FastCGI spawn-er from Lighttpd to help create the service. Download the latest version of Lighttpd from here, extract the package, run the configure script, make, and copy spawn-fcgi binary to /usr/bin.

1
2
3
root@domU:~/lighttpd-1.4.20# ./configure
root@domU:~/lighttpd-1.4.20# make
root@domU:~/lighttpd-1.4.20# cp src/spawn-fcgi /usr/bin

Then we can spawn the PHP5-FastCGI like this:

1
2
3
4
root@domU:~# /usr/bin/spawn-fcgi -f /usr/bin/php5-cgi\
   -a 127.0.0.1 -p 16000 -C 5 -F 2\
   -P /var/run/fastcgi-php.pid\
   -u www-data -g www-data

This command will instantiate two PHP5 FastCGI processes (each of which have 5 children) and bind them to 127.0.0.1 (localhost) and port 16000. So we have ten processes listening for PHP requests. The PHP processes run under www-data permission.

Stage 3 Build Nginx

Imagine how one man can beat the world? Nginx (Engine X) is a blazingly super fast HTTP server written by Ignor Sysoev. According to Netcraft in December 2008, Nginx serves or proxied 3.5 millions of virtual hosts in the 3rd place of the market. 2 of Alexa Top-100 sites use Nginx.

Download Nginx from its official site and extract the tarball, then run:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
root@domU:~/nginx-0.7.34# ./configure --with-http_ssl_module\
  --with-http_realip_module --with-http_addition_module\
  --with-http_sub_module --with-http_dav_module\
  --with-http_flv_module --with-http_stub_status_module\
  --with-mail --with-mail_ssl_module\
  --http-log-path=/var/log/nginx/access.log\
  --http-client-body-temp-path=/mnt/nginx/client\
  --http-proxy-temp-path=/mnt/nginx/proxy\
  --http-fastcgi-temp-path=/mnt/nginx/fastcgi\
  --pid-path=/var/run/nginx.pid\
  --lock-path=/var/lock/nginx.lock\
  --sbin-path=/usr/sbin\
  --error-log-path=/var/log/nginx/error.log\
  --conf-path=/database/configuration/nginx/nginx.conf\
  --user=www-data --group=www-data --with-sha1=/usr/lib
root@domU:~/nginx-0.7.34# make &amp;&amp; make install

Nginx is configured with most useful modules. Note that –http-client-body-temp-path, –http-proxy-temp-path and –http-fastcgi-temp-path are cache directories used by Nginx. Default user and group can be configured to the system’s default user for http service instead of nobody, although they can also be configured at runtime.

Stage 4 Run Nginx

Starting up Nginx is simple and straight. After properly configuring your nginx settings, just type nginx and hit return. Then it will start. I also provide a set of Nginx configuration here to simplfy your process. There are several important pieces of code to make Drupal work under Nginx in the configuration.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# rewrite rules
if (!-e $request_filename) {
  rewrite ^/(.*)$ /index.php?q=$1 break;
}
 
include supercache;
 
# serve php files
location ~ \.php(/|$) {
  fastcgi_pass    127.0.0.1:16000;
  fastcgi_index   index.php;
  fastcgi_param   SCRIPT_FILENAME /database/www/mydomain.com$fastcgi_script_name;
  include         fastcgi_params;
}
 
# hide protected files
location ~* \.(engine|inc|info|install|module|profile|po|sh|sql|theme|tpl(\.php)?|xtmpl)$|^(code-style\.pl|Entries.*|Repository|Root|Tag|Template)$ {
  deny all;
}

The location context for PHP scripts makes Nginx talk to PHP FastCGI server. And the if context for rewrite makes Drupal support clean URLs.

You’re done!

Download Nginx configuration files

References

An old thread from the official Drupal forum.

Comment (1)

  1. wayne wrote::

    eh…
    I really don’t like the lighttpd compiling step…

    [Reply]

    Tuesday, July 7, 2009 at 11:00 pm #

Supported by Webinit Consulting