Apache Airflow 2.0.0.b2-动态EmailOperator[文件]属性

Apache Airflow 2.0.0.b2-动态EmailOperator[文件]属性,airflow,directed-acyclic-graphs,apache-airflow-xcom,Airflow,Directed Acyclic Graphs,Apache Airflow Xcom,TL;DR我如何创建一个动态EmailOperator,从属于XCom属性的文件路径发送文件 大家好 我使用的是ApacheAirflow 2.0.0.b2。我的问题是,我的DAG创建了一个文件,其名称在运行时更改。我想通过电子邮件发送此文件,但在将动态文件名输入EmailOperator时遇到问题 我尝试过但失败的事情!: def get_email_operator(**kwargs): export_file_path = kwargs['ti'].xcom_pull(key='O

TL;DR我如何创建一个动态EmailOperator,从属于XCom属性的文件路径发送文件

大家好

我使用的是ApacheAirflow 2.0.0.b2。我的问题是,我的DAG创建了一个文件,其名称在运行时更改。我想通过电子邮件发送此文件,但在将动态文件名输入EmailOperator时遇到问题

我尝试过但失败的事情!:

def get_email_operator(**kwargs):
    export_file_path = kwargs['ti'].xcom_pull(key='OUTPUT_CSV')
    email_subject = 'Termed Drivers - ' + date_string
    op = EmailOperator(
        task_id="get_email_operator",
        to=['someemail@somedomain.net'],
        subject=email_subject,
        files=[export_file_path,],
        html_content='<br>')
    op.execute(kwargs)
  • 文件
    属性使用模板

    files=["{{ ti.xcom_pull(key='OUTPUT_CSV') }}"],
    
    不幸的是,只有当操作符中的字段被标记为模板时,模板才起作用<代码>文件
    不是EmailOperator上的模板字段

  • 使用函数动态创建我的任务

     def get_email_operator(?...):
        export_file_path = ti.xcom_pull(key='OUTPUT_CSV')
        email_subject = 'Some Subject'
        return EmailOperator(
            task_id="get_email_operator",
            to=['someemail@somedomain.net'],
            subject=email_subject,
            files=[export_file_path,],
            html_content='<br>',
            dag=current_dag)
    
    ..task3 >> get_email_operator() >> task4
    

    文件将在Airflow 2中模板化,因为上周合并了

    但是,您不需要等待,您可以使用自己的自定义运算符包装当前运算符,指定模板字段列表

    比如:

    然后可以在代码中使用
    MyEmailOperator
    文件将被模板化

    您还可以通过使用包装EmailOperator的PythonOperator来解决此问题:

    def get_email_operator(**context):
        xcom = context['ti'].xcom_pull(task_ids='OUTPUT_CSV')
        email_subject = 'Some Subject'
        op = EmailOperator(
            task_id="get_email_operator",
            to=['someemail@somedomain.net'],
            subject=email_subject,
            files=[xcom,],
            html_content='<br>')
        op.execute(context)
    
    python = PythonOperator(
        task_id='archive_s3_file',
        dag=dag,
        python_callable=get_email_operator,
        provide_context=True
    )
    
    ..task3 >> python >> task4
    
    def get_email_操作符(**上下文):
    xcom=context['ti'].xcom\u pull(task\u id='OUTPUT\u CSV')
    email_subject='Some subject'
    op=电子邮件操作员(
    任务\u id=“获取电子邮件\u操作员”,
    to=['someemail@somedomain.net'],
    主题=电子邮件主题,
    文件=[xcom,],
    html_内容=“
    ”) op.execute(上下文) python=PythonOperator( 任务\u id='archive\u s3\u file', dag=dag, python\u callable=get\u email\u运算符, 提供上下文=True ) ..task3>>python>>task4
    非常感谢。我之所以选择第二种解决方案,是因为我担心在缺乏经验的情况下,我的管道设计会出错。当我将上下文传递给EmailOperator的execute方法时,它的工作非常出色。@BlackDynamite NP。我建议你至少试试第一种解决办法。它更简单,并且在下一个版本中发布修复程序时,您可以轻松删除自定义操作符并将其替换为气流操作符。
    def get_email_operator(**context):
        xcom = context['ti'].xcom_pull(task_ids='OUTPUT_CSV')
        email_subject = 'Some Subject'
        op = EmailOperator(
            task_id="get_email_operator",
            to=['someemail@somedomain.net'],
            subject=email_subject,
            files=[xcom,],
            html_content='<br>')
        op.execute(context)
    
    python = PythonOperator(
        task_id='archive_s3_file',
        dag=dag,
        python_callable=get_email_operator,
        provide_context=True
    )
    
    ..task3 >> python >> task4