gpt4 book ai didi

python - 在 python 中加载模块范围的配置

转载 作者:行者123 更新时间:2023-12-04 17:51:08 26 4
gpt4 key购买 nike

让我们假设,在一个模块中有以下简约的 python 类,例如模块:

module/
__init__.py
db.py
document.py

数据库.py

import yaml

class DB(object):
config = {}

@classmethod
def load_config(cls, config_path):
cls.config = yaml.load(open(config_path, 'r').read())

和文档.py

from .db import DB

class Document(object):
db = None

def __init__(self):
self.db = DB()

最终用户将按如下方式使用这样的模块:

from Module import DB, Document

DB.load_config('/path/to/config.yml')

Document.do_some_stuff()

doc1 = Document()
doc2 = Document.find(...)
doc2.update_something(...)
doc2.save()

预计 Document 类及其每个实例都可以在内部访问类 DB,并具有用户指定的配置。但是,由于 Document 执行了 DB 类的内部导入(from .db import DB),它接收到一个“新的”DB 具有默认配置的类。

我做了很多搜索,大多数问题和答案都是关于模块范围的配置,而不是最终用户指定的。

我怎样才能实现这样的功能?我猜这里存在一些架构问题,但解决它的最简单方法是什么?

最佳答案

也许这不是最合适的答案,但几个月前我写了一个名为 aconf 的模块为了这个确切的目的。它是用 8 行代码编写的基于内存的 Python 全局配置模块。我们的想法是您可以执行以下操作:

您创建一个 Config 对象来强制用户输入您的程序所需的配置(在本例中它位于 config.py 中):

""" 'Config' class to hold our desired configuration parameters. 

Note:
This is technically not needed. We do this so that the user knows what he/she should pass
as a config for the specific project. Note how we also take in a function object - this is
to demonstrate that one can have absolutely any type in the global config and is not subjected
to any limitations.
"""

from aconf import make_config

class Config:
def __init__(self, arg, func):
make_config(arg=arg, func=func)

您在整个模块中使用您的配置(在本例中,在 functionality.py 中):

""" Use of the global configuration through the `conf` function. """

from aconf import conf

class Example:
def __init__(self):
func = conf().func
arg = conf().arg

self.arg = func(arg)

然后使用它(在本例中是在 main.py 中):

from project.config import Config
from project.functionality import Example

# Random function to demonstrate we can pass _anything_ to 'make_config' inside 'Config'.
def uppercase(words):
return words.upper()

# We create our custom configuration without saving it.
Config(arg="hello world", func=uppercase)

# We initialize our Example object without passing the 'Config' object to it.
example = Example()
print(example.arg)
# >>> "HELLO WORLD"

整个aconf模块如下:

__version__ = "1.0.1"
import namedtupled

def make_config(**kwargs):
globals()["aconf"] = kwargs

conf = lambda: namedtupled.map(globals()["aconf"])
config = lambda: globals()["aconf"]

...本质上,您只需在运行时将配置保存到 globals()

这太愚蠢了,让我怀疑是否应该允许你这样做。我写 aconf 是为了好玩,但从来没有在大型项目中亲自使用过它。事实上,您可能会遇到让您的代码对其他开发人员来说很奇怪的问题。

关于python - 在 python 中加载模块范围的配置,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44849969/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com