Running CherryPy behind Apache
This is a high-level discussion of the various ways to use CherryPy behind Apache. Individual HOWTO's are at:
When should you run your CherryPy app behind Apache?
The CherryPy HTTP server (before CherryPy 3.0.0 beta) doesn't support SSL out of the box (although there is a third-party module for it). So, if you have a simple website that doesn't have a really high traffic website (say, less than 50 hits/second) and if you don't need SSL, then running CherryPy exposed is fine. Otherwise, running it behind Apache is probably the right option for you.
What are the advantages?
- You can configure Apache to serve static files directly (and free CherryPy from doing this)
- You have access to all the mod_* modules from Apache. For instance:
- mod_ssl so Apache can handle SSL for you and CherryPy doesn't have to know about this (recipe here).
- mod_gzip if you want Apache to compress your pages instead of CherryPy (Apache is probably a bit faster at this)
- VirtualHosting/mod_rewrite/mod_proxy if you want to mix & match multiple sites. They can be served from the same CherryPy server or from multiple ones.
- all other mod_* modules ...
Are there any drawbacks?
I've been using this setup for many production websites for almost 4 years, some of them on Windows and some of them on Linux and quite frankly, I don't think there are any drawbacks. The only minor thing that I can think of is that you have to install Apache and learn how to configure it. But it is not very hard and it is worth it because Apache is truly a great webserver and you can take advantage of its numerous features.
Comparing the various methods
IMHO, the best way to do this is to use mod_rewrite. I've tried FastCGI and the performance is about the same but it is more complex to setup.
|interface to CherryPy||socket||socket||in-process||socket||socket|
|works with .htaccess||Y|
Getting the right Host header in CherryPy
One problem with this setup is that requests that arrive to CherryPy will look like they're coming from "localhost" (the "Host" header will say "localhost:port).
This is not a problem if you're only using relative or absolute URLs (the browser will do the right thing), but this is a problem if you're using canonical URLs (URLs that include the protocol and domain name) generated by CherryPy. This is also a problem if you want to issue a redirect because a redirect should include a canonical URL.
This is an especially important issue because CherryPy will create redirects for you in cases where the url is missing a final '/'. Redirecting users to http://127.0.0.1:8080/data/ when they typed in http://www.example.info/data is not likely to win you many friends.
If you are using Apache 2.0 and have control of your configuration, the easiest solution is to add the following in your (virtual) server's conf file:
If you also want newer Apache 1.x compatibility (works for 1.3.33) or you can't edit the Apache config file, the proxy tool will automatically use the X-Forwarded-Host header provided by Apache.
[/] tools.proxy.on: True
For earlier Apache 1.x installations, you need to explicitly set the proxy.base, which tells CherryPy to use a different "Host" header than the one coming from the request:
[/] tools.proxy.on: True tools.proxy.base: 'http://mydomain.com'
|replace this||with this|