运行一个导入Airflow包的Python文件需要Airflow实例吗?
我在使用Airflow时遇到了一个奇怪的导入问题。我想创建一个模块,其他人可以从中导入内容。同时,我也想对这个模块进行单元测试。不过,我发现只要从Airflow包中导入任何东西,它就会尝试运行Airflow。
举个例子:
# myfile.py
from airflow import DAG
print("Hello world")
然后用 python myfile.py
运行它,结果是:
(.venv) c:\Users\Jarro\Development\airflow-tryout-import>python myfile.py
WARNING:root:OSError while attempting to symlink the latest log directory
Traceback (most recent call last):
File "c:\Users\Jarro\Development\airflow-tryout-import\myfile.py", line 1, in <module>
from airflow import DAG
File "C:\Users\Jarro\Development\airflow-tryout-import\.venv\Lib\site-packages\airflow\__init__.py", line 68, in <module>
settings.initialize()
File "C:\Users\Jarro\Development\airflow-tryout-import\.venv\Lib\site-packages\airflow\settings.py", line 559, in initialize
configure_orm()
File "C:\Users\Jarro\Development\airflow-tryout-import\.venv\Lib\site-packages\airflow\settings.py", line 237, in configure_orm
raise AirflowConfigException(
airflow.exceptions.AirflowConfigException: Cannot use relative path: `sqlite:///C:\Users\Jarro/airflow/airflow.db` to connect to sqlite. Please use absolute path such as `sqlite:////tmp/airflow.db`.
除了错误本身,我更担心的是,似乎我无法从Airflow中导入东西,而不会引发一些副作用(比如数据库初始化)。我是不是走错了方向?有没有其他方法可以从Airflow中导入东西,而不会有这些副作用,比如为了类型提示的目的?
2 个回答
1
你可以在没有初始化 Airflow 的情况下进行导入,这样会自动创建一个默认的数据库,可能你已经注意到了。不过,Airflow 在 Windows 系统上并不好用,表现也不太稳定。
如果你主要是想进行类型检查或者注释,可能可以考虑使用 TYPE_CHECKING
这个块。
from __future__ import annotations
from typing import TYPE_CHECKING
if TYPE_CHECKING:
from airflow.models.dag import DAG
3
这个问题发生是因为Python中的导入方式。你正在从airflow
这个包中导入东西,而这个包里有一个__init__
文件。
如果你查看这个文件,会发现里面有一段代码负责处理所有的airflow初始化工作。
在__init__.py
的第67到68行:
if not os.environ.get("_AIRFLOW__AS_LIBRARY", None):
settings.initialize()
如果你只是想像你说的那样导入一些东西用于类型提示,你可以把环境变量_AIRFLOW__AS_LIBRARY
设置成任何值,这样就不会进行初始化了。