Yuj*_*ita 30 python django configuration
如果未定义应用程序中的默认设置,那么处理默认设置的dangangonautic方法是settings.py什么?
我目前default_settings在应用程序中放置了一个文件,我考虑了一些选项.我倾向于第一种选择,但可能存在我在使用时不知道的陷阱globals()
我FOO = getattr(settings, 'FOO', False)经常看到应用程序在使用该设置的文件顶部执行操作,但我认为如果值/名称很长,则此方法存在可读性/重复性问题.
1:将设置放在函数中并迭代locals/set globals
def setup_defaults():
FOO = 'bar'
for key, value in locals().items():
globals()[key] = getattr(settings, key, value)
setup_defaults()
Run Code Online (Sandbox Code Playgroud)
优点:
缺点:
2:写下getattr(settings, 'MY_SETTING', default_settings.MY_SETTING)每个电话
优点: - 非常清楚.
缺点: - 重复
3:始终将设置定义为 FOO = getattr(settings, 'FOO', '...setting here...')
优点: - 始终覆盖默认值
缺点:
4:创建实用功能 get_or_default(setting)
优点:
缺点:
5:创建一个设置类
class Settings(object):
FOO = 'bar'
def __init__(self):
# filter out the startswith('__') of
# self.__dict__.items() / compare to django.conf.settings?
my_settings = Settings()
Run Code Online (Sandbox Code Playgroud)
缺点:
我很乐意听到反馈.
Ber*_*ant 42
我认为settings.py在你的应用程序包中创建一个很常见的东西,你可以在其中定义你的设置:
from django.conf import settings
FOO = getattr(settings, 'FOO', "default_value")
Run Code Online (Sandbox Code Playgroud)
在您的应用中,您可以从应用的settings模块中导入它们:
from myapp.settings import *
def print_foo():
print FOO
Run Code Online (Sandbox Code Playgroud)
但我认为每个人都认为Django缺乏更好的通用架构!如果您正在寻找一种更复杂的方法来处理这个问题,那么有一些第三方应用程序就像django-appconf一样,但如果您想为您的应用程序引入另外一个依赖项,那么您的决定就是它!
看来,我在那看到的每个解决方案都倾向于创建应用程序设置,代理,包装等内容的内部副本。当在运行时修改设置时(如在测试中所做的那样),这会造成混乱并产生问题。
对我来说,所有设置都属于其中django.conf.settings,仅在那里。您不应从其他地方阅读它们,也不应将其复制以备后用(因为它们可能会更改)。您应该将它们设置一次,以后不要再理会默认值了。
我了解在内部使用应用程序设置时冲掉应用程序前缀的冲动,但这也是恕我直言的一个好主意。遇到麻烦时,SOME_APP_FOO将不会产生结果,因为它在FOO内部使用。对吧?还有什么呢?还记得显式更好吗?
恕我直言,最好的方法是在Django自己的设置中设置这些默认值,为什么不使用已有的管道?models.py始终不会导入任何模块导入挂钩或劫持来初始化一些额外且复杂的元类管道。
为什么不使用AppConfig.ready设置默认值?
class FooBarConfig(AppConfig):
name = 'foo_bar'
def ready(self):
from django.conf import settings
settings = settings._wrapped.__dict__
settings.setdefault('FOO_BAR_SETTING', 'whatever')
Run Code Online (Sandbox Code Playgroud)
或者最好在一个单独的模块中以简洁明了的方式定义它们,并将它们作为(或接近)Settings类的实现导入:
class FooBarConfig(AppConfig):
name = 'foo_bar'
def ready(self):
from . import app_settings as defaults
from django.conf import settings
for name in dir(defaults):
if name.isupper() and not hasattr(settings, name):
setattr(settings, name, getattr(defaults, name))
Run Code Online (Sandbox Code Playgroud)
我不确定使用__dict__最好的解决方案,但是您知道了,可以始终通过用户hasattr/ setattr组合来获得效果。
这样,您的应用程序设置为:
django.conf.settings-如果需要,可以实现一些名称转换PS。有一个警告,关于不要在运行时修改设置,但不能解释原因。所以我认为这一次在初始化期间可能是一个合理的例外;)
PS2。不要命名单独的模块只是settings当你把这个可能会比较混乱settings的django.conf。
小智 5
这个怎么样?
在 myapp/settings.py 中:
from django.conf import settings
FOO = 'bar'
BAR = 'baz'
_g = globals()
for key, value in _g.items():
_g[key] = getattr(settings, key, value)
Run Code Online (Sandbox Code Playgroud)
在 myapp/other.py 中:
import myapp.settings
print myapp.settings.FOO
Run Code Online (Sandbox Code Playgroud)
鉴于ncoghlan 的这个答案,我觉得这样使用 globals() 没问题。