• Sales: 1-800-961-2888
  • Support: 1-800-961-4454

Ubuntu - Apache Rails and Thin


Following from the Ubuntu Intrepid - Thin web server for Ruby article, let's look at creating and configuring Apache to proxy to thin so we can serve our Ruby on Rails application.

Contents

Prerequisites

To get the most out of this article you need to have a couple of things preinstalled:

Firstly, you need Apache installed Ubuntu Intrepid - Apache and PHP install - if you don't require PHP then please feel free to leave that section out.

Secondly, you will need to have thin installed - as mentioned above, please see the Ubuntu Intrepid - Thin web server for Ruby article for more details.

Rails application

To start with, we will need a basic Ruby on Rails application. Move into your public_html folder (create one if you do not have one already):

cd ~/public_html

Then create a Rails application. We'll use the default sqlite database for this example:

rails railsapp

Apache modules

Apache will need the proxy and rewrite modules enabled.

Depending on your Apache install you may need to issue all the following commands:

sudo a2enmod proxy
sudo a2enmod proxy_balancer
sudo a2enmod proxy_http
sudo a2enmod rewrite

Once done, reload Apache:

sudo /etc/init.d/apache2 force-reload

Apache Virtual Host

So what's the plan?

Well, for our simple application we'll set 3 thin instances running from port 5000 and in production mode.

Let's start off by creating the virtual host:

sudo nano /etc/apache2/sites-available/domain.com

The following will suffice for a basic application:

<VirtualHost *:80>
  ServerName domain.com
  ServerAlias www.domain.com

  DocumentRoot /home/demo/public_html/railsapp/public

  RewriteEngine On

  <Proxy balancer://thinservers>
    BalancerMember http://127.0.0.1:5000
    BalancerMember http://127.0.0.1:5001
    BalancerMember http://127.0.0.1:5002
  </Proxy>

  # Redirect all non-static requests to thin
  RewriteCond %{DOCUMENT_ROOT}/%{REQUEST_FILENAME} !-f
  RewriteRule ^/(.*)$ balancer://thinservers%{REQUEST_URI} [P,QSA,L]

  # Custom log file locations
  ErrorLog  /home/demo/public_html/railsapp/log/error.log
  CustomLog /home/demo/public_html/railsapp/log/access.log combined

</VirtualHost>

Nice and simple — what we are doing is rerouting (non-static) rails requests to a 3rd party server, in this case thin.

Enable

Don't forget to enable the vhost:

sudo a2ensite domain.com

And restart Apache:

sudo /etc/init.d/apache2 reload

If you get any port and NameVirtualHost errors then please read the Apache Virtual Host article which will take you through setting up said details.

Thin configuration

Next we need to configure thin on our application.

To kill two birds with one stone, we'll go straight into creating an init.d file so the thin servers are started on a Cloud Server reboot.

Remember we want 3 servers running sequentially from port 5000 in production mode:

sudo thin config -C /etc/thin/railsapp.yml -c /home/demo/public_html/railsapp/  --servers 3 -p 5000 -e production

Have a quick check of the file we created:

cat /etc/thin/railsapp.yml

the contents of which look good:

--- 
pid: tmp/pids/thin.pid
address: 0.0.0.0
timeout: 30
port: 5000
log: log/thin.log
max_conns: 1024
require: []

environment: production
max_persistent_conns: 512
servers: 3
daemonize: true
chdir: /home/demo/public_html/railsapp

Stating thin

Now we'ce created our init script, let's start it:

sudo /etc/init.d/thin start

The terminal output confirms the actions:

[start] /etc/thin/railsapp.yml ...
Starting server on 0.0.0.0:5000 ... 
Starting server on 0.0.0.0:5001 ... 
Starting server on 0.0.0.0:5002 ...

Cool.

Navigate

All that's left is to navigate to your domain:

http://www.domain.com

Where you will be greeted with the rails welcome page.

Restart

As we created an init script for the thin servers you can restart them in the normal way:

sudo /etc/init.d/thin restart

Summary

Setting up a virtual host to proxy to the thin web server is fairly simple.

Add to that the ease of installing and configuring thin, the whole process is very quick and powerful.



© 2011-2013 Rackspace US, Inc.

Except where otherwise noted, content on this site is licensed under a Creative Commons Attribution-NonCommercial-NoDerivs 3.0 Unported License


See license specifics and DISCLAIMER

6 Comments

The two lines starting with ProxyPass and ProxyPassReverse should be removed.
They completely negate the preceding RewriteRule and prevent precompiled assets from being served on a 3.2 rails app in production mode with default assets pipeline config.

Thanks Joel. I confess, I haven't worked with this setup myself, but it does look like you're correct. Should the ProxyPreserveHost directive remain or be removed as well?

I don't know if ProxyPreserveHost is really needed. I kept it in my config and it doesn't seem to hurt. Now that the server is live, I can't easily test if it changes something.

I made a few other changes that were important for me in the thin yml config file:
- changed the "address" line to 127.0.0.1 (instead of 0.0.0.0) so that the thin workers are not directly accessible from the outside
- added "user" and "group" lines so that thin does not run as root
- added "onebyone: true" to have (almost) rolling restarts.

Ok, I tried on a test server and both ProxyPreserveHost and the whole "<Proxy *>" block that follows seem useless. I didn't try on my production server yet.

Thanks again. This article was written about five years ago and in the time since no one appears to have brought up the ProxyPass issue. We definitely appreciate you catching it and letting us know about it.

You're welcome. I understand that it may have been needed in the past. I posted it because when I googled the problem I found other people having the same. I even found a Stackoverflow answer explaining that it's a common error repeated in many apache reverse proxy tutorials... So I thought it might be a good idea to report it to the place where I had found the tutorial that I used for myself, which is here.

Have a nice day, and thanks (from France) for the tutorial.

Add new comment