Skip to content Skip to sidebar Skip to footer

How To Manage Local Vs Production Settings In Django?

What is the recommended way of handling settings for local development and the production server? Some of them (like constants, etc) can be changed/accessed in both, but some of th

Solution 1:

Two Scoops of Django: Best Practices for Django 1.5 suggests using version control for your settings files and storing the files in a separate directory:

project/
    app1/
    app2/
    project/
        __init__.py
        settings/
            __init__.py
            base.py
            local.py
            production.py
    manage.py

The base.py file contains common settings (such as MEDIA_ROOT or ADMIN), while local.py and production.py have site-specific settings:

In the base file settings/base.py:

INSTALLED_APPS = (
    # common apps...
)

In the local development settings file settings/local.py:

from project.settings.base import *

DEBUG = True
INSTALLED_APPS += (
    'debug_toolbar', # and other apps for local development
)

In the file production settings file settings/production.py:

from project.settings.base import *

DEBUG = False
INSTALLED_APPS += (
    # other apps for production site
)

Then when you run django, you add the --settings option:

# Running django for local development
$ ./manage.py runserver 0:8000 --settings=project.settings.local

# Running django shell on the production site
$ ./manage.py shell --settings=project.settings.production

The authors of the book have also put up a sample project layout template on Github.


Solution 2:

In settings.py:

try:
    from local_settings import *
except ImportError as e:
    pass

You can override what needed in local_settings.py; it should stay out of your version control then. But since you mention copying I'm guessing you use none ;)


Solution 3:

Instead of settings.py, use this layout:

.
└── settings/
    ├── __init__.py  <= not versioned
    ├── common.py
    ├── dev.py
    └── prod.py

common.py is where most of your configuration lives.

prod.py imports everything from common, and overrides whatever it needs to override:

from __future__ import absolute_import # optional, but I like it
from .common import *

# Production overrides
DEBUG = False
#...

Similarly, dev.py imports everything from common.py and overrides whatever it needs to override.

Finally, __init__.py is where you decide which settings to load, and it's also where you store secrets (therefore this file should not be versioned):

from __future__ import absolute_import
from .prod import *  # or .dev if you want dev

##### DJANGO SECRETS
SECRET_KEY = '(3gd6shenud@&57...'
DATABASES['default']['PASSWORD'] = 'f9kGH...'

##### OTHER SECRETS
AWS_SECRET_ACCESS_KEY = "h50fH..."

What I like about this solution is:

  1. Everything is in your versioning system, except secrets
  2. Most configuration is in one place: common.py.
  3. Prod-specific things go in prod.py, dev-specific things go in dev.py. It's simple.
  4. You can override stuff from common.py in prod.py or dev.py, and you can override anything in __init__.py.
  5. It's straightforward python. No re-import hacks.

Solution 4:

I use a slightly modified version of the "if DEBUG" style of settings that Harper Shelby posted. Obviously depending on the environment (win/linux/etc.) the code might need to be tweaked a bit.

I was in the past using the "if DEBUG" but I found that occasionally I needed to do testing with DEUBG set to False. What I really wanted to distinguish if the environment was production or development, which gave me the freedom to choose the DEBUG level.

PRODUCTION_SERVERS = ['WEBSERVER1','WEBSERVER2',]
if os.environ['COMPUTERNAME'] in PRODUCTION_SERVERS:
    PRODUCTION = True
else:
    PRODUCTION = False

DEBUG = not PRODUCTION
TEMPLATE_DEBUG = DEBUG

# ...

if PRODUCTION:
    DATABASE_HOST = '192.168.1.1'
else:
    DATABASE_HOST = 'localhost'

I'd still consider this way of settings a work in progress. I haven't seen any one way to handling Django settings that covered all the bases and at the same time wasn't a total hassle to setup (I'm not down with the 5x settings files methods).


Solution 5:

I use a settings_local.py and a settings_production.py. After trying several options I've found that it's easy to waste time with complex solutions when simply having two settings files feels easy and fast.

When you use mod_python/mod_wsgi for your Django project you need to point it to your settings file. If you point it to app/settings_local.py on your local server and app/settings_production.py on your production server then life becomes easy. Just edit the appropriate settings file and restart the server (Django development server will restart automatically).


Post a Comment for "How To Manage Local Vs Production Settings In Django?"