Django settings settings module programmatically at runtime based on environment

Viewed 667

I have a dev and prod environment, I am trying to programmatically assign the settings module based on an environment variable DEV so fat my settings have the following structure:

project
--settings
----__init__.py
----common.py
----dev.py
----prod.py

inside my __init__.py I have:

import os

if os.environ['DEV_ENV']:
    os.environ['DJANGO_SETTINGS_MODULE'] = 'project.settings.dev'
else:
    os.environ['DJANGO_SETTINGS_MODULE'] = 'project.settings.prod'

However, when I run python3 manage.py migrate I get this error:

settings.DATABASES is improperly configured. Please supply the ENGINE value. Check settings documentation for more details.

however if I run with --settings flag manually, it works

python3 manage.py migrate --settings=project.settings.dev

3 Answers

Give this a try in __init__.py

import os
from .common import *

environment = os.environ.get("DEV_ENV")

if environment == development: #assuming value of DEV_ENV is 'development'
    from .dev import *
else:
    from .prod import *

this will load the development settings module if the value of DEV_ENV is set to development, otherwise by default it will load the production settings module.

Your logic should work within the manage.py script.

Alternatively, I would consider just setting DJANGO_SETTINGS_MODULE wherever you set DEV_ENV if possible.

Recently I found Python Decouple library and it's awesome for this purpose.

How I use it? I create a .env file in the project directory, I have an example template for my use case:

MODE=local
DEBUG=True
DB_NAME=hood
DB_USER=postgres
DB_PASSWORD=abc123
DB_HOST=127.0.0.1
REDIS_HOST=127.0.0.1
SENTRY_DNS={{sentry_dns}}

and then in my __init__.py I decide environment based off of values in this file

example:

from decouple import config

mode = config('MODE')

if mode == 'dev':
    from .development import *
elif mode == 'prod':
    from .production import *
else:
    from .local import *

This solves 2 main purposes:

  • it solves the which env I'm using now problem
  • it allows you to put passwords and env variables away from your git repository
Related