tornado 并发编程系列(3)——Dynaconf 动态配置文件
Dynaconf是一个Python库,它可以用来管理应用程序的配置。它提供了许多有用的功能,例如从多个源(例如环境变量、配置文件、命令行参数等)加载配置,并允许通过一些简单的API访问配置。在本文中,我们将探讨如何在Tornado中使用Dynaconf来管理应用程序的配置。
安装Dynaconf
首先,我们需要安装Dynaconf库。可以使用pip包管理器来安装Dynaconf:
pip install dynaconf
载入配置
Dynaconf支持从多个源(例如环境变量、.env文件、YAML文件、INI文件、JSON文件、.envrc文件、.toml文件、命令行参数等)加载配置。为了使配置工作起来更加方便,我们可以将这些源的路径定义在一个名为settings.toml的文件中,如下所示:
[default]
ENV_FOR_DYNACONF=development
[development]
LOGLEVEL=DEBUG
APP_NAME=Tornado
这个文件定义了默认的环境变量、日志级别和Tornado应用程序的名称。如果我们想要添加其他的源,只需要添加另一个选项并指定另一个位置即可。例如,如果我们想要从一个叫做myconfig.yaml的YAML文件加载配置,我们可以在settings.toml中添加以下内容:
[default]
ENV_FOR_DYNACONF=development
[development]
LOGLEVEL=DEBUG
APP_NAME=Tornado
CONFIG_FILES=myconfig.yaml
在启动Tornado应用程序之前,我们需要在应用程序代码中加载Dynaconf。为了展示如何加载Dynaconf,我们将首先创建一个最简单的Tornado应用程序:
import tornado.ioloop
import tornado.web
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
def make_app():
return tornado.web.Application([
(r"/", MainHandler),
])
if __name__ == "__main__":
app = make_app()
app.listen(8888)
tornado.ioloop.IOLoop.current().start()
这里我们创建了一个Tornado应用程序,它监听8888端口,当我们访问
http://localhost:8888/时,它将写入“Hello, world”
。现在我们需要在应用程序中加载Dynaconf。为此,我们可以在应用程序代码的顶部添加以下几行:
from dynaconf import Dynaconf
settings = Dynaconf(
envvar_prefix="MY_APP",
settings_files=['settings.toml', '.secrets.toml'],
)
import tornado.ioloop
import tornado.web
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
def make_app():
return tornado.web.Application([
(r"/", MainHandler),
])
if __name__ == "__main__":
app = make_app()
app.listen(8888)
tornado.ioloop.IOLoop.current().start()
这里我们首先从Dynaconf导入Dynaconf类。然后我们创建了一个名为settings的Dynaconf实例,并指定了从哪些源加载配置。此处,我们指定MY_APP作为环境变量的前缀,并且使用settings.toml和.secrets.toml作为配置文件。最后,我们在应用程序代码的顶部创建了一个名为settings的Dynaconf实例。现在,我们可以在应用程序中使用settings变量来访问配置。
访问配置
现在我们已经成功地将Dynaconf加载到了Tornado应用程序中,并且可以使用settings变量来访问配置。有几种不同的方法可以访问配置:
使用点号分隔符和配置文件中定义的变量名称:
settings.APP_NAME
以上代码将返回“Tornado”。
使用Dynaconf提供的get()方法:
settings.get("APP_NAME")
以上代码将返回“Tornado”。
使用Dynaconf提供的get_clean()方法:
settings.get_clean("APP_NAME")
以上代码将返回“Tornado”,并会自动remove掉任何有毒的字符。
我们可以使用点号分隔符来访问配置文件中的任何选项。例如,如果我们想要访问日志级别:
settings.LOGLEVEL
以上代码将返回“DEBUG”。
可以将Dynaconf中的get()和get_clean()方法与默认值一起使用。例如,我们可以写出以下代码:
settings.get("NON_EXISTENT_VAR", default="default_value")
如果“NON_EXISTENT_VAR”不存在,将返回“default_value”。
我们还可以使用Dynaconf提供的pure()方法来获得一个纯净的字典,该字典只包含来自配置文件的选项。以下是一个例子:
clean_dict = settings.pure()
print(clean_dict)
以上代码将返回一个字典,该字典只包含配置文件中的选项,而不包括任何环境变量或命令行参数。
Dynaconf还提供了一些其他方法,例如:
-
as_bool():将值转换为布尔值。
-
as_int():将值转换为整数。
-
as_float():将值转换为浮点数。
-
as_list():将值转换为列表。
-
as_dict():将值转换为字典。
默认情况下,Dynaconf会自动检测值的类型,并使用适当的方法将其转换为指定的类型。如果您想显式指定一个类型,可以使用as_xxx()方法。例如,以下代码将把值转换为布尔类型:
settings.as_bool("MY_BOOL_VAR")
以上代码将返回布尔类型的值。
Dynaconf还提供了一种方法来访问嵌套的配置值。例如,如果我们的配置文件包含以下内容:
[default]
some.nested.key1 = "value1"
some.nested.key2 = "value2"
我们可以使用以下代码来访问nested.key1:
settings.some.nested.key1
Tornado集成
项目中,如果没有nacos,但是需要动态加载配置,应该如何实现?
api.yaml为api配置
routers.yaml为路由配置
import os
import dynaconf
from dynaconf import Dynaconf
settings = Dynaconf(
envvar_prefix="DYNACONF",
settings_files=['config/api.yaml'],
)
settings_router = dynaconf.LazySettings(
envvar_prefix="DYNACONF",
settings_files=['config/routers.yaml'],
)
def check_config_file_update():
settings_router.reload()
这段代码使用了dynaconf库来管理配置文件。主要的步骤包括:
-
导入必要的库和模块:import os,import dynaconf,from dynaconf import Dynaconf。
-
通过Dynaconf创建settings实例,载入api.yaml文件作为配置文件。
-
通过
LazySettings
创建settingsrouter实例,载入routers.yaml文件作为配置文件。 -
定义函数checkconfigfileupdate(),在函数内调用
settings_router.reload()方法
,重新载入配置文件
整个代码的作用是载入和管理两个配置文件,并在需要时重新载入
配置文件。
其中,Dynaconf和LazySettings是dynaconf
库提供的两种不同的配置管理方式,前者可以在配置文件载入时进行验证和解析,后者则使用懒加载
的方式,即在需要时才载入配置文件
checkconfigileupdate()
函数可以监控配置文件的变化并重新载入,从而保证程序使用的配置文件始终是最新的。
转载自:https://juejin.cn/post/7231152303583264828