Using Django with FastCGI
Posted by on 02 July 2012 10:37 AM
|
|
This is to be used as a reference only. Please check out our up-to-date article using the most recent technology and processes: https://help.asmallorange.com/index.php?/Knowledgebase/Article/View/305/0/installing-django-using-virtualenv. Using Django on ASO with FastCGIIntroductionAfter much looking around at various resources and my experience on getting Django FCGI working, I thought I would post an up-to-date guide on getting Django working with ASO. Hopefully this guide will be a benefit for the ASO community.This guide will be aimed towards Tiny account holders, but to anyone else who has more storage to play with, they can tweak some of the steps to their liking. This guides differs in such that the setup is as close to the recommended setup on Django's deployment page for Running Django on a shared-hosting provider with Apache. AssumptionsThis guide assumes that the reader is familiar with Linux and its basic commands, a terminal, SSH, and have basic programming knowledge, preferably (hopefully) in Python. If you are confused at this point about what I am talking about, then it may be a good idea to read up on what all of this is so that you don't feel like a deer in the headlights as you proceed. Additionally, knowing a decent text editor (emacs, vim, nano, etc) is a must.I won't go through a super detailed tutorial on some of these "basic" things such as logging into your account through SSH, changing to every single directory, and anything similar. If something is severely left out or makes the guide a complete loss, please edit where necessary. RequirementsTo perform anything that will be shown in the rest of this guide you must have shell/ssh access on your account. This can be done by submitting a support request.Django is not really picky on what version Python you are using since the core components require anything between 2.4-2.7. However, any modules from the django.contrib package may require more recent versions of Python. I would highly recommend either Python2.6 or Python2.7 since that is better supported overall by Django and any other contributing modules. You may request a particular version to be installed by submitting a ticket. You should not request Python3.x installed since Django does not support this version due to backwards compatibility support from Python. More information can be found at the Django install faq for the curious. If you plan on using MySQL as your database back-end, you might as well submit a ticket for the MySQLdb module for the version of Python that you have installed or requested. PreparationWhile you are waiting for your support ticket(s) to be resolved or if they are done already, we can take care of these next steps that don't require the packages being installed. If you don't have shell/ssh access, then I guess just sit tight.First, we will create a directory where we will store Python packages/modules that we will be installing or symlink'ing to. You may set up your directories wherever you like, just make sure to keep that in mind through the rest of the guide when setting up environment variables and when I refer to this directory. I prefer to create a directory structure similar to "/usr/local" in my home directory: mkdir -p ~/local/lib/python2.X/site-packages or /home/username/local/lib/python2.x/site-packages for the full path. Replace "X" with your Python version that is (will be installed). To set up your shell/ssh environment, we will edit your .bashrc and .bash_profile. The aliases and environment variables set in these files will make working with your Python and Django installs through the SSH simpler. First, open up .bashrc and add the following line: alias python='/usr/local/bin/python2.X'or alias python='/your/path/to/python2.x'
Replace "X" with your Python version that is (will be) installed. This will execute the correct Python version you wish to use whenever you run "python" on the command line for the interpreter or when running scripts. Now open .bash_profile to set up two environment variables so that commands become available on the command line once Django is installed and to add to the path where Python looks for installed packages/modules. Please add the following two lines: export PATH=$PATH:$HOME/local/lib/python2.X/site-packages/django/bin
export PYTHONPATH=$PYTHONPATH:$HOME/local/lib/python2.X/site-packages You will then need to logout/re-login SSH for the bash changes to take effect or run the following commands. source ~/.bashrc Tickets Resolved & Prep-Work Now Done?Lets take a quick break and test what we have done thus far.
source ~/.bash_profile
source ~/.bashrc Now you should be able to execute "python" and see something similar: [email protected] [~]# python
Python 2.6.2 (r262:71600, Aug 5 2009, 13:32:15) [GCC 4.1.2 20080704 (Red Hat 4.1.2-44)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>>
To install Python libraries you should use pip and the --prefix option. pip install --prefix="/home/username/local/lib/$library_name/"
Installing DjangoThere are two typical ways of installing Django: Release or latest development version. Which to choose? I have always used the development version and have never had any problems. You could also download the latest release tarball too. If you do decide to use the tarball release, just keep in mind some of these steps are irrelevant and/or different.Now Tiny accounts are only limited to 75Mb of space and performing a regular Subversion checkout takes just over 74Mb of space. Unacceptable. Seems like we are hosed, right? Luckily, we can export just the folder and set of files we need to get Django up and running. The rest of the checkout has a lot of bloat for keeping all the revision history, documentation, etc that is entirely unnecessary and can be found online where you can browse the source. This leaves the Django code at approximately 19Mb; definitely beats ~74Mb :D. Ready? Great! So now lets install django into that site-packages directory we created earlier: Django recently switched from svn to git so the installation has changed.
cd ~/local/lib/python2.x/site-packages ln -s django-install/django django
This will export the core django-install code into the "site-package" directory then symlink the django directory above so the paths work correctly. To test that you can use Django properly you should execute and see the following: [email protected] [~/]# django-admin.py
Type 'django-admin.py help' for usage. [email protected] [~/]# python Python 2.6.2 (r262:71600, Aug 5 2009, 13:32:15) [GCC 4.1.2 20080704 (Red Hat 4.1.2-44)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import django >>> This is good, close out of the interpreter and Django is installed. However, if something goes wrong: [email protected] [~/]# django-admin.py
-jailshell: django-admin.py: command not found # or >>> import django Traceback (most recent call last): File "<stdin>", line 1, in <module> ImportError: No module named django >>> or run 'python -c "import django"'
Check in .bash_profile that your PATH includes the where the django/bin directory is and that your PYTHONPATH includes the directory in which the ./django directory is located. If your .bash_profile appears correct, check the actual environment: echo $PATH
echo $PYTHONPATH or if you get 'ImportError: No module named importlib' Then run 'pip install importlib' as root (or open support ticket and we can install it) then try running django-admin.py again as user. Create a Django ProjectNow, I won't go through all the steps of starting off your Django project, but I will do the bare minimum to get the basics up and running. Now I prefer to have a directory that holds my Django project, media folder, scripts, and templates:cd ~/
mkdir website cd website # replace 'myproj' with whatever your project name django-admin.py startproject myproj # this is up to you, but it is nice to keep everything contained mkdir media mkdir scripts mkdir templates # we now have # ~/website # ./media # ./mpyroj # ./scripts # ./templates The last things that needs to get done is create a symlink to your project in the ./site-packages directory so Python know where to find your project. Remember: we added the ./site-packages to our PYTHONPATH so Python knows where to find everything; nice! cd ~/local/lib/python2.6/site-packages
ln -s ~/website/myproj Quick check that we can import our project in Python: python
Python 2.6.2 (r262:71600, Aug 5 2009, 13:32:15) [GCC 4.1.2 20080704 (Red Hat 4.1.2-44)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import myproj >>> or run 'python -c "import myproj"'
No import errors? Great, lets move on! Install FlupRecall the link referencing how Django is preferred to be installed in the beginning? Well, using FCGI the "Django way" requires Flup to be installed. It may be a good idea to check the Flup website to see what the latest release is.cd ~/
wget http://www.saddi.com/software/flup/dist/flup-1.0.2.tar.gz tar xzvf flup-1.0.2.tar.gz cd flup-1.0.2 cp -r flup ~/local/lib/python2.6/site-packages/ Quick check that we can import flup in Python: python
Python 2.6.2 (r262:71600, Aug 5 2009, 13:32:15) [GCC 4.1.2 20080704 (Red Hat 4.1.2-44)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import flup >>> or run 'python -c "import flup"'
No import errors? Great, lets move on! FCGI on Shared HostingWe are almost at the end of our journey. First we need to create a simple FCGI program in our ~/public_html that will be executed that will dispatch web requests to your Django site. First create/open a file in your favorite editor "dispatch.fcgi" in your ~/public_html directory:#!/usr/local/bin/python2.6
import sys import os # Make sure to change 'username' to your username! sys.path.insert(0, '/home/username/local/lib/python2.6/site-packages') os.environ['DJANGO_SETTINGS_MODULE'] = 'myproj.settings' from django.core.servers.fastcgi import runfastcgi runfastcgi(method="threaded", daemonize="false") A few things to note. Replace the first line to where your python2.X is installed. You can check by executing `which python2.X` in case you aren't sure. Change the "username" to your login name. Finally, change "myproj.settings" to your "yourprojname.settings". You can add additional FCGI settings to the runfastcgi call in the last line. One of the most useful for development is debug="true" which provides debug information before django's debugging machinery has loaded. You can see all settings in django.core.servers.fastcgi. Also we need to make sure that this file is executable so that it can be run by Apache: chmod 755 dispatch.fcgi
We can test the script by running: ./dispatch.fcgi
You should see HTML output the console! If so, we are in good shape. If something goes wrong, make sure that FCGI is working by looking at the Testing FastCGI on this ASO wiki page for making sure FCGI is working on your shared hosting. Modify .htaccessIn your ~/public_html directory, we just need to modify the .htaccess file so that web requests are dispatched to your dispatch.fcgi script.Open up ~/public_html/.htaccess and the entire file should be: AddHandler fcgid-script .fcgi RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^(.*)$ dispatch.fcgi/$1 [QSA,L] Here is an explanation of what this is doing. The comments in the code below will cause an error, so use the one above. AddHandler fcgid-script .fcgi # use fast-script to execute our .fcgi file RewriteEngine On # rewrite url request enabled RewriteCond %{REQUEST_FILENAME} !-f # if the FILENAME requested isn't an actual file, perform the next command RewriteRule ^(.*)$ dispatch.fcgi/$1 [QSA,L] # send requested urn to the dispatch.fcgi to be processed Test your new WebsiteGo to http://www.yourwebsite.com!Hopefully you should see the Django welcome page because you haven't created anything yet on your site. Enjoy! When you make changes to your code and would like to see them on your site, just update the timestamp of your dispatch.fcgi file and Apache will restart your Django application for you. touch mysite.fcgi
Admin MediaIf you run into trouble with media not showing up in the admin side of your app (no css, images, etc), you may need to link to them from your site's document root:
$ ln -s /home/username/local/lib/python2.x/site-packages/django/contrib/admin/media media
More info from the official Django documentation here:
ConclusionI hope this guide is helpful and that the ASO community may benefit from this wealth of information.NotesTo make sure no one else on your shard hosting server can view your password in your project's [i]./settings.py[/i] file, we should change the permissions so only you can view and edit this file:chmod 600 ~/website/myproj/settings.py
| |
|