Lately I’ve been working on developing a web application project, I guess everyone involved in such process had to make the uneasy decision to choose the right Web Stack to run the application. Multiple factors usually drive the final decision,total cost of ownership (TCO), scalability, stability and performances. The TCO factor can be easy overcome with FLOSS (Free and open source software), scalability is a very broad term and concept that doesn’t have any clear answer. Stability can be achieved with software that is widely used and widely reviewed and tested for a long time, never pick something new just because it’s cool. Doesn’t matter if the website serve millions of users or just a few hundred, slow or bad performances can make the user experience a nightmare. Performance enhancement can be achieved with, Memory caching system, Low memory footprint web servers, good and slim database design, query optimization to work under heavy loads. Please be aware that applications, services and workloads differ from case to case, you might need more write capacity rather than read, serving multimedia files or whatever else, don’t blame me if you have troubles with your production application after following this how-to. For me and some other, this setup works quite well, I hope the same for you
.
This tutorial covers the set up a free, full-featured web development framework based on Ubuntu Server 12.04(LTS), Django 1.4 stable, Postgresql database V. 9.1, Nginx web server V.1.1.19 and Gunicorn.
Ubuntu Server
Linux for high-volume server workloads
http://www.ubuntu.com/business/server/overview
Django
The web framework for perfectionists with deadlines
www.djangoproject.com
Postgresql
A powerful, open source object-relational database system.
http://www.postgresql.org
Nginx
A web server with a strong focus on high concurrency, performance and low memory usage.
http://wiki.nginx.org/Main
Gunicorg
A WSGI HTTP Server, the link between Django an Nginx.
http://gunicorn.org/
Postgresql installation and setup
apt-get install postgresql python-psycopg2 sudo -u postgres psql template1 ALTER USER postgres with encrypted password 'a_strong_password'; template1=# CREATE DATABASE test; template1=# CREATE USER test WITH PASSWORD 'test'; template1=# GRANT ALL PRIVILEGES ON DATABASE test to test;
In /etc/postgresql/9.1/main/pg_hba.conf
Change
local all postgres peer To local all postgres md5 local all all peer to local all all md5
Restart Postgresql server with:
/etc/init.d/postgresql restart
To thest the local connection to the database please use:
psql -d postgres -U postgres
and
psql -d test -U test
Django installation and setup.
apt-get install aria2c aria2c http://www.djangoproject.com/download/1.4/tarball/ tar xvfz Django-1.4.tar.gz python setup.py install mkdir /var/djangoweb/ django-admin.py startproject myproject django-admin.py startproject myproject cd myproject/ mkdir /var/djangoweb/myproject/static ln -s /usr/local/lib/python2.7/dist-packages/django/contrib/admin /var/djangoweb/myproject/static/
in myproject/settings.py
Add
import os.path PROJECT_DIR = os.path.dirname(__file__)
Database setup in django
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2', # Add 'postgresql_psycopg2', 'mysql', 'sqlite3' or 'oracle'.
'NAME': 'test', # Or path to database file if using sqlite3.
'USER': 'test', # Not used with sqlite3.
'PASSWORD': 'test', # Not used with sqlite3.
'HOST': '', # Set to empty string for localhost. Not used with sqlite3.
'PORT': '', # Set to empty string for default. Not used with sqlite3.
}
}
Then go to the INSTALLED_APPS section and uncomment
django.contrib.admin line.
INSTALLED_APPS = (
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.sites',
'django.contrib.messages',
'django.contrib.staticfiles',
# Uncomment the next line to enable the admin:
# 'django.contrib.admin',
# Uncomment the next line to enable admin documentation:
# 'django.contrib.admindocs',
)
and # ‘django.contrib.admin’,
INSTALLED_APPS = (
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.sites',
'django.contrib.messages',
'django.contrib.staticfiles',
# Uncomment the next line to enable the admin:
'django.contrib.admin',
# Uncomment the next line to enable admin documentation:
# 'django.contrib.admindocs',
)
in myproject/urls.py uncomment the following lines.
from django.contrib import admin admin.autodiscover() url(r'^admin/', include(admin.site.urls)),
The urls.py file have to look like this.
from django.conf.urls import patterns, include, url
# Uncomment the next two lines to enable the admin:
from django.contrib import admin
admin.autodiscover()
urlpatterns = patterns('',
# Examples:
# url(r'^$', 'myproject.views.home', name='home'),
#url(r'^myproject/', include('myproject.foo.urls')),
# Uncomment the admin/doc line below to enable admin documentation:
# url(r'^admin/doc/', include('django.contrib.admindocs.urls')),
# Uncomment the next line to enable the admin:
url(r'^admin/', include(admin.site.urls)),
)
Now the basic parameters are defined, we must perform the first database synchronization,
go on top of the project root and issue the “python manage.py syncdb” command.
You’ll see the creation of the first Django tables inside the database, you also need to create
the administrator user.
Creating tables ... Creating table auth_permission Creating table auth_group_permissions Creating table auth_group Creating table auth_user_user_permissions Creating table auth_user_groups Creating table auth_user Creating table django_content_type Creating table django_session Creating table django_site Creating table django_admin_log You just installed Django's auth system, which means you don't have any superusers defined. Would you like to create one now? (yes/no): yes Username (leave blank to use 'root'): phillip E-mail address: phillip@foo.com Password: Password (again): Superuser created successfully. Installing custom SQL ... Installing indexes ... Installed 0 object(s) from 0 fixture(s)
At this point the Django interaction with the database looks working properly.
In order to get access to Django administration page you need to run the
embedded python web server.
python manage.py runserver 0.0.0.0:80 Validating models... 0 errors found Django version 1.4, using settings 'myproject.settings' Development server is running at http://0.0.0.0:80/ Quit the server with CONTROL-C.
Point the browser to:
http://server_ipaddress/admin/
Gunicorn installation and setup
Install gunicorn
apt-get install git python-setuptools git clone git://github.com/benoitc/gunicorn.git cd gunicorn/ python setup.py install
inside the root project folder myproject
vim gunicorn.conf.py
bind = "127.0.0.1:8888" workers = 2 #recommended (2 x $num_cores) + 1
To run gunicor go in the root project folder and run:
gunicorn_django -c gunicorn.conf.py
To Daemonize the Gunicorn process add -D
gunicorn_django -c gunicorn.conf.py -D
Yum must get:
gunicorn_django -c gunicorn.conf.py 2012-05-01 19:53:28 [6176] [INFO] Starting gunicorn 0.14.2 2012-05-01 19:53:28 [6176] [INFO] Listening at: http://127.0.0.1:8888 (6176) 2012-05-01 19:53:28 [6176] [INFO] Using worker: sync 2012-05-01 19:53:28 [6180] [INFO] Booting worker with pid: 6180 2012-05-01 19:53:28 [6181] [INFO] Booting worker with pid: 6181
Nginx installation and configuration
apt-get install nginx-full openssl rm /etc/nginx/sites-enabled/default touch /etc/nginx/sites-available/django ln -s /etc/nginx/sites-available/django /etc/nginx/sites-enabled/django
In /etc/nginx/sites-enabled/django please add:
server {
listen server_ipaddress:80;
#server_name *.site1;
access_log /var/log/nginx/djangosite1.access.log;
error_log /var/log/nginx/djangosite1.error.log;
location / {
proxy_pass http://127.0.0.1:8888;
}
#location /static {
# autoindex on;
# root /root/blog/public_html/;
# }
location /static/admin {
autoindex on;
root /var/djangoweb/myproject/static/admin;
}
}
/etc/init.d/nginx restart
Django admin web interface.

Now you can point the browser to http://server_ipaddress/admin/, be aware the myproject directory is just the schema container for the project, no applications are yet configured or installed. I strongly advise to follow “Writing your first Django app” how-to, do not copy paste the code.
If you want to find more about django development please take a look to:
Django From the Ground Up video series
DjangoCon 2011
The Django book
I hope this document will be useful for who is struggling with Django setup. Stay tuned.
