kubernetes - 如何将脚本模板的结果作为输入参数传递给 argo 工作流中 dag 中的另一个任务

标签 kubernetes argo-workflows

我创建了一个 WorkflowTemplate,我想在其中将脚本模板的结果作为输入参数传递给另一个任务

这是我的WorkflowTemplate

apiVersion: argoproj.io/v1alpha1
kind: WorkflowTemplate
metadata:
  name: dag-wft
spec:
  entrypoint: whalesay
  templates:
  - name: whalesay
    inputs:
      parameters:
        - name: message
          default: '["tests/hello", "templates/hello", "manifests/hello"]'
    dag:
      tasks:
        - name: prepare-lst
          template: prepare-list-script
          arguments:
            parameters:
              - name: message
                value: "{{inputs.parameters.message}}"

        - name: templates
          depends: prepare-lst
          templateRef:
            name: final-dag-wft
            template: whalesay-final
          arguments:
            parameters:
            - name: fnl_message
              value: "{{item}}"
          withParam: "{{tasks.prepare-lst.outputs.parameters.templates_lst}}"

        - name: manifests
          depends: prepare-lst && (templates.Succeeded || templates.Skipped)
          templateRef:
            name: final-dag-wft
            template: whalesay-final
          arguments:
            parameters:
            - name: fnl_message
              value: "{{item}}"
          withParam: "{{tasks.prepare-lst.outputs.parameters.manifests_lst}}"

  - name: prepare-list-script
    inputs:
      parameters:
        - name: message
    script:
      image: python
      command: [python]
      source: |
        manifests_lst = []
        # templates list preparation
        templates_lst = ['templates/' for template in "{{inputs.parameters.message}}" if 'templates/' in template]
        
        print(templates_lst)

        # manifests list preparation
        for i in "{{inputs.parameters.message}}":
          if 'templates/' not in i:
            manifests_lst.append(i)

        print(manifests_lst)

    outputs:
      parameters:
        - name: templates_lst
        - name: manifests_lst

在上面的脚本模板中,我添加了两个变量 templates_lstmanifests_lst 的打印语句。我想将这两个变量结果作为输入传递给 dag 中的其他两个任务。另外两个任务是 templatesmanifests

我访问输出值的方式是 "{{tasks.prepare-lst.outputs.parameters.templates_lst}}""{{tasks.prepare-lst.outputs .parameters.manifests_lst}}”。它不工作

我该怎么做?

最佳答案

<强>1。完全定义您的输出参数

您的输出参数规范不完整。您需要指定输出参数的来源

由于您有多个输出参数,您不能只使用标准输出 ({{tasks.prepare-lst.outputs.parameters.result}})。您必须编写两个文件并从每个文件中导出一个输出参数。

<强>2。加载 JSON 数组,使其可迭代

如果您遍历数组的字符串表示形式,您一次只会得到一个字符。

<强>3。使用环境变量将输入传递给 Python

虽然这不是绝对必要的,但我认为这是最佳实践。如果恶意行为者有能力设置 message 参数,他们就可以将 Python 注入(inject)到您的工作流程中。将参数作为环境变量传递,以便字符串保持为字符串。

变化:

   - name: prepare-list-script
     inputs:
       parameters:
         - name: message
     script:
       image: python
       command: [python]
+      env:
+      - name: MESSAGE
+        value: "{{inputs.parameters.message}}"
       source: |
+        import json
+        import os
+        message = json.loads(os.environ["MESSAGE"])
         manifests_lst = []
         # templates list preparation
-        templates_lst = ['templates/' for template in "{{inputs.parameters.message}}" if 'templates/' in template]
+        templates_lst = ['templates/' for template in message if 'templates/' in template]
         
-        print(templates_lst)
+        with open('/mnt/out/templates_lst.txt', 'w') as outfile:
+          outfile.write(str(json.dumps(templates_lst)))
 
         # manifests list preparation
         for i in "{{inputs.parameters.message}}":
           if 'templates/' not in i:
             manifests_lst.append(i)
 
-        print(manifests_lst)
+        with open('/mnt/out/manifests_lst.txt', 'w') as outfile:
+          outfile.write(str(json.dumps(manifests_lst)))
+      volumeMounts:
+      - name: out
+        mountPath: /mnt/out
+    volumes:
+    - name: out
+      emptyDir: { }
 
     outputs:
       parameters:
         - name: templates_lst
+          valueFrom:
+            path: /mnt/out/templates_lst.txt
         - name: manifests_lst
+          valueFrom:
+            path: /mnt/out/manifests_lst.txt

关于kubernetes - 如何将脚本模板的结果作为输入参数传递给 argo 工作流中 dag 中的另一个任务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70351103/

相关文章:

Kubernetes Ingress 无法访问(本地主机)

kubernetes - ingress-nginx、cert-manager 和 ingressClassName

apache-spark - Spark 2.3 提交 Kubernetes 错误

argo-workflows - 与 Argocd 类似,为 Argo 工作流程中的用户启用匿名只读访问

argo-workflows - 如何获得子工作流程步骤/任务输出?

jinja2 - 如何在 argo 工作流程中转义 "{{"和 "}}"

kubernetes - 使用 JSONPATH 获取 configmap 值

kubernetes - 使用 Argo Workflows 创建队列系统

argo-workflows - Argo 工作流程中命名空间安装与托管命名空间安装之间的区别?

kubernetes - 错误: the server doesn't have a resource type "svc"