刚开始使用Airflow并想知道构建大型DAG的最佳实践是什么。对于我们的ETL,我们有许多属于逻辑分组的任务,但这些组依赖于彼此。以下哪项被认为是最佳做法?
也欢迎其他建议。
答案 0 :(得分:9)
DAG只是python文件。因此,您可以将单个dag定义拆分为多个文件。不同的文件应该只有接受dag对象的方法,并使用该dag对象创建任务。
但请注意,您应该只在全局范围内使用一个dag对象。 Airflow将全局范围内的所有dag对象作为单独的dags进行拾取。
通常认为保持每个dag尽可能简洁是一种好习惯。但是,如果您需要设置此类依赖项,则可以考虑使用子标记。有关此内容的更多信息,请访问:https://airflow.incubator.apache.org/concepts.html?highlight=subdag#scope
您也可以使用ExternalTaskSensor,但要注意随着dag数量的增加,处理任务之间的外部依赖关系可能会变得更加困难。我认为子标签可能是你用例的方法。
答案 1 :(得分:1)
随着 TaskGroups 在 Airflow 2.x 中的出现,值得对 a previous answer 进行扩展。 TaskGroups 只是任务的 UI 分组,但它们也用作一堆相关任务的方便的逻辑分组。 TaskGroup 中的任务可以捆绑和抽象出来,以便更容易地从更大的部分构建 DAG。话虽如此,拥有一个充满相关任务的文件可能仍然很有用,而无需将它们捆绑到一个任务组中。
分解 DAG 的技巧是将 DAG 放在一个文件中,例如 my_dag.py
,将任务的逻辑块或任务组放在单独的文件中,每个文件有一个逻辑任务块或任务组。每个文件都包含函数(或方法,如果您想采用面向对象的方法),每个函数都返回一个操作员实例或一个 TaskGroup 实例。
为了说明,my_dag.py
(如下)从 foo_bar_tasks.py
导入操作符返回函数,并从 xyzzy_taskgroup.py
导入 TaskGroup 返回函数。在 DAG 上下文中,调用这些函数并将它们的返回值分配给任务或任务组变量,这些变量可以分配上游/下游依赖项。
dags/my_dag.py
:
# std lib imports
from airflow import DAG
# other airflow imports
from includes.foo_bar_tasks import build_foo_task, build_bar_task
from includes.xyzzy_taskgroup import build_xyzzy_taskgroup
with DAG(dag_id="my_dag", ...) as dag:
# logical chunk of tasks
foo_task = build_foo_task(dag=dag, ...)
bar_task = build_bar_task(dag=dag, ...)
# taskgroup
xyzzy_taskgroup = build_xyzzy_taskgroup(dag=dag, ...)
foo_task >> bar_task >> xyzzy_taskgroup
plugins/includes/foo_bar_tasks.py
:
# std lib imports
from airflow import DAG
from airflow.operators.foo import FooOperator
from airflow.operators.bar import BarOperator
# other airflow imports
def build_foo_task(dag: DAG, ...) -> FooOperator:
# ... logic here ...
foo_task = FooOperator(..., dag=dag)
return foo_task
def build_bar_task(dag: DAG, ...) -> BarOperator:
# ... logic here ...
bar_task = BarOperator(..., dag=dag)
return bar_task
plugins/includes/xyzzy_taskgroup.py
:
# std lib imports
from airflow import DAG
from airflow.operators.baz import BazOperator
from airflow.operators.qux import QuxOperator
from airflow.utils import TaskGroup
# other airflow imports
def build_xyzzy_taskgroup(dag: DAG, ...) -> TaskGroup:
xyzzy_taskgroup = TaskGroup(group_id="xyzzy_taskgroup")
# ... logic here ...
baz_task = BazOperator(task_id="baz_task", task_group=xyzzy_taskgroup, ...)
# ... logic here ...
qux_task = QuxOperator(task_id="qux_task", task_group=xyzzy_taskgroup, ...)
baz_task >> qux_task
return xyzzy_taskgroup
答案 2 :(得分:0)
似乎可以将您的 Python 模块放入 plugins/
子文件夹并从 DAG 文件中导入它们:
https://airflow.apache.org/docs/apache-airflow/stable/plugins.html