Useful NGINX configurations for Rails app

Nginx is now becoming the favorable choice of many Rails developers when deploying the Rails app. It is lightweight, fast and has almost everything we need. In this post, I am going to introduce a few useful configs which I often use in Rails app.

1. Redirect www to non-www or vice-versa

Usually, it is better to use 1 consistent domain for your website to improve your site's SEO as well as user awareness. Here is the config for redirecting all www request to non-www request.

server {
#listen 80 is default
server_name www.example.com;
return 301 $scheme://example.com$request_uri;
}
server {
    #listen 80 is default
    server_name example.com;
    ## here goes the rest of your conf...
}

2. Add caching header to assets (images, javascripts, stylesheets)

By default, browser will have to download all these assets everytime we refresh the page. It is inefficient because they do not change very often. Therefore, those assets should be cached on browser to prevent reloading. This in hence makes your website faster.

location ~* ^.+.(jpg|jpeg|gif|css|png|js|ico|xml)$ {
  access_log        off;
  expires           15d; #expire after 15 days
}

3. HTTP Basic authentication

If you want to limit the access of your website to a few users (perhaps you are doing a alpha test), HTTP basic is the best way to do that. We can also use HTTP Basic Authentication in Rails code but it requires new deployment of the app (sometimes we have to use Rails code because we don't have access to nginx configuration).
There are a few steps in Nginx, but they are all very simple

  1. create authentication file which keeps username and password in the following format

    username1:password1
    username2:password2
    
  2. add nginx config

    location / {
        auth_basic           "closed site";
        auth_basic_user_file conf/htpasswd; #adjust the path to your own auth file
    }
    

4. Maintenance page

In this config, if I want to take off my site and show maintenance page to all users, I can easily create new file called maintenance.html in public folder and Nginx will redirect all requests to this static page. This is very handy because we don't have to create a custom maintenance page in our app and deploy the app again.

server {
        listen      80;
        server_name mysite.com;
        root    /var/www/mysite.com/;

        location / {
            if (-f $document_root/public/maintenance.html) {
                return 503;
           }
            ... # the rest of your config goes here
         }

        error_page 503 @maintenance;
        location @maintenance {
                rewrite ^(.*)$ /maintenance.html break;
        }
}

Reference: https://lincolnloop.com/blog/pro-tip-redirecting-custom-nginx-maintenance-page/

What are your frequently used config? Share your thought and let's discuss.

Happy coding