13

在尝试找到存储和保存 settings.py 和数据库之外的设置的地方时,我使用 environment.json 作为环境变量。我在 settings.py 中导入这些。

我的问题是,当我尝试在我的环境中更改或存储新值时envsettings.py并没有注意到更改 - 可能是因为 Django 读取了 settings.py 的时间和次数。

有没有一种方法可以像下面尝试的那样以我想要的方式使用我的环境变量?

# settings.py
import json
with open('/home/dotcloud/environment.json') as f:
    env = json.load(f)
EMAIL_HOST = env.get('EMAIL_PORT', '500')

# views.py
import json
def site_configuration(request):
    with open('/home/dotcloud/environment.json') as f:
        env = json.load(f)
    if request.method == 'POST':
        os.environ['EMAIL_PORT'] = request.POST['email_port']
    return render(request, ...)

# python manage.py shell demo
>>> import json
>>> with open('/home/dotcloud/environment.json') as f:
...     env = json.load(f)
... 
>>> project_settings.EMAIL_PORT
'500'
>>> env['EMAIL_PORT']
Traceback (most recent call last):
  File "<console>", line 1, in <module>
KeyError: 'EMAIL_PORT'
>>> env['EMAIL_PORT'] = "123"
>>> env['EMAIL_PORT']
'123'
>>> project_settings.EMAIL_PORT
'500'
>>> project_settings.EMAIL_PORT == env['EMAIL_PORT']
False'

如果没有,我还能如何存储由settings.py我的 Django 项目中某处检索到的可变设置?

4

2 回答 2

37

您可能想查看foreman( GitHub ) 或honcho( GitHub )。这两个都在当前目录中查找一个.env文件,从中加载本地环境变量。

对于大多数项目,我的.env外观是这样的(我使用 dj-database-url 进行数据库配置):

DATABASE_URL=sqlite://localhost/local.db
SECRET_KEY=<a secret key>
DEBUG=True

在您的settings.py文件中,您可以os.environ像这样加载这些设置:

import os
DEBUG = os.environ.get('DEBUG', False)

如果有必要的设置,您可以assert在尝试设置它们之前将它们存在:

assert 'SECRET_KEY' in os.environ, 'Set SECRET_KEY in your .env file!'
SECRET_KEY = os.environ['SECRET_KEY']

在我开始的最后几个项目中,我一直在使用这种处理本地设置的方法,我认为它非常有效。一个警告是永远不要承诺你.env的源代码控制。这些是仅存在于当前配置的本地设置,应该为不同的环境重新创建。

于 2012-09-17T17:57:11.410 回答
7

我看到问题略有变化,原始答案仍在下方,但这个答案略有不同:


首先,确保您使用的是正确的 settings.py (print 'This file is being loaded'应该可以解决问题)。

其次,我个人建议不要使用 json 文件进行配置,因为它不像 Python 文件那样动态,但无论如何它都应该工作。

我推荐的做这样的事情的方式:

  1. base_settings.py使用标准设置创建文件
  2. 创建一个settings.py这将是您的默认设置导入。该文件from base_settings import *的顶部应该有一个以继承基本设置。
  3. 例如,如果您想要一个自定义设置文件,dotcloud_settings.py只需添加from dotcloud_settings import settings(或base_settings)并将环境变量设置DJANGO_SETTINGS_MODULEdotcloud_settingsyour_project.dotcloud_settings取决于您的设置。

请注意,从这些设置文件中导入 Django 模块时应该非常小心。如果任何模块执行此操作from django.conf import settings,它将在该点之后停止解析您的设置。

至于使用json文件,当然原理大致相同:

  • 再一次,确保你没有django.conf.settings在这里导入的任何东西
  • 将 json 文件中的所有变量设置为全局变量:

    import json with open('/home/dotcloud/environment.json') as f: env = json.load(f) # 一个小技巧,让我们的环境中的所有变量 globals().update(env)


无论如何,我建议转而让设置文件导入此模块。

此外,Django 默认情况下不会监听环境变量(除此之外,DJANGO_SETTINGS_MODULE这也可能是问题所在。

于 2012-09-09T00:43:06.277 回答