IF条件判断教程
当您在数据开发模块进行作业开发编排时,想要实现通过设置条件,选择不同的执行路径,可使用IF条件判断。
本教程包含以下三个常见场景举例。
IF条件的数据来源于EL表达式,通过EL表达式,根据具体的场景选择不同的EL表达式来达到目的。您可以参考本教程,根据您的实际业务需要,开发您自己的作业。
EL表达式用法可参考EL表达式。
根据前一个节点的执行状态进行IF条件判断
场景说明
根据前一个CDM节点是否执行成功,决定执行哪一个IF条件分支。基于图1的样例,说明如何设置IF条件。
配置方法
- 登录DataArts Studio控制台,找到所需要的DataArts Studio实例,单击实例卡片上的“进入控制台”,进入概览页面。
- 选择“空间管理”页签,在工作空间列表中,找到所需要的工作空间,单击工作空间的“数据开发”,系统跳转至数据开发页面。
- 在“作业开发”页面,新建数据开发作业,然后分别选择CDM节点和两个Dummy节点,选中连线图标并拖动,编排图1所示的作业。
其中CDM节点的失败策略需要设置为“继续执行下一节点”。
图2 配置CDM节点的失败策略
- 右键单击连线,选择“设置条件”,在弹出的“编辑EL表达式”文本框中输入IF条件。
每一个条件分支都需要填写IF条件,IF条件为通过EL表达式语法填写三元表达式。当三元表达式结果为true的时候,才会执行连线后面的节点,否则后续节点将被跳过。
此Demo中使用的EL表达式为“#{Job.getNodeStatus("node_name")}”,这个表达式的作用为获取指定节点的执行状态,成功状态返回success,失败状态返回fail。本例使用中,IF条件表达式分别为:
- 上面的A分支IF条件表达式为: #{(Job.getNodeStatus("CDM")) == "success" ? "true" : "false"}
- 下面的B分支IF条件表达式为:#{(Job.getNodeStatus("CDM")) == "fail" ? "true" : "false"}
输入IF条件表达式后,配置IF条件匹配失败策略,可选择仅跳过相邻的下一个节点,或者跳过该IF分支后续所有节点。配置完成后单击确定,保存作业。图3 配置失败策略
- 测试运行作业,并前往实例监控中查看执行结果。
- 待作业运行完成后,从实例监控中查看作业实例的运行结果,如图4所示。可以看到运行结果是符合预期的,当前CDM执行的结果为fail的时候,跳过A分支,执行B分支。
根据前一个节点的输出结果进行IF条件判断
场景说明
目标场景:通过HIVE SQL统计成绩在85分以上的人数,并将执行结果作为参数传递到下一个节点,通过与人数通过标准进行数值比较,然后决定执行哪一个IF条件分支。
场景分析:由于HIVE SQL节点的Select语句执行结果为单字段的二维数组,因此为获取二维数组中的值,EL表达式#{Loop.dataArray[][]}或#{Loop.current[]}均可以实现,且当前只有For Each节点支持Loop表达式,所以HIVE SQL节点后面需要连接一个For Each节点。
此场景下不能使用StringUtil表达式#{StringUtil.split(StringUtil.split(StringUtil.split(Job.getNodeOutput("前一节点名"),"]")[0],"[")[0],"\\"")[0]}替代Loop表达式,因为StringUtil表达式最终获取的数据类型为String,无法与标准数据Int比较大小。
作业编排如图5所示:
其中,For Each节点的关键配置如下:
- 数据集:数据集就是HIVE SQL节点的Select语句的执行结果。使用EL表达式#{Job.getNodeOutput('HIVE')},其中HIVE为前一个节点的名称。
- 子作业参数:子作业参数是子作业中定义的参数,可以将主作业前一个节点的输出,传递到子作业以供使用。此处变量名为result,其值为数据集中的某一列,使用EL表达式#{Loop.dataArray[0][0]}或#{Loop.current[]},本例以{Loop.dataArray[0][0]}为例进行说明。
而For Each节点中所选的子作业,需要根据For Each节点传过来的子作业参数,决定执行For Each中子作业的哪一个IF条件分支,作业编排如图6所示。
其中,子作业的关键配置为IF条件设置,本例使用表达式${result}获取作业参数的值。
此处不能使用EL表达式#{Job.getParam("job_param_name")} ,因为此表达式只能直接获取当前作业里配置的参数的value,并不能获取到父作业传递过来的参数值,也不能获取到工作空间里面配置的全局变量,作用域仅为本作业。
而表达式${job_param_name},既可以获取到父作业传递过来的参数值,也可以获取到全局配置的变量。
配置方法
开发子作业
- 登录DataArts Studio控制台,找到所需要的DataArts Studio实例,单击实例卡片上的“进入控制台”,进入概览页面。
- 选择“空间管理”页签,在工作空间列表中,找到所需要的工作空间,单击工作空间的“数据开发”,系统跳转至数据开发页面。
- 在“作业开发”页面,新建数据开发子作业For Each。选择四个Dummy节点,选中连线图标并拖动,编排图6所示的作业。
- 右键单击节点间的连线,选择“设置条件”,在弹出的“编辑EL表达式”文本框中输入IF条件。
每一个条件分支都需要填写IF条件,IF条件为通过EL表达式语法填写三元表达式。当三元表达式结果为true的时候,才会执行连线后面的节点,否则后续节点将被跳过。
- 上面的>5分支,IF条件表达式为:#{${result} > 5 ? "true" : "false"}
- 中间的=5分支,IF条件表达式为:#{${result} == 5 ? "true" : "false"}
- 下面的<5分支,IF条件表达式为:#{${result} < 5 ? "true" : "false"}
输入IF条件表达式后,配置IF条件匹配失败策略,可选择仅跳过相邻的下一个节点,或者跳过该IF分支后续所有节点。
表达式中包含多条件的场景下,可以通过“||”联合多个条件。例如:
#{(${result} >= 19 || ${result} <=9) ? "true" : "false"}
- 配置作业参数。此处需将参数名填写为result,仅用于主作业testif中的For Each节点识别子作业参数;参数值无需填写。
图7 配置作业参数
- 配置完成后保存作业。
开发主作业
- 在“作业开发”页面,新建数据开发主作业testif。选择HIVE SQL节点和For Each节点,选中连线图标并拖动,编排图5所示的作业。
- 配置HIVE SQL节点属性。此处配置为引用SQL脚本,SQL脚本的语句如下所示。其他节点属性参数无特殊要求。
--从student_score表中统计成绩在85分以上的人数-- SELECT count(*) FROM student_score WHERE score> "85" ;
图8 HIVE SQL脚本执行结果
- 配置For Each节点属性,如图9所示。
- 子作业:子作业选择已经开发完成的子作业“foreach”。
- 数据集:数据集就是HIVE SQL节点的Select语句的执行结果。使用EL表达式#{Job.getNodeOutput('HIVE')},其中HIVE为前一个节点的名称。
- 子作业参数:子作业参数是子作业中定义的参数,可以将主作业前一个节点的输出,传递到子作业以供使用。此处变量名为子作业参数名result,其值为数据集中的某一列,使用EL表达式#{Loop.dataArray[0][0]}。
- 配置完成后保存作业。
测试运行主作业
- 单击主作业画布上方的“测试运行”按钮,测试作业运行情况。主作业运行后,会通过For Each节点自动调用运行子作业。
- 单击左侧导航栏中的“实例监控”,进入实例监控中查看作业运行结果。
- 待作业运行完成后,从实例监控中查看子作业foreach的运行结果,如图10所示。可以看到运行结果是符合预期的,当前HIVE SQL执行的结果是4,所以>5和=5的分支被跳过,执行<5这个分支成功。
多IF条件下当前节点的执行策略
如果当前节点的执行依赖多个IF条件的节点,执行的策略包含逻辑或和逻辑与两种。
当执行策略配置为逻辑或,则表示多个IF判断条件只要任意一个满足条件,则执行当前节点。
当执行策略配置为逻辑与,则表示多个IF判断条件需要所有条件满足时,才执行当前节点。
如果没有配置执行策略,系统默认为逻辑或处理。
配置方法
配置执行策略
- 登录DataArts Studio控制台,找到所需要的DataArts Studio实例,单击实例卡片上的“进入控制台”,进入概览页面。
- 选择“空间管理”页签,在工作空间列表中,找到所需要的工作空间,单击工作空间的“数据开发”,系统跳转至数据开发页面。
- 在数据开发模块,单击“配置管理 > 配置”,单击“默认项配置”。
- “多IF策略”可设置为“逻辑与”或者“逻辑或”。
- 单击“保存”。
开发作业
- 在“作业开发”页面,新建一个数据开发作业。
- 拖动三个DWS SQL算子作为父节点,一个Python算子作为子节点,选中连线图标并拖动,编排图11所示的作业。
- 右键单击节点间的连线,选择“设置条件”,在弹出的“编辑EL表达式”文本框中输入IF条件。
每一个条件分支都需要填写IF条件,IF条件为通过EL表达式语法填写三元表达式。
- test1节点IF条件表达式为:#{(Job.getNodeStatus("test1")) == "success" ? "true" : "false"},
- test2节点IF条件表达式为:#{(Job.getNodeStatus("test2")) == "success" ? "true" : "false"},
- test3节点IF条件表达式为:#{(Job.getNodeStatus("test3")) == "success" ? "true" : "false"},
此处表达式均采用前一个节点的执行状态进行IF条件判断。
输入IF条件表达式后,配置IF条件匹配失败策略,可选择仅跳过相邻的下一个节点,或者跳过该IF分支后续所有节点。
测试运行作业