Airflow : 执行任务触发规则详解

默认情况下,任务只会在所有父任务成功完成后执行。这通常是预期的行为。但是如果你想要更复杂的东西呢?如果希望在一个上游任务成功后立即执行该任务,该怎么办?或者在另一组任务失败时执行另一组任务?在处理数据流程的多个用例时,掌握这个概念是必不可少的:Ariflow触发规则。

应用场景

让我们从下面具体的用例开始,以便更好地理解为什么这个特性可能对你有帮助。
在这里插入图片描述

任务失败响应

当任务失败时你能做什么?Airflow提供了不同的机制,但在失败的情况下,常见的反应是使用回调。这很简单:给Operator参数on_failure_callback提供函数,一旦任务失败,它就会调用该函数。它很棒,但也有一些局限性:

  • 调度器不管理回调。如果失败,则无法重试或得到警告。
  • 回调函数应该运行轻量级任务。如果需要实现更复杂业务,应该采用其他方案。

解决这些缺点的方法是使用Airflow触发规则!

解决BranchPythonOperator缺陷

让我们看一下下面的数据流程:

在这里插入图片描述

choose_model使用BranchPythonOperator在is_inaccurateis_accurate之间进行选择,然后不管选择的任务是什么都执行store。然而,你可以从上面看到,事情并不如预想那样执行。当一个任务被跳过时,其所有直接下游任务都被跳过。如果你想始终都要执行store呢?Airflow触发规则该如何设置?

Airflow 触发规则

触发器规则定义了任务运行的前提——基于什么条件。默认情况下,所有任务都具有相同的触发规则all_success,即如果一个任务的所有上游任务都成功,则该任务运行。只能指定一个触发规则:

my_task = PythonOperator(
  task_id='my_task',
  trigger_rule='all_success'
)

触发规则有很多。让我们看看每一个。

Airflow触发规则详解

  • all_success

这个很简单,你已经用过了。当所有直接上游任务都成功时,任务运行。

图2

然而,如果上游任务被跳过,那么下游任务也会被跳过:

图3

  • all_failed

很简单,如果所有直接上游任务都失败,则运行一个任务

图4

如果你想做一些清理或更复杂的事情,你不能在回调中实现,这个Airflow触发规则是很方便的。你可以定义一组任务,以便在某些任务失败时执行。与all_success一样,如果跳过一个直接上游任务,也会跳过该任务。

  • all_done

在所有直接上游任务完成后立即触发任务,而不管它们的状态如何。

图5

如果你总是希望执行某个任务,而不管上游任务的状态如何,例如清理某些资源,则此触发器规则可能很有用。

  • one_failed

只要上游任务有一个失败,你的任务会执行。

图6

如果有长时间运行的任务,并且希望在其中一个任务失败后立即执行某些操作,则非常有用。

  • one_success

就像one_failed一样,但是相反。只要其中一个上游任务成功,你的任务就会运行。

图7

  • none_failed

如果所有直接上游任务都成功或被跳过,则任务运行。只有你想要处理跳过状态时才有用。

图8

  • none_skipped

如果没有直接上行任务处于跳过状态,则任务运行。

图9

  • none_failed_min_one_success

先前称为“none_failed_or_skip”(在气流2.2之前),使用此触发规则,如果所有直接上游任务都没有失败并且至少有一个成功,则你的任务运行。

这是处理BranchPythonOperator缺陷时必须使用的规则。

图10

规则配置实战

基本示例(使用 Python API)

假设你有一个简单的 DAG(有向无环图),其中包含三个任务task1task2task3。你想设置task3的触发规则为one_failed。以下是示例代码:

from airflow import DAG
from airflow.operators.dummy_operator import DummyOperator
from datetime import datetime

default_args = {
    'owner': 'airflow',
    'start_date': datetime(2024, 1, 1)
}

dag = DAG('trigger_rule_example', default_args=default_args, schedule_interval=None)

task1 = DummyOperator(task_id='task1', dag=dag)
task2 = DummyOperator(task_id='task2', dag=dag)
task3 = DummyOperator(task_id='task3', dag=dag, trigger_rule='one_failed')

task1 >> task3
task2 >> task3

在这个示例中:

  • 首先,导入了必要的模块,包括DAGDummyOperatorDummyOperator是一个简单的占位符任务,用于演示目的。
  • 定义了default_args,其中包含owner(任务所有者)和start_date(DAG 开始日期)等默认参数。
  • 创建了一个名为trigger_rule_example的 DAG,设置了schedule_intervalNone,表示这个 DAG 不是按照时间间隔调度的(可以根据实际需求修改)。
  • 创建了三个任务task1task2task3。对于task3,通过trigger_rule='one_failed'设置了触发规则。
  • 最后,通过>>操作符定义了任务之间的依赖关系,task1task2的输出都流向task3。这意味着task3会根据one_failed触发规则,在task1或者task2失败时被触发。

使用 TaskFlow API 示例(较新的方式)

以下是一个使用 TaskFlow API 设置触发规则的示例。假设你有一个简单的函数式任务的 DAG:

from airflow.decorators import dag, task
from datetime import datetime

@dag(dag_id='taskflow_trigger_rule_example', start_date=datetime(2024, 1, 1), schedule_interval=None)
def my_dag():
    @task
    def task1():
        return 1

    @task
    def task2():
        # 模拟一个可能的错误
        raise ValueError("Error in task2")

    @task(trigger_rule='one_failed')
    def task3(result1, result2):
        try:
            # 尝试处理结果,这里只是简单打印
            print(f"Task3 received results: {result1}, {result2}")
        except Exception as e:
            print(f"Error in task3: {e}")

    result1 = task1()
    result2 = task2()
    task3(result1, result2)

my_dag = my_dag()

在这个示例中:

  • 使用@dag装饰器定义了一个 DAG,包含start_dateschedule_interval等参数。
  • 定义了三个任务task1task2task3task1返回一个简单的值,task2模拟了一个错误(抛出ValueError)。
  • 对于task3,通过@task(trigger_rule='one_failed')设置了触发规则。task3尝试接收task1task2的结果并进行处理。由于task2会出错,根据one_failed规则,task3会被触发并处理可能的错误情况。

上面示例展示了如何在 Airflow 中配置触发规则,无论是使用传统的 Python API 还是较新的 TaskFlow API。你可以根据实际的业务需求,调整触发规则和任务的具体逻辑。

Taskflow API为定义Python任务及其依赖项提供了一种简单的方法,使用的语法更接近于使用常规Python函数,而不是更面向对象的操作符API。这使得API可以极大地简化大量使用PythonOperator的dag,并使用xcom在结果任务之间传递数据。通过确保在任务之间显式地传递值,而不是在相应的函数中隐藏任务之间的依赖关系,该API还解决了使用xcom传递数据的不足。

然而,Taskflow API的一个缺点是它的使用目前仅限于Python任务,否则将使用PythonOperator实现。因此,涉及任何其他Airflow操作的任务都需要使用常规API来定义任务及其依赖关系。尽管这并不妨碍混合和匹配这两种风格,但如果不小心,生成的代码可能会变得令人困惑。

总结

Airflow触发规则使用简单,但功能强大,因为它们可以解决实际场景问题。不要犹豫,使用触发规则比回调更可靠、高效处理错误。触发规则对于管理资源非常有用,但是需要你采用更好的方法来创建或和拆除任务。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值