数据 ETL 调度引擎对接

想让数据 ETL 任务流对接外部调度系统(Airflow/Azkaban/DolphinScheduler 等),需要新增一个调度引擎实现时读这篇

06-二次开发 / 数据与调度
数据ETLETL调度引擎计算引擎workflowairflowazkabandolphinscheduleroozieall_templatepipeline_config_uipipeline_jump_buttonpipeline_run_buttonsubmit_pipelinedelete_pipelinedag_json

数据 ETL 调度引擎对接(二次开发)

1. 背景与原理

数据 ETL 模块在平台上提供 任务流编排能力:拖拉拽算子、配置每个节点、连出上下游关系,编排结果以 dag_json 形式存进数据库(etl_pipeline 表)。

但 cube-studio 本身只负责编排,并不直接向远程调度系统创建/删除任务。要真正把编排出来的 DAG 提交到 Airflow / Azkaban / DolphinScheduler 等调度系统执行,需要二次开发实现一个 调度引擎(workflow) 适配,完成:

  • 向远程调度系统创建任务、删除任务;
  • 把远程任务的信息记录回本地数据库。

2. 调度引擎的派发约定(关键)

每个 ETL 任务流(ETL_Pipeline)有一个 workflow 字段(界面标签为"计算引擎",模型注释为"调度引擎",默认 data_analysis,见 myapp/models/model_etl_pipeline.py:29myapp/views/view_etl_pipeline.py:242-250)。

平台根据 workflow 的值,按固定命名约定动态加载 对应的实现类(myapp/views/view_etl_pipeline.py:479-480 等多处):

import importlib
# 模块名 = view_etl_pipeline_<workflow>
params = importlib.import_module('myapp.views.view_etl_pipeline_' + pipeline.workflow)
# 类名   = <WORKFLOW 大写>_ETL_PIPELINE,构造参数是 pipeline 模型对象
etl_pipeline = getattr(params, pipeline.workflow.upper() + '_ETL_PIPELINE')(pipeline)

所以要新增一个调度引擎 xxx,约定是:

  1. 新建文件 myapp/views/view_etl_pipeline_xxx.py
  2. 在其中定义类 XXX_ETL_PIPELINE,构造函数接收 pipelineETL_Pipeline 模型对象);
  3. ['xxx', 'xxx'] 加进 workflow 字段的 choicesmyapp/views/view_etl_pipeline.py:242-250),用户新建任务流时即可选择该引擎。

说明:当前代码库 不存在 view_etl_pipeline_airflow.py / view_etl_pipeline_azkaban.py / view_etl_pipeline_dolphinscheduler.py(已核实),只有两个内置引擎实现:

  • myapp/views/view_etl_pipeline_etl.py(类 ETL_ETL_PIPELINE,是一个 Airflow 风格的对接模板/桩,默认 host='http://airflow.oa.com'submit_pipeline / delete_pipeline 内部多为 todo,需二开补全);
  • myapp/views/view_etl_pipeline_data_analysis.py(类 DATA_ANALYSIS_ETL_PIPELINE,cube-studio 内置 的数据分析任务流 runner,已完整实现,跑在 K8s 上)。

当前 workflowchoices 也只有 etldata_analysis 两项(myapp/views/view_etl_pipeline.py:248)。要对接 Airflow/Azkaban/DolphinScheduler,请按上面的命名约定新建文件并扩展 choices,把 view_etl_pipeline_etl.py 当作模板照着实现。

3. 一个调度引擎要实现哪些东西

实现类(如 ETL_ETL_PIPELINE)需要提供以下属性/方法,平台基类 view_etl_pipeline.py 会按下面的方式调用它们:

名称 形态 作用 被调用处
all_template 类属性(dict) 想要支持的算子模板列表 view_etl_pipeline.py:526
pipeline_config_ui 类属性 / 属性 任务流的公共参数配置(任务流负责人、调度周期、告警等) view_etl_pipeline.py:503
pipeline_jump_button(self) 方法,返回 list 编排页右上角"快捷跳转"按钮(跳到调度系统实例/日志页) view_etl_pipeline.py:504
pipeline_run_button(self) 方法,返回 list 编排页右上角"任务提交/运行"按钮 view_etl_pipeline.py:505
submit_pipeline(self) 方法,返回 (dag_json, redirect_url) dag_json 提交给远程调度系统 view_etl_pipeline.py:570:568-569
delete_pipeline(self) 方法 在远程调度系统中删除任务(清理上下游/远程任务) view_etl_pipeline.py:323-325

注意:pipeline_config_ui 被当作属性访问(无括号),view_etl_pipeline_etl.py 里是类属性 dict,view_etl_pipeline_data_analysis.py 里则用方法/属性形式提供,两种都可以。

3.1 all_template 结构

all_template 是一个 dict,关键字段(参考 myapp/views/view_etl_pipeline_etl.py:18 起):

  • templte_list算子模板列表,按分组(group)组织;平台会遍历它给每个模板补 template_id / changed_on / created_on / usernameview_etl_pipeline.py:528-535)。
    • ⚠️ 字段名是 templte_list(源码中的拼写,少一个 a),照抄即可,别"纠正"成 template_list
  • templte_common_ui_config公共配置参数,每个任务节点都带(任务名、调度周期 crontab、队列、监控告警、超时等)。
  • task_metadata_ui_config:任务元数据配置(如中文名 label)。
  • message / status:固定返回字段。

3.2 submit_pipeline 返回值

submit_pipeline 返回二元组 (dag_json, redirect_url),平台按 dag_json, redirect_url = etl_pipeline.submit_pipeline() 解包(view_etl_pipeline.py:570)。redirect_url 一般指向远程调度系统中该 DAG 的页面。模板里的示例实现(view_etl_pipeline_etl.py:977-980):

def submit_pipeline(self):
    # todo: 检查任务是否存在;创建/修改/删除远程任务;发起远程调度
    return "", self.host + "/code?dag_id=%s" % self.pipeline.name

3.3 跳转/运行按钮结构

pipeline_jump_button / pipeline_run_button 返回按钮列表,每个按钮形如(view_etl_pipeline_etl.py:947-973):

{
    "name": "调度实例",
    "action_url": self.host + "/tree?dag_id=%s" % self.pipeline.name,  # 跳转目标
    "icon_svg": "<svg ...>...</svg>"                                    # 按钮图标
}

其中"提交"按钮的 action_url 通常指向平台自身的提交接口 "/etl_pipeline_modelview/api/submit_etl_pipeline/<pipeline.id>",由它再调用你的 submit_pipeline()

4. 实现步骤小结

  1. 复制 myapp/views/view_etl_pipeline_etl.pyview_etl_pipeline_<引擎名>.py,重命名类为 <引擎名大写>_ETL_PIPELINE
  2. __init__ 里的 host 改成你的调度系统地址;
  3. 按上表实现 all_templatepipeline_config_uipipeline_jump_buttonpipeline_run_buttonsubmit_pipelinedelete_pipeline
  4. view_etl_pipeline.py:242-250workflow choices 里加上该引擎;
  5. 新建 ETL 任务流时选择该计算引擎,即会使用你的实现类。

相关源码

内容 位置
workflow(计算引擎)字段 / choices myapp/views/view_etl_pipeline.py:242-250
引擎实现类的动态加载约定 myapp/views/view_etl_pipeline.py:479-480:524-525:568-569:323-324
模板列表接口(调 all_template myapp/views/view_etl_pipeline.py:516-537
提交接口(调 submit_pipeline myapp/views/view_etl_pipeline.py:563-570
删除清理(调 delete_pipeline myapp/views/view_etl_pipeline.py:305-325
参考实现:Airflow 风格模板/桩 myapp/views/view_etl_pipeline_etl.pyETL_ETL_PIPELINE
参考实现:内置数据分析 runner myapp/views/view_etl_pipeline_data_analysis.pyDATA_ANALYSIS_ETL_PIPELINE
ETL 数据模型 myapp/models/model_etl_pipeline.py
最后更新 2026-06-30完整文档以官方仓库为准:GitHub Wiki