Django:加载芹菜的生产设置



我的 Django 项目有多个用于开发、生产和测试的设置文件。我正在使用主管来管理芹菜工人。我的问题如何根据我所处的环境加载芹菜的设置文件。

通过使用环境变量。假设您在存储库的根目录中有以下设置文件。

  • config.settings.development.py
  • config.settings.production.py

定义芹菜实例的推荐方法是在类似模块celery.py

配置中:
from __future__ import absolute_import, unicode_literals
import os
from celery import Celery
# set the default Django settings module for the 'celery' program.
# os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'config.settings.production')
app = Celery('proj')
# Using a string here means the worker doesn't have to serialize
# the configuration object to child processes.
# - namespace='CELERY' means all celery-related configuration keys
#   should have a `CELERY_` prefix.
app.config_from_object('django.conf:settings', namespace='CELERY')
# Load task modules from all registered Django app configs.
app.autodiscover_tasks()

@app.task(bind=True)
def debug_task(self):
print('Request: {0!r}'.format(self.request))

与其在模块中设置DJANGO_SETTINGS_MODULE变量(我已经注释掉了(,请确保在启动supervisord时这些变量存在于环境中。

要在暂存、测试和生产系统中设置这些变量,您可以执行以下 bash 命令。

例如,在您的生产系统上:

$ export DJANGO_SETTINGS_MODULE=config.settings.production
$ echo $DJANGO_SETTINGS_MODULE

我还建议您从.env文件中加载它们。在我看来,这更方便。你可以用例如python-dotenv来做到这一点。


更新

.env文件在不同的系统上大多是唯一的,通常不受源代码/版本控制。我的意思是对于开发,您可能有一个更详细的LOG_LEVEL或不同的SECRET_KEY,因为您不希望它们显示在源代码管理中,或者希望能够在不修改源文件的情况下调整它们。

因此,在您的base.py(production.pydevelopment.py继承(中,您可以使用例如以下内容从文件中加载变量:

import os
from dotenv import load_dotenv
load_dotenv()  # .env file has to be in the same directory
# ...
import os
DJANGO_SETTINGS_MODULE = os.getenv("DJANGO_SETTINGS_MODULE")
print(DJANGO_SETTINGS_MODULE)
# ...

我个人不使用该包,因为我使用docker,它具有定义.env文件的声明性方式,但上面的代码应该让您了解它是如何工作的。有类似的软件包,比如django-environ,在《Django的两勺子》一书中都有介绍。所以我倾向于使用它而不是python-dotenv,这是一个品味问题。

您可能希望配置不同的设置文件。从这里您有两种选择。你可以在运行时使用 django-admin 设置参数

django-admin runserver --settings=thecelery.settings

此外,您还可以选择在 settings.py 中配置设置。如果您当前有 1 个设置文件,这将要求您设置其他设置文件,并在实例上设置环境变量。然后在您的基本设置文件中,您可以像这样执行操作

import os
environment your_env = os.environ["environment"]
if your_env == "celery":
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "thecelerysettings")
else:
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "defaultsettings")