fastcgi.txt 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381
  1. .. _howto-deployment-fastcgi:
  2. ============================================
  3. How to use Django with FastCGI, SCGI, or AJP
  4. ============================================
  5. .. highlight:: bash
  6. Although the current preferred setup for running Django is :ref:`Apache with
  7. mod_python <howto-deployment-modpython>`, many people use shared hosting, on
  8. which protocols such as FastCGI, SCGI or AJP are the only viable options. In
  9. some setups, these protocols also allow better security -- and, possibly, better
  10. performance -- than mod_python_.
  11. .. admonition:: Note
  12. This document primarily focuses on FastCGI. Other protocols, such as SCGI
  13. and AJP, are also supported, through the ``flup`` Python package. See the
  14. Protocols_ section below for specifics about SCGI and AJP.
  15. Essentially, FastCGI is an efficient way of letting an external application
  16. serve pages to a Web server. The Web server delegates the incoming Web requests
  17. (via a socket) to FastCGI, which executes the code and passes the response back
  18. to the Web server, which, in turn, passes it back to the client's Web browser.
  19. Like mod_python, FastCGI allows code to stay in memory, allowing requests to be
  20. served with no startup time. Unlike mod_python_ (or `mod_perl`_), a FastCGI
  21. process doesn't run inside the Web server process, but in a separate,
  22. persistent process.
  23. .. _mod_python: http://www.modpython.org/
  24. .. _mod_perl: http://perl.apache.org/
  25. .. admonition:: Why run code in a separate process?
  26. The traditional ``mod_*`` arrangements in Apache embed various scripting
  27. languages (most notably PHP, Python and Perl) inside the process space of
  28. your Web server. Although this lowers startup time -- because code doesn't
  29. have to be read off disk for every request -- it comes at the cost of
  30. memory use. For mod_python, for example, every Apache process gets its own
  31. Python interpreter, which uses up a considerable amount of RAM.
  32. Due to the nature of FastCGI, it's even possible to have processes that run
  33. under a different user account than the Web server process. That's a nice
  34. security benefit on shared systems, because it means you can secure your
  35. code from other users.
  36. Prerequisite: flup
  37. ==================
  38. Before you can start using FastCGI with Django, you'll need to install flup_, a
  39. Python library for dealing with FastCGI. Version 0.5 or newer should work fine.
  40. .. _flup: http://www.saddi.com/software/flup/
  41. Starting your FastCGI server
  42. ============================
  43. FastCGI operates on a client-server model, and in most cases you'll be starting
  44. the FastCGI process on your own. Your Web server (be it Apache, lighttpd, or
  45. otherwise) only contacts your Django-FastCGI process when the server needs a
  46. dynamic page to be loaded. Because the daemon is already running with the code
  47. in memory, it's able to serve the response very quickly.
  48. .. admonition:: Note
  49. If you're on a shared hosting system, you'll probably be forced to use
  50. Web server-managed FastCGI processes. See the section below on running
  51. Django with Web server-managed processes for more information.
  52. A Web server can connect to a FastCGI server in one of two ways: It can use
  53. either a Unix domain socket (a "named pipe" on Win32 systems), or it can use a
  54. TCP socket. What you choose is a manner of preference; a TCP socket is usually
  55. easier due to permissions issues.
  56. To start your server, first change into the directory of your project (wherever
  57. your :ref:`manage.py <ref-django-admin>` is), and then run the
  58. :djadmin:`runfcgi` command::
  59. ./manage.py runfcgi [options]
  60. If you specify ``help`` as the only option after :djadmin:`runfcgi`, it'll
  61. display a list of all the available options.
  62. You'll need to specify either a ``socket``, a ``protocol`` or both ``host`` and
  63. ``port``. Then, when you set up your Web server, you'll just need to point it at
  64. the host/port or socket you specified when starting the FastCGI server. See the
  65. examples_, below.
  66. Protocols
  67. ---------
  68. Django supports all the protocols that flup_ does, namely fastcgi_, `SCGI`_ and
  69. `AJP1.3`_ (the Apache JServ Protocol, version 1.3). Select your preferred
  70. protocol by using the ``protocol=<protocol_name>`` option with ``./manage.py
  71. runfcgi`` -- where ``<protocol_name>`` may be one of: ``fcgi`` (the default),
  72. ``scgi`` or ``ajp``. For example::
  73. ./manage.py runfcgi protocol=scgi
  74. .. _flup: http://www.saddi.com/software/flup/
  75. .. _fastcgi: http://www.fastcgi.com/
  76. .. _SCGI: http://python.ca/scgi/protocol.txt
  77. .. _AJP1.3: http://tomcat.apache.org/connectors-doc/ajp/ajpv13a.html
  78. Examples
  79. --------
  80. Running a threaded server on a TCP port::
  81. ./manage.py runfcgi method=threaded host=127.0.0.1 port=3033
  82. Running a preforked server on a Unix domain socket::
  83. ./manage.py runfcgi method=prefork socket=/home/user/mysite.sock pidfile=django.pid
  84. Run without daemonizing (backgrounding) the process (good for debugging)::
  85. ./manage.py runfcgi daemonize=false socket=/tmp/mysite.sock maxrequests=1
  86. Stopping the FastCGI daemon
  87. ---------------------------
  88. If you have the process running in the foreground, it's easy enough to stop it:
  89. Simply hitting ``Ctrl-C`` will stop and quit the FastCGI server. However, when
  90. you're dealing with background processes, you'll need to resort to the Unix
  91. ``kill`` command.
  92. If you specify the ``pidfile`` option to :djadmin:`runfcgi`, you can kill the
  93. running FastCGI daemon like this::
  94. kill `cat $PIDFILE`
  95. ...where ``$PIDFILE`` is the ``pidfile`` you specified.
  96. To easily restart your FastCGI daemon on Unix, try this small shell script::
  97. #!/bin/bash
  98. # Replace these three settings.
  99. PROJDIR="/home/user/myproject"
  100. PIDFILE="$PROJDIR/mysite.pid"
  101. SOCKET="$PROJDIR/mysite.sock"
  102. cd $PROJDIR
  103. if [ -f $PIDFILE ]; then
  104. kill `cat -- $PIDFILE`
  105. rm -f -- $PIDFILE
  106. fi
  107. exec /usr/bin/env - \
  108. PYTHONPATH="../python:.." \
  109. ./manage.py runfcgi socket=$SOCKET pidfile=$PIDFILE
  110. Apache setup
  111. ============
  112. To use Django with Apache and FastCGI, you'll need Apache installed and
  113. configured, with `mod_fastcgi`_ installed and enabled. Consult the Apache
  114. documentation for instructions.
  115. Once you've got that set up, point Apache at your Django FastCGI instance by
  116. editing the ``httpd.conf`` (Apache configuration) file. You'll need to do two
  117. things:
  118. * Use the ``FastCGIExternalServer`` directive to specify the location of
  119. your FastCGI server.
  120. * Use ``mod_rewrite`` to point URLs at FastCGI as appropriate.
  121. .. _mod_fastcgi: http://www.fastcgi.com/mod_fastcgi/docs/mod_fastcgi.html
  122. Specifying the location of the FastCGI server
  123. ---------------------------------------------
  124. The ``FastCGIExternalServer`` directive tells Apache how to find your FastCGI
  125. server. As the `FastCGIExternalServer docs`_ explain, you can specify either a
  126. ``socket`` or a ``host``. Here are examples of both:
  127. .. code-block:: apache
  128. # Connect to FastCGI via a socket / named pipe.
  129. FastCGIExternalServer /home/user/public_html/mysite.fcgi -socket /home/user/mysite.sock
  130. # Connect to FastCGI via a TCP host/port.
  131. FastCGIExternalServer /home/user/public_html/mysite.fcgi -host 127.0.0.1:3033
  132. In either case, the file ``/home/user/public_html/mysite.fcgi`` doesn't
  133. actually have to exist. It's just a URL used by the Web server internally -- a
  134. hook for signifying which requests at a URL should be handled by FastCGI. (More
  135. on this in the next section.)
  136. .. _FastCGIExternalServer docs: http://www.fastcgi.com/mod_fastcgi/docs/mod_fastcgi.html#FastCgiExternalServer
  137. Using mod_rewrite to point URLs at FastCGI
  138. ------------------------------------------
  139. The second step is telling Apache to use FastCGI for URLs that match a certain
  140. pattern. To do this, use the `mod_rewrite`_ module and rewrite URLs to
  141. ``mysite.fcgi`` (or whatever you specified in the ``FastCGIExternalServer``
  142. directive, as explained in the previous section).
  143. In this example, we tell Apache to use FastCGI to handle any request that
  144. doesn't represent a file on the filesystem and doesn't start with ``/media/``.
  145. This is probably the most common case, if you're using Django's admin site:
  146. .. code-block:: apache
  147. <VirtualHost 12.34.56.78>
  148. ServerName example.com
  149. DocumentRoot /home/user/public_html
  150. Alias /media /home/user/python/django/contrib/admin/media
  151. RewriteEngine On
  152. RewriteRule ^/(media.*)$ /$1 [QSA,L,PT]
  153. RewriteCond %{REQUEST_FILENAME} !-f
  154. RewriteRule ^/(.*)$ /mysite.fcgi/$1 [QSA,L]
  155. </VirtualHost>
  156. .. _mod_rewrite: http://httpd.apache.org/docs/2.0/mod/mod_rewrite.html
  157. Django will automatically use the pre-rewrite version of the URL when
  158. constructing URLs with the ``{% url %}`` template tag (and similar methods).
  159. lighttpd setup
  160. ==============
  161. lighttpd_ is a lightweight Web server commonly used for serving static files. It
  162. supports FastCGI natively and, thus, is a good choice for serving both static
  163. and dynamic pages, if your site doesn't have any Apache-specific needs.
  164. .. _lighttpd: http://www.lighttpd.net/
  165. Make sure ``mod_fastcgi`` is in your modules list, somewhere after
  166. ``mod_rewrite`` and ``mod_access``, but not after ``mod_accesslog``. You'll
  167. probably want ``mod_alias`` as well, for serving admin media.
  168. Add the following to your lighttpd config file:
  169. .. code-block:: lua
  170. server.document-root = "/home/user/public_html"
  171. fastcgi.server = (
  172. "/mysite.fcgi" => (
  173. "main" => (
  174. # Use host / port instead of socket for TCP fastcgi
  175. # "host" => "127.0.0.1",
  176. # "port" => 3033,
  177. "socket" => "/home/user/mysite.sock",
  178. "check-local" => "disable",
  179. )
  180. ),
  181. )
  182. alias.url = (
  183. "/media" => "/home/user/django/contrib/admin/media/",
  184. )
  185. url.rewrite-once = (
  186. "^(/media.*)$" => "$1",
  187. "^/favicon\.ico$" => "/media/favicon.ico",
  188. "^(/.*)$" => "/mysite.fcgi$1",
  189. )
  190. Running multiple Django sites on one lighttpd
  191. ---------------------------------------------
  192. lighttpd lets you use "conditional configuration" to allow configuration to be
  193. customized per host. To specify multiple FastCGI sites, just add a conditional
  194. block around your FastCGI config for each site::
  195. # If the hostname is 'www.example1.com'...
  196. $HTTP["host"] == "www.example1.com" {
  197. server.document-root = "/foo/site1"
  198. fastcgi.server = (
  199. ...
  200. )
  201. ...
  202. }
  203. # If the hostname is 'www.example2.com'...
  204. $HTTP["host"] == "www.example2.com" {
  205. server.document-root = "/foo/site2"
  206. fastcgi.server = (
  207. ...
  208. )
  209. ...
  210. }
  211. You can also run multiple Django installations on the same site simply by
  212. specifying multiple entries in the ``fastcgi.server`` directive. Add one
  213. FastCGI host for each.
  214. Running Django on a shared-hosting provider with Apache
  215. =======================================================
  216. Many shared-hosting providers don't allow you to run your own server daemons or
  217. edit the ``httpd.conf`` file. In these cases, it's still possible to run Django
  218. using Web server-spawned processes.
  219. .. admonition:: Note
  220. If you're using Web server-spawned processes, as explained in this section,
  221. there's no need for you to start the FastCGI server on your own. Apache
  222. will spawn a number of processes, scaling as it needs to.
  223. In your Web root directory, add this to a file named ``.htaccess``:
  224. .. code-block:: apache
  225. AddHandler fastcgi-script .fcgi
  226. RewriteEngine On
  227. RewriteCond %{REQUEST_FILENAME} !-f
  228. RewriteRule ^(.*)$ mysite.fcgi/$1 [QSA,L]
  229. Then, create a small script that tells Apache how to spawn your FastCGI
  230. program. Create a file ``mysite.fcgi`` and place it in your Web directory, and
  231. be sure to make it executable:
  232. .. code-block:: python
  233. #!/usr/bin/python
  234. import sys, os
  235. # Add a custom Python path.
  236. sys.path.insert(0, "/home/user/python")
  237. # Switch to the directory of your project. (Optional.)
  238. # os.chdir("/home/user/myproject")
  239. # Set the DJANGO_SETTINGS_MODULE environment variable.
  240. os.environ['DJANGO_SETTINGS_MODULE'] = "myproject.settings"
  241. from django.core.servers.fastcgi import runfastcgi
  242. runfastcgi(method="threaded", daemonize="false")
  243. Restarting the spawned server
  244. -----------------------------
  245. If you change any Python code on your site, you'll need to tell FastCGI the
  246. code has changed. But there's no need to restart Apache in this case. Rather,
  247. just reupload ``mysite.fcgi``, or edit the file, so that the timestamp on the
  248. file will change. When Apache sees the file has been updated, it will restart
  249. your Django application for you.
  250. If you have access to a command shell on a Unix system, you can accomplish this
  251. easily by using the ``touch`` command::
  252. touch mysite.fcgi
  253. Serving admin media files
  254. =========================
  255. Regardless of the server and configuration you eventually decide to use, you
  256. will also need to give some thought to how to serve the admin media files. The
  257. advice given in the :ref:`modpython <serving-the-admin-files>` documentation
  258. is also applicable in the setups detailed above.
  259. Forcing the URL prefix to a particular value
  260. ============================================
  261. Because many of these fastcgi-based solutions require rewriting the URL at
  262. some point inside the webserver, the path information that Django sees may not
  263. resemble the original URL that was passed in. This is a problem if the Django
  264. application is being served from under a particular prefix and you want your
  265. URLs from the ``{% url %}`` tag to look like the prefix, rather than the
  266. rewritten version, which might contain, for example, ``mysite.fcgi``.
  267. Django makes a good attempt to work out what the real script name prefix
  268. should be. In particular, if the webserver sets the ``SCRIPT_URL`` (specific
  269. to Apache's mod_rewrite), or ``REDIRECT_URL`` (set by a few servers, including
  270. Apache + mod_rewrite in some situations), Django will work out the original
  271. prefix automatically.
  272. In the cases where Django cannot work out the prefix correctly and where you
  273. want the original value to be used in URLs, you can set the
  274. ``FORCE_SCRIPT_NAME`` setting in your main ``settings`` file. This sets the
  275. script name uniformly for every URL served via that settings file. Thus you'll
  276. need to use different settings files if you want different sets of URLs to
  277. have different script names in this case, but that is a rare situation.
  278. As an example of how to use it, if your Django configuration is serving all of
  279. the URLs under ``'/'`` and you wanted to use this setting, you would set
  280. ``FORCE_SCRIPT_NAME = ''`` in your settings file.