通过 merging/updating 属性将配置加载到模块的命名空间
Load-once config by merging/updating properties onto module's namespace
在Python中采用以下配置单例class:
# -*- coding: utf-8 -*-
from __future__ import unicode_literals, print_function
from builtins import *
import sys
class Config(object):
__instance = None
def __new__(cls):
if cls.__instance is None:
cls.__instance = super(Config, cls).__new__(cls)
cls.__instance.__initialized = False
return cls.__instance
def __init__(self):
print('INIT')
if self.__initialized:
return
self.__initialized = True
self._defaults = {"foo": True, "bar": False}
for k, v in self._defaults.items():
setattr(self, k, v)
def reload(self):
print(self)
if not self._defaults:
return
for k, v in self._defaults.items():
setattr(self, k, v)
我可以编写一个测试来验证属性设置和更新是否正确:
import config; config = config.Config()
print(config)
print(config.foo)
assert(config.foo is True)
config.foo = False
print(config.foo)
assert(config.foo is False)
config.reload()
print(config.foo)
assert(config.foo is True)
输出:
INIT
<config.Config object at 0x10bbf73d0>
True
False
<config.Config object at 0x10bbf73d0>
True
这工作正常,但我的强迫症无法处理我必须导入配置并执行其主要 class。
我尝试将 sys.modules[__name__] = Config()
添加到 config.py
的底部,这样我就可以只做 import config
,但它对 reload()
犹豫不决:
TypeError: 'NoneType' object is not callable
奇怪的是,我只希望它抱怨模块命名空间上的值没有更新,但它似乎事先中断了 - 只是试图执行 reload()
.
我在这里运气不好吗?或者有什么神奇的方法可以同时使用 reload()
和单行 import config
?
当你 reload
时它不起作用的原因是因为在分配给 sys.modules[__name__]
之后,模块及其内置函数被垃圾收集并替换为 None
。我假设你知道这一点,因为你 from builtins import *
。但是,导入的内置函数也会被垃圾回收。
要解决此问题,您可以在 reload
中导入内置函数,这样您就可以使用不进行垃圾回收的版本。
旁注:这是未经测试的,因为我无法重现您的问题 here,但我相信它会发生,因为该网站在导入时可能会出现问题。
在Python中采用以下配置单例class:
# -*- coding: utf-8 -*-
from __future__ import unicode_literals, print_function
from builtins import *
import sys
class Config(object):
__instance = None
def __new__(cls):
if cls.__instance is None:
cls.__instance = super(Config, cls).__new__(cls)
cls.__instance.__initialized = False
return cls.__instance
def __init__(self):
print('INIT')
if self.__initialized:
return
self.__initialized = True
self._defaults = {"foo": True, "bar": False}
for k, v in self._defaults.items():
setattr(self, k, v)
def reload(self):
print(self)
if not self._defaults:
return
for k, v in self._defaults.items():
setattr(self, k, v)
我可以编写一个测试来验证属性设置和更新是否正确:
import config; config = config.Config()
print(config)
print(config.foo)
assert(config.foo is True)
config.foo = False
print(config.foo)
assert(config.foo is False)
config.reload()
print(config.foo)
assert(config.foo is True)
输出:
INIT
<config.Config object at 0x10bbf73d0>
True
False
<config.Config object at 0x10bbf73d0>
True
这工作正常,但我的强迫症无法处理我必须导入配置并执行其主要 class。
我尝试将 sys.modules[__name__] = Config()
添加到 config.py
的底部,这样我就可以只做 import config
,但它对 reload()
犹豫不决:
TypeError: 'NoneType' object is not callable
奇怪的是,我只希望它抱怨模块命名空间上的值没有更新,但它似乎事先中断了 - 只是试图执行 reload()
.
我在这里运气不好吗?或者有什么神奇的方法可以同时使用 reload()
和单行 import config
?
当你 reload
时它不起作用的原因是因为在分配给 sys.modules[__name__]
之后,模块及其内置函数被垃圾收集并替换为 None
。我假设你知道这一点,因为你 from builtins import *
。但是,导入的内置函数也会被垃圾回收。
要解决此问题,您可以在 reload
中导入内置函数,这样您就可以使用不进行垃圾回收的版本。
旁注:这是未经测试的,因为我无法重现您的问题 here,但我相信它会发生,因为该网站在导入时可能会出现问题。