Upload
tomas-sirny
View
255
Download
1
Embed Size (px)
Citation preview
Settings in Django
ApplicationsHandling of settings in various environments
Tomáš Sirný
@junckritter
Default
• 1 file - settings.py
• good for local development
• deploy to production?
• different environments / developer machines
(OSX/Win)
• to git or not to git?
Simple solution
• if-clause for name of production/devel machine
• magic with imports from different files
• manually curated file on production machine
• …
Problems
• Hard to manage different sets of settings
• Copying of files/code snippets in deploy scripts,
test/build configs
• Not replicable if not versioned
• No recommendation in Django documentation
The right way
• based on https://speakerdeck.com/jacobian/the-
best-and-worst-of-django?slide=81 (by Django’s
contributor)
• Two Scoops of Django
Principles
• common parts to base.py
• separate file for each environment
• use env variable DJANGO_SETTINGS_MODULEor CLI parameter --settings= for ./manage.py
• everything is in git
• easy additions/changes of particular setting values
Our setup• __init__.py
• base.py
• helpers.py
• local.tpl.py
• admin.py
• staging.py
• production.py
base.py
• sane defaults - application could (mostly) run as-is
• INSTALLED_APPS, DEBUG, DATABASES,
CACHES
• settings for applications
helpers.py
• code running at the end
• generate final settings based on temporary ones
DEBUG_MODULES = ['action', ‘emails’] in local.py
for module in globals().get('DEBUG_MODULES', []):
LOGGING[‘loggers’][module] = …
local.tpl.py
• template for local development
• good starting point for newcomer
• good place to manifest changes / new settings,
visible in VCS diff
[environment].py
• from .base import *
• …
• execfile(os.path.join(PROJECT_PATH,
'project/settings/helpers.py
[environment].py
• only changes for particular environment
• diff against base.py (or Django’s global settings)
• $DJANGO_SETTINGS_MODULE=[environment].py
Pros
• More control
• Easy check/reference to particular setting
• Easier build/deployment
• Documented changes/defaults
Cons
• Possible duplication for similar environments
(admin, production) - more layers, shared parts
• env variable have to be set everywhere
Tips & tricks
Settings for applications
• settings file is big chunk of code
• all settings in one (or few) place(s)
• harder to find settings for particular application
Our solution
• settings.py in each application with defaults
• app1/settings.py
• app2/settings.py
• global settings file can override
• APP_SETTING =
settings.get(‘GLOBAL_APP_SETTING, ‘default’)
Cache invalidation
• hard problem in CS
• especially during deployment/migration
• format of key is usually tied to version of code
Cache invalidation
in base.py
from subprocess import check_output, CalledProcessError
try:
VERSION = check_output(
'git rev-parse --short=8 HEAD',
shell=True
).strip()
except CalledProcessError:
VERSION = 'test'
Cache invalidation
in production.py
CACHES = {
'default': {
'BACKEND': 'project.cache.EnhancedRedisCache',
'LOCATION': 'redis:6379',
'VERSION': VERSION,
'OPTIONS': {
'DB': 1,
'PASSWORD': '',
'PARSER_CLASS': 'redis.connection.HiredisParser'
}
}
}
One more thing
Migrate Postgres
psql -h <host1> ... -c 'copy (select ... from
<tablename> where …) to stdout' |
psql -h <host2> ... -c 'copy <tablename> from stdin'