Django setup notes

This might be helpful if you're new to Django and figuring out how to develop and deploy it effectively.

I tend to keep my projects together in a subversion repository, which means I like everything in one place. I develop locally, and then deployment consists of svn update on the remote server. I generally lay things out like below.

/var/www/project
|-- db
|-- django
|   `-- project
|       |-- __init__.py
|       |-- application
|       |   |-- __init__.py
|       |   |-- models.py
|       |   |-- views.py
|       |-- manage.py
|       |-- settings.py
|       |-- urls.py
|-- media
|   |-- admin
|   |   `-- media -> /usr/share/python-support/python-django/django/contrib/admin/media/
|   |-- images
|   |   `-- something.png
|   |-- blah.css
`-- www
    |-- base.html
    |-- application
        |-- something.html
  • db stores a SQLite DB -- generally enough for me but of course you can use a "real" database. Because my projects are small, a database backup then consists of a svn ci. You need to make sure the web server has permissions to this. As a hack I link /var/www/project/db/dbfile.db into my local development tree, which generally isn't under /var/www/. This makes it easier to deploy.
  • django holds generated stuff, views, models, etc. Run django-admin.py in this directory. Apps live underneath it too.
  • media stores static media. I use the Debian packages, so link into the default store for the admin media files, and setup ADMIN_MEDIA_PREFIX in settings.py to be /media/admin/.
  • www holds the HTML templates.

I then setup Apache with a snippet like

DocumentRoot /var/www/project

<Location "/">
         SetHandler python-program
             PythonHandler django.core.handlers.modpython
             PythonPath "['/var/www/project/django'] + sys.path"
             SetEnv DJANGO_SETTINGS_MODULE project.settings
             PythonDebug On
</Location>

Alias /media /var/www/project/media
<Location "/media">
         SetHandler none
</Location>
<Directory "/var/www/project/media">
          AllowOverride none
              Order allow,deny
              Allow from all
              Options FollowSymLinks Indexes
</Directory>

This lets Apache serve up the static files, which it obviously does well. The only other trick is getting the Django server to serve up the static stuff when I'm developing with it locally. I add the following to the bottom of urls.py

if "GATEWAY_INTERFACE" not in os.environ:
    urlpatterns += patterns('',
            (r'^media/(?P<path>.*)$', 'django.views.static.serve', {'document_root': '/path/to/local/dev/project/media/'}),
                )

This makes sure it only serves when it is not running under mod_python.