Nginx

From DreamHost
Jump to: navigation, search

VPS

Overview

The main nginx wiki article describes this software well:

Nginx is a free, open-source, high-performance HTTP server and reverse proxy, as well as an IMAP/POP3 proxy server. Written by Igor Sysoev in 2005, Nginx now hosts nearly 6% (13M) of all domains worldwide.

Nginx is known for its high performance, stability, rich feature set, simple configuration, and low resource consumption.

Nginx is one of a handful of servers written to address the C10K problem. Unlike traditional servers, Nginx doesn't rely on threads to handle requests. Instead it uses a much more scalable event-driven (asynchronous) architecture. This architecture uses small, but most importantly, predictable amounts of memory under load. Even if you don't expect to handle thousands of simultaneous requests, you can still benefit from Nginx's high-performance and small memory footprint. Nginx scales in all directions: from the smallest VPS all the way up to clusters of servers.

Nginx powers several high-visibility sites, such as WordPress, Hulu, Github, Ohloh, SourceForge and TorrentReactor.

Nginx is available on DreamHost Private Servers as an optional web server to run your sites. Older Private Servers may need to be moved to the new cluster for this feature to work out-of-the-box. If the feature is not available as described below, then you can write in to tech support to get your PS moved to a newer server that supports it.

Why nginx?

So, all DreamHost Private Servers use Apache by default. That's good enough, right? Well, yes and no. A very well tuned Apache server can certainly hold its own, but that can be difficult to do and requires a fair amount of knowledge/tinkering. Most people wanting a PS are interested in better performance because they've outgrown shared servers. Nginx is a very good choice in cases where you have a blog or other site that gets large volumes of traffic and are running into performance/memory issues on a PS for the reasons mentioned in the quote above. Basically, in general, it will serve your site faster while using less memory than Apache -- which will let you handle a much larger amount of traffic much more gracefully than Apache would. For a more detailed look at this, take a look at the Web Server Performance Comparison page.

Why doesn't DreamHost use nginx by default then?!

Inquiring minds want to know!! Well, the reason for that is really quite simple. Practically every piece of web software in existence expects to be served using Apache. Generally, that means this software uses htaccess for various and sundry things. For instance, an out-of-the-box WordPress installation will work fine with nginx. However, if you turn permalinks on, suddenly links to your posts will break. Why? Permalinks generate htaccess rewrite rules that route requests to the index.php file that will then translate nice looking URLs like http://www.someblog.com/2009/12/some-article/ into something that WordPress knows how to work with. Note that nginx does not read .htaccess files! As such, most web software that utilizes them will be "broken" immediately upon installation without additional work.

PHP, Nginx, and You

One thing to keep in mind before enabling Nginx is how PHP is handled with it. When using Nginx a set number of PHP processes are started up for every user a domain is hosted under. The same number are started regardless of how many domains are hosted for it. As such, if you have 10 domains spread across 10 separate FTP users you'll get 10x as many PHP processes as you would otherwise get. So, if Nginx is starting up 5 PHP processes, you would end up with 50, which would eat up a considerable amount of memory. The best configuration when using Nginx is to consolidate your domains under one FTP user. You should definitely do this prior to switching to Nginx. Also keep in mind that the number of PHP processes that spawn per user is automatically scaled with the amount of memory your PS is set to use, so increasing your PS's memory allocation

Limiting the amount of processes spawned per domain

  • Globally - With an admin user and sudo, place export PHP_FCGI_CHILDREN=8 into /dh/nginx/servers/httpd-ps12345/environ, where 8 is the number of desired processes per domain.
  • Per-user - Create $HOME/.php-launcher as an executable (chmod a+x) script containing the following, where 8 is the number of desired processes per domain:
#!/bin/sh
export PHP_FCGI_CHILDREN=8
exec /dh/cgi-system/php5.cgi $*

(Note: The "Globally" method seemed to produce a 'ulimit' error for me which won't go away, even if I revert the file. The "Per-user" method, however, with a value of 2 reduced my memory footprint from 1.3 GB to 130 megs. This should be done by DH by default... seems like a huge waste without it.)

Customizing PHP under Nginx

Note: the following instructions assume you are not running supervisor to control PHP on your VPS server. If you are, the instructions do not apply.

Dreamhost has a few bits of custom logic in their nginx init script to allow PHP customization:

  • If you have a file at $HOME/.php-ini, it's used in place of the system php.ini.
  • If you have an executable at $HOME/.php-launcher, it's used instead of the default PHP binary.

Running PHP 5.3 or 5.4 under Nginx

To change the version of PHP that runs, you need to do 2 things:

  1. Edit or create $HOME/.php-launcher to run the version of PHP you want:
    exec /dh/cgi-system/php53.cgi $*
    exec /dh/cgi-system/php54.cgi $*
    • Note - you will also need to give the .php-launcher file the user execution bit using this command (or something similar to it):
    chmod u+x $HOME/.php-launcher
  2. Link $HOME/.php-ini with the php.ini for the correct PHP version by either executing the following command:
    ln -s /etc/php53/php.ini .php-ini
    ln -s /etc/php54/php.ini .php-ini
    • Or create a copy of the DreamHost php.ini file using this command
    cp /etc/php53/php.ini .php-ini
    cp /etc/php54/php.ini .php-ini

Once you have done those two things, you need to restart PHP. If you have an admin user, you can do using the command below. Otherwise, reboot the VPS to activate the new configuration.

 sudo /etc/init.d/nginx restartphp

Enabling Nginx

So, you know the benefits and the downside to using nginx now and want to proceed anyways. This is how! Before proceeding, you may want to read through the entire guide to make preparations beforehand to avoid potential downtime due to not having the necessary configuration settings in place. Also keep in mind that enabling this will do so for all domains on your PS!

Browse to the Private Servers -> Configure Server area of your webpanel and switch the HTTP Server to nginx (if this option isn't available, contact support and ask if your PS can be moved to a newer server):

Nginx webserver.jpg

That's it! After a few minutes your PS will be running with nginx rather than Apache.

Configuration File Locations

The default nginx configuration will likely work for most people out-of-the-box. If you want to look at it though, you can find it here:

/dh/nginx/servers/httpd-psXXXXXX/nginx.conf

You cannot work with this file through FileZilla or similar SFTP tools, you must use SSH and pico to view/edit.

sudo pico /dh/nginx/servers/httpd-psXXXXXX/nginx.conf  

Where "psXXXXXX" is your PS. Note that you'll need an admin user created with sudo privileges to access that directory. The defaults in there will be fine. Each domain has a directory that the default nginx.conf will load files from when nginx starts. These directories will follow this naming convention:

/home/YOURUSER/nginx/YOURDOMAIN.COM/*

Where "YOURUSER" is (surprise, surprise) the user your site is hosted under and "YOURDOMAIN.COM" is your domain or subdomain. The nginx directory mentioned above may, or may not exist. If it doesn't, simply create it like so:

cd ~
mkdir -p nginx/yourdomain.com

Create new .conf files in this directory to customize your nginx server. All of the entries in this file get "inserted" into the SERVER block of the default nginx.conf.

Whenever you make changes to these files make sure you reload nginx with your admin user to make sure there aren't syntax issues that will bite you later!

sudo /etc/init.d/nginx reload

Create new .conf files in this directory to customize your nginx server. All of the entries in this file get "inserted" into the SERVER block of the default nginx.conf.

Nginx and Custom PHP Install

When you install your own version of php, such as one that DreamHost doesn't support with Nginx (such as php 5.4.X) you need a way to start/stop nginx and php.

Quick php install:

sudo ./configure --prefix=/home/example/php --enable-sockets --with-curl --enable-mbstring --with-mysql --with-gd
sudo make
sudo make install

Next copy the following script into /etc/init.d/php-fastcgi

#!/bin/bash
BIND=/home/username/.php.sock      # Binds to the socket
USER=username                      # User that will own this process
PHP_FCGI_CHILDREN=15               # Number of php children
PHP_FCGI_MAX_REQUESTS=1000         # Number of max requests per child

PHP_DIR=/home/username/php/bin     # Location of your php install
PHP_CGI=$PHP_DIR/php-cgi           # Location of php-cgi
PHP_CGI_NAME=`basename $PHP_CGI`
PHP_CGI_ARGS="- USER=$USER PATH=$PHP_DIR PHP_FCGI_CHILDREN=$PHP_FCGI_CHILDREN PHP_FCGI_MAX_REQUESTS=$PHP_FCGI_MAX_REQUESTS $PHP_CGI -b $BIND"
RETVAL=0

start() {
	echo -n "Starting Nginx: "
	/etc/init.d/nginx start
	echo -n "Starting PHP FastCGI: "
	start-stop-daemon --quiet --start --background --chuid "$USER" --exec /usr/bin/env -- $PHP_CGI_ARGS
	RETVAL=$?
	echo "$PHP_CGI_NAME."
}
stop() {
	echo -n "Stopping Nginx: "
	/etc/init.d/nginx stop
	echo -n "Stopping PHP FastCGI: "
	killall -q -w -u $USER $PHP_CGI
	RETVAL=$?
	echo "$PHP_CGI_NAME."
}

case "$1" in
   start)
     start
 ;;
   stop)
     stop
 ;;
   restart)
     stop
     start
 ;;
   *)
     echo "Usage: php-fastcgi {start|stop|restart}"
     exit 1
 ;;
esac
exit $RETVAL

You now can use one of the following commands (depending on your goal) to start, stop, or restart the server:

sudo /etc/init.d/php-fastcgi start
sudo /etc/init.d/php-fastcgi stop
sudo /etc/init.d/php-fastcgi restart

Nginx Configurations for Common Web Applications

That's great and all, but let's get down to business! You have a web application that needs some tender love and affection to get running with nginx! Below are some of the most common use cases. In all examples, we'll assume a domain named example.com exists and is the site we're setting this configuration up for. Also, note that any line prefaced with a "#" is a comment.

WordPress

This is probably the most used web application around and it works great with nginx! Before we get going here, you should create a wordpress.conf file (the name doesn't really matter, but generally you want to at least give it a .conf extension) in the following location:

/home/YOURUSER/nginx/example.com/

Like so:

nano /home/YOURUSER/nginx/example.com/wordpress.conf

This is where you'll put all your nginx config rules.

If you are going to share wordpress configuration across multiple sites, you can create a default file and then create symlinks for each of your sites, like so:

mkdir -p /home/YOURUSER/nginx/default-wp/
nano /home/YOURUSER/nginx/default-wp/wordpress.conf
ln -s /home/YOURUSER/nginx/default-wp/ /home/YOURUSER/nginx/example.com
ln -s /home/YOURUSER/nginx/default-wp/ /home/YOURUSER/nginx/example2.com

Permalinks

The most basic set of WordPress rules that will get you up and running immediately are these:

#######################
# Permalinks

if (!-e $request_filename) {
  rewrite ^.*$ /index.php last;
}

That will get all basic WordPress functionality going in terms of permalinks.

An alternate approach, which does not use 'if', is as follows:

#######################
# Permalinks

try_files $uri $uri/ /index.php?$args;

Multisite

If you're using Multisite, you will need slightly more advanced rules:

######################
# Permalinks

if (!-e $request_filename) {
 rewrite ^/files(.*) /wp-includes/ms-files.php?file=$1 last;

 rewrite ^(/[^/]+)?(/wp-.*) $2 last;
 rewrite ^(/[^/]+)?(/.*.php) $2 last;

 rewrite ^.*$ /index.php last;
}

This will provide basic functionality for Multisite.

W3 Total Cache

The W3 Total Cache plugin for Wordpress will automatically recognize that it is running under Nginx and will create a default Nginx configuration file which you can copy into your /nginx/<domain name>/ directory.

W3 Total Cache should also be setup to use XCache:

For the W3 settings, I basically turned on XCache support in my dreamhost config panel, then used it everywhere in the W3 settings. Then I enabled the Page Cache, Object Cache, and Browser Cache modules. All three are set to use the XCache to hold their data, so the cached info is stored in RAM, basically.

The Page Cache does whole-page caching, and is nice and fast for repeated queries to the same pages, for logged in or anon users.

The Object Cache does object caching, and causes my admin section to be nice and speedy, since things like posts and such are pulled from memory instead of the database.

The Browser Cache basically just sets the proper expire headers on everything, thus images and such don’t have to be redownloaded all the time. (Snarfed from here)

WP Super Cache

If you're using the WP Super Cache plugin, you'll want to use the following in place of the permalink rules above:

#######################
# WP Super Cache

# if the requested file exists, return it immediately
if (-f $request_filename) {
  break;
}

set $supercache_file '';
set $supercache_uri $request_uri;

if ($request_method = POST) {
  set $supercache_uri '';
}

# Using pretty permalinks, so bypass the cache for any query string
if ($query_string) {
  set $supercache_uri '';
}

if ($http_cookie ~* "comment_author_|wordpress|wp-postpass_" ) {
  set $supercache_uri '';
}

# if we haven't bypassed the cache, specify our supercache file
if ($supercache_uri ~ ^(.+)$) {
  set $supercache_file /wp-content/cache/supercache/$http_host$1/index.html;
}

# only rewrite to the supercache file if it actually exists
if (-f $document_root$supercache_file) {
  rewrite ^(.*)$ $supercache_file break;
}

# all other requests go to Wordpress
if (!-e $request_filename) {
  rewrite ^.*$ /index.php last;
}

FeedBurner

If you have your blog's RSS feed setup using FeedBurner, you'll want to add the following lines above the permalink or supercache lines mentioned previously:

#######################
# FeedBurner

if ($http_user_agent !~ FeedBurner) {
  rewrite ^/comment/feed/ http://feeds.feedburner.com/your-comment-feed last;
  rewrite ^/feed/ http://feeds.feedburner.com/your-feed last;
}

You'll need to replace the "your-comment-feed" and "your-feed" bits with the appropriate FeedBurner URLs you get when you add your feeds to their system.

Drupal

Before we get going here, you should create a drupal.conf file (the name doesn't really matter, but generally you want to at least give it a .conf extension) in the following location:

/home/YOURUSER/nginx/example.com/

Like so:

nano /home/YOURUSER/nginx/example.com/drupal.conf

This is where you'll put all your nginx config rules.

Top Level Domain Install

If your Drupal is installed at the top level of your domain (i.e., http://www.example.com/ is your Drupal install), then you want to add these rules:

#######################
# Drupal Clean URLs (Top Level Domain)

if (!-e $request_filename) {
rewrite ^/(.*)$ /index.php?q=$1 last;
}

Subdirectory Install

If your Drupal is installed in a subdirectory (i.e., http://www.example.com/drupal/ is your Drupal install), then you want to add these rules:

#######################
# Drupal Clean URLs (Subdirectory)

if (!-e $request_filename) {
rewrite ^/drupal$ /drupal/ permanent;
rewrite ^/drupal/(.*)$ /drupal/index.php?q=$1 last;
rewrite ^/(.*)$ /index.php?q=$1 last;
}

You would replace occurrences of "drupal" in the above with whatever your subdirectory is named.

Enable Clean URLs

If you haven't already, you need to login to your Drupal admin user and go to the Administer -> Site Configuration -> Clean URLs area and turn Clean URLs on. If you have trouble finding it, then try browsing to http://www.example.com/index.php?q=admin/settings/clean-urls. If you get an error message saying Clean URLs aren't supported, make sure you remembered to reload your nginx configuration as discussed earlier in the article.

Gotchas

Unfortunately, this configuration currently causes site searches that contain spaces to break. With Apache, when you search for "some thing" that gets converted to "search/node/some+thing". When this is processed by nginx the "+" gets encoded so you end up with "search/node/some%20thing". Thus, your search ends up looking for the string "some+thing" rather than "some thing". There are currently no known workarounds that were forthcoming.

Drupal 6 with Boost, Clean URLs

For this setup I had moved my drupal site off of apache to nginx. Been very happy with the performance. Getting drupal to work was easy but a little slow. I also wanted the drupal module boost to work as well. This here is the config file for my site exactly as it is. I will explain each section. First here is the entire config file located in /home/YOURUSER/nginx/example.com/drupal.conf

#######################################################
### nginx.conf catch-all
#######################################################

client_max_body_size 75M;
 
gzip_static on;
gzip on;
gzip_comp_level 9;
gzip_types application/x-javascript text/css text/plain text/xml application/xml application/xml+rss text/javascript;

location ~ \.(gif|jpg|jpeg|png|tif|bmp|jpe)$ {

valid_referers server_names none blocked ~(pcwintech.com|google.|simpleportforwarding.com);

if ($invalid_referer) {

rewrite ^ http://$host/showimage?file=${uri} permanent;
}

}

location ~ \.(exe|zip|reg|vbs)$ {

valid_referers server_names none blocked ~(pcwintech.com|google.|simpleportforwarding.com);

if ($invalid_referer) {

rewrite ^ http://$host? permanent;
}

}


location = /favicon.ico {
log_not_found off;
access_log off;
}

location = /robots.txt {
allow all;
log_not_found off;
access_log off;
}

# This is mostly based on Drupal's stock .htaccess
location ~* ^.+(\.(txt|engine|inc|info|install|module|profile|po|sh|.*sql|theme|tpl(\.php)?|xtmpl)|code-style\.pl|/Entries.*|/Repository|/Root|/Tag|/Template)$ {
return 404;
}

# serve static files directly
location ~* ^.+\.(jpg|jpeg|gif|png|ico|swf|flv)$ {
access_log off;
expires 30d;
}

# Very rarely should these ever be accessed outside of your lan
location ~* \.(txt|log)$ {
allow 192.168.0.0/16;
deny all;
}

location ~ \..*/.*\.php$ {
return 403;
}

## Deny some crawlers
if ($http_user_agent ~* (HTTrack|HTMLParser|libwww) ) {
return 444;
}
## Deny certain Referers (case insensitive)
if ($http_referer ~* (poker|sex|girl) ) {
return 444;
}
## www. redirect
if ($host = 'pcwintech.com' ) {
rewrite ^/(.*)$ http://www.pcwintech.com/$1 permanent;
}


##
## required only when using purl, spaces & og for modules: ajax_comments, watcher and fasttoggle
## the /og path should be modified to match your default for og/purl URL for organic groups
##
location ~* ^/og {
rewrite ^/og\-(.*)/ajax_comments/(.*)$ /index.php?q=ajax_comments/$2 last;
rewrite ^/og\-(.*)/context/ajax-block-view$ /index.php?q=context/ajax-block-view last;
rewrite ^/og\-(.*)/comment/reply/(.*)\?reload=1$ /index.php?q=comment/reply/$2&reload=1 last;
rewrite ^/og\-(.*)/node/([0-9]+)/toggle/(.*)$ /index.php?q=node/$2/toggle/$3 last;
rewrite ^/og\-(.*)/node/([0-9]+)/edit\?(.*)$ /index.php?q=node/$2/edit?$3 last;
rewrite ^/og\-(.*)/user/([0-9]+)/watcher/toggle/(.*)$ /index.php?q=user/$2/watcher/toggle/$3 last;
rewrite ^/(.*)$ /index.php?q=$1 last;
}

## 6.x starts
location / {
deny 1.2.3.4;
deny 83.228.199.228;
deny 194.8.75.141;
deny 84.122.26.246;
deny 194.8.75.0/24;
deny 194.8.74.0/24; 
#rewrite ^/(.*)/$ /$1 permanent; # remove trailing slashes - disabled
try_files $uri @cache;
}

location @cache {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @drupal;
add_header Expires "Tue, 24 Jan 1984 08:00:00 GMT"; 
add_header Cache-Control "must-revalidate, post-check=0, pre-check=0";
add_header X-Header "Boost Citrus 1.9"; 
charset utf-8;
try_files /cache/normal/$host${uri}_$args.html /cache/$host${uri}_$args.html @drupal;
}

location @drupal {
###
### now simplified to reduce rewrites
###
rewrite ^/(.*)$ /index.php?q=$1 last;
}

location ~* (/\..*|settings\.php$|\.(htaccess|engine|inc|info|install|module|profile|pl|po|sh|.*sql|theme|tpl(\.php)?|xtmpl)$|^(Entries.*|Repository|Root|Tag|Template))$ {
deny all;
}

location ~* /files/.*\.php$ {
return 444;
}
location ~* /themes/.*\.php$ {
return 444;
}

location ~ \.css$ {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @uncached;
access_log off;
expires max; #if using aggregator
add_header X-Header "Boost Citrus 2.1";
try_files /cache/perm/$host${uri}_.css /cache/$host${uri}_.css $uri =404;
}

location ~ \.js$ {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @uncached;
access_log off;
expires max; # if using aggregator
add_header X-Header "Boost Citrus 2.2"; 
try_files /cache/perm/$host${uri}_.js /cache/$host${uri}_.js $uri =404;
}

location ~ \.json$ {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @uncached;
access_log off;
expires max; # if using aggregator
add_header X-Header "Boost Citrus 2.3"; 
try_files /cache/normal/$host${uri}_.json /cache/$host${uri}_.json $uri =404;
}

location @uncached {
access_log off;
expires max; # max if using aggregator, otherwise sane expire time
}

location ~* /files/imagecache/ {
access_log off;
try_files $uri @drupal; #imagecache support - now it works
}

location ~* ^.+\.(jpg|jpeg|gif|png|ico)$ {
access_log off;
expires 30d;
try_files $uri =404;
}

location ~* \.xml$ {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @drupal;
add_header Expires "Tue, 24 Jan 1984 08:00:00 GMT";
add_header Cache-Control "must-revalidate, post-check=0, pre-check=0";
add_header X-Header "Boost Citrus 2.4"; 
charset utf-8;
types { }
default_type application/rss+xml;
try_files /cache/normal/$host${uri}_.xml /cache/normal/$host${uri}_.html /cache/$host${uri}_.xml $uri @drupal;
}

location ~* /feed$ {
if ( $request_method !~ ^(GET|HEAD)$ ) {
return 405;
}
if ($http_cookie ~ "DRUPAL_UID") {
return 405;
}
error_page 405 = @drupal;
add_header Expires "Tue, 24 Jan 1984 08:00:00 GMT";
add_header Cache-Control "must-revalidate, post-check=0, pre-check=0";
add_header X-Header "Boost Citrus 2.5"; 
charset utf-8;
types { }
default_type application/rss+xml;
try_files /cache/normal/$host${uri}_.xml /cache/normal/$host${uri}_.html /cache/$host${uri}_.xml $uri @drupal;
}

#######################################################
### nginx.conf catch-all
#######################################################

A lot of the code in the config file already has explanations for them, so I wont cover all of them..

location ~ \.(gif|jpg|jpeg|png|tif|bmp|jpe)$ {

valid_referers server_names none blocked ~(pcwintech.com|google.|simpleportforwarding.com);

if ($invalid_referer) {

rewrite ^ http://$host/showimage?file=${uri} permanent;
}

}

location ~ \.(css|exe|zip|reg|vbs)$ {

valid_referers server_names none blocked ~(pcwintech.com|google.|simpleportforwarding.com);

if ($invalid_referer) {

rewrite ^ http://$host? permanent;
}

}

These prevent hot linking to the site. For the Pictures I have them being redirected to a showimage page on the site. I have allowed my sites and goole access to them. All others will be redirected. On the zip and exe files they will be redirected to the sites home page instead.

You will notice ~(pcwintech.com|google.|simpleportforwarding.com) this allows for all sub domains of my site in. like forums.pcwintech.com and www.pcwintech.com On the google one this allows all subdomains and main domains like google.com or google.uk

## www. redirect
if ($host = 'pcwintech.com' ) {
rewrite ^/(.*)$ http://www.pcwintech.com/$1 permanent;
}

This will redirect to the www part of the site. so if a user comes to pcwintech.com they will be redirected to www.pcwintech.com

## 6.x starts
location / {
deny 1.2.3.4;
deny 83.228.199.228;
deny 194.8.75.141;
deny 84.122.26.246;
deny 194.8.75.0/24;
deny 194.8.74.0/24; 
#rewrite ^/(.*)/$ /$1 permanent; # remove trailing slashes - disabled
try_files $uri @cache;
}

this section is used for boost, but also where I put the deny IPs rules. As you see deny 83.228.199.228; will block that IP where deny 194.8.75.0/24; will block the whole range of IPs. This config file should work as is for you. Make sure to change the domain in the config file to yours. This is where drupal is the top level domain, has boost enabled and clean urls. After this config the performance picked up a good amount and has been running very smooth. --Shane 17:14, 25 November 2010 (UTC)

MediaWiki

MediaWiki is a popular wiki software running this wiki and many others. It was developed by the founders of Wikipedia - which continues to use and maintain the software today. It is available for free and an open-source project. I moved a MediaWiki 1.17.0 site (using Clean URLs) off of Apache to nginx. First, create an mediawiki.conf file in the appropriate directory:

/home/YOURUSER/nginx/example.com/mediawiki.conf
location / {
        try_files $uri $uri/ /index.php;
    }
	
location /cache {
        deny  all;
    }
location ~* ^.+\.(js|css|png|jpg|jpeg|gif|ico)$ {
        expires max;
        log_not_found off;
        access_log off;
    }
location /dumps {
        root /home/YOURUSER/example.com/local;
        autoindex on;
    }
### Dreamhost analog stats
if ($request_uri ~* ^/(stats|failed_auth\.html).*$)
{
	break;
}

--Varnent 21:28, 24 July 2011 (PDT)


phpBB

Increase FastCGI Timeout

Put this in a .conf file as described above

fastcgi_read_timeout 120;

Source: https://www.phpbb.com/community/viewtopic.php?f=46&t=1778165#p10746575

Sending Mass E-Mail Settings

If you want to send mass emails with SMTP authentication you have to use POP-BEFORE-SMTP as the "Authentication method for SMTP".

JHeckman (talk) 22:51, 25 January 2013 (PST)

Password Protecting Directories

Unfortunately, the Htaccess / WebDAV section of the webpanel doesn't work with nginx -- including the password protection bit. Fortunately, that doesn't mean you can't password protect directories! You just have to do it the old fashioned way. First, create a basic_auth.conf file in the appropriate directory:

/home/YOURUSER/nginx/example.com/basic_auth.conf

Then add the following content:

location / {
  auth_basic "Restricted";
  auth_basic_user_file /home/YOURUSER/example.com/.htpasswd;
}

The auth_basic parameter is just the title of the prompt the user is hit with. The auth_basic_user_file parameter specifies where the password file is. This password file is the same sort Apache uses. Now, you need to actually create that file! Run this:

htpasswd -c /home/YOURUSER/example.com/.htpasswd LOGIN

Where LOGIN is the username you want to be used to authenticate as. After typing that command you'll be prompted to enter a password and then confirm that password like this:

New password: 
Re-type new password: 
Adding password for user LOGIN

At this point, reload the nginx config as discussed previously and you should start getting prompted when you try browsing to that domain. As usual, you can specify subdirectories be protected as well:

location /subdirectory/ {
  auth_basic "Restricted";
  auth_basic_user_file /home/YOURUSER/example.com/.htpasswd;
}

If you are using PHP in that directory, you will also need to add the following to allow .php files to be password protected:

location ~ ^/.+\.php$ {
 auth_basic "Restricted";
 auth_basic_user_file /home/YOURUSER/example.com/.htpasswd;
}

To add new passwords or change existing ones, just use this command:

htpasswd /home/YOURUSER/example.com/.htpasswd LOGIN

The -c parameter is only necessary if you need to create the file. Once it exists you no longer need that parameter. If you use an existing login it will change the password to the new one you enter.

Redirecting Domains

I used this to redirect a domain's additional domain extensions to the primary domain extension. First, create an domainredirects.conf file in the appropriate directory:

/home/YOURUSER/nginx/example.com/domainredirects.conf

All of the files you create in that directory get loaded in the SERVER block of the default nginx.conf (/dh/nginx/servers/httpd-pXXXXXX/nginx.conf). So there is no need to alter the default .conf file for redirects.

if ($host = "(example.com|example.net|example2.com)" ) {
		rewrite ^/(.*)$ http://www.example.com/$1 permanent;
	}

--Varnent 00:33, 25 July 2011 (PDT)

Redirecting Single Files

if ($request_filename ~ oldfile.html){
	rewrite ^ http://mydomain.com/newfile.php? permanent;
}

A more efficient (but slightly less flexible) alternative is:

location /oldfile.html { return 301 $scheme://$server_name/newfile.php$request_uri; }

Blocking IPs

Sometimes your site starts getting hit a ton by some abusive IP and you end up wanting to block it. Here's the nginx way to do that. First, create an access.conf file in the appropriate directory:

/home/YOURUSER/nginx/example.com/access.conf

Then add the following content:

location / {
  deny 1.2.3.4;
}

That line will block the 1.2.3.4 IP from accessing your site entirely. If you want to block it from a subdirectory, you would do this:

location /subdirectory/ {
  deny 1.2.3.4;
}

If you want to block access to all IPs with some exceptions, you would do this:

location / {
  allow 9.8.7.6;
  deny all;
}

It defaults to allowing all non-specified IPs (unless there's a deny all, of course). You can create multiple sets of these rules in your access.conf file:

location / {
  allow 9.8.7.6;
  deny all;
}

location /subdirectory/ {
  allow all;
}

The above would allow 9.8.7.6 to browse your entire site. All other IPs would be blocked from everywhere in your site except for /subdirectory which everyone could view.

Gzip Compression

By default, gzip compression is enabled. If you want to disable them for a domain, then create a settings.conf file in the appropriate directory:

/home/YOURUSER/nginx/example.com/settings.conf

You could create one specifically named gzip.conf if you wanted, but for simple settings like this, you might want to dump them all into one generic file. Add the following contents to the conf file you created:

gzip off;

That's it! As usual, don't forget to reload nginx. There are additional gzip compression options you can set that are all detailed here.

Troubleshooting

Common Problems:

  • If none of your website are coming back up after flipping the switch in the Dreamhost control panel to Nginx, it may be because the Nginx setup did not complete properly. In my case, when attempting to start Nginx from the root user admin command line:

$ sudo /etc/init.d/nginx start

It failed saying it could not find the nginx.conf configuration file. Turns out the automated configuration process had created it, but for some reason, had not copied it over from the temporary file "nginx.conf.pushing" which was under /dh/nginx/servers/httpd-<your VPS name>/. A quick "cp nginx.conf.pushing nginx.conf" and then a "sudo /etc/init.d/nginx restart" and up she came.
  • As stated earlier in this page, Nginx starts up helper processes for each username. If you have websites on a Dreamhost VPS *and* a shared server, the automated setup script will create "server" entries for all your user, regardless if they are on the VPS or not. In my case, I had one user with a few websites on the VPS and 15+ users on a shared server and it started up process for all of them. You can fix this by going into your nginx.conf (as root user) and removing all the "server" sections that are for users not on your VPS.

$ sudo /etc/init.d/nginx reload

External Links

WordPress-related

Drupal-related