kubernetesargo-workflowsargoproj

Unable to use jsonpath function for output parameter in Argo Workflows


I've one workflow in which I'm using jsonpath function for a output parameter to extract a specific value from json string, but it is failing with this error Error (exit code 255)

Here is my workflow

apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: wf-dev-
spec:
  entrypoint: main
  templates:
    - name: main

      dag:
        tasks:
          - name: dev-create
            templateRef:
              name: dev-create-wft
              template: main
            arguments:
              parameters:
                - name: param1
                  value: "val1"

          - name: dev-outputs
            depends: dev-create.Succeeded
            templateRef:
              name: dev-outputs-wft
              template: main
            arguments:
              parameters:
                - name: devoutputs
                  value: "{{=jsonpath(tasks.dev-create.outputs.parameters.devoutputs, '$.alias.value')}}"

In the above workflow task dev-create invokes another workflowTemplate dev-create-wft which returns the output of another workflowTemplate

Here is my workflowTemplate

apiVersion: argoproj.io/v1alpha1
kind: WorkflowTemplate
metadata:
  name: dev-create-wft

spec:
  entrypoint: main
  templates:
    - name: main
      outputs:
        parameters:
          - name: devoutputs
            valueFrom:
               expression: "tasks['dev1'].outputs.parameters.devoutputs"
      inputs:
        parameters:
          - name: param1
      dag:
        tasks:
          - name: dev1
            templateRef:
              name: fnl-dev
              template: main
            arguments:
              parameters:
                - name: param1
                  value: "{{inputs.parameters.param1}}"

The returned json output looks like this

{
    "alias": {
        "value": "testing:dev1infra",
        "type": "string",
        "sensitive": false
    },
    "match": {
        "value": "dev1infra-testing",
        "type": "string",
        "sensitive": false
    }
}

Does jsonpath function supported in workflow? The reason why am asking is, it's working when I used the same function in another workflowTemplate dev-outputs-wft

What could be the issue?


Solution

  • When an expression fails to evaluate, Argo Workflows simply does not substitute the expression with its evaluated value. Argo Workflows passes the expression as if it were the parameter.

    {{=}} "expression tag templates" in Argo Workflows must be written according to the expr language spec.

    In simple tag templates, Argo Workflows itself does the interpreting. So hyphens in parameter names are allowed. For example, value: "{{inputs.parameters.what-it-is}}" is evaluated by Argo Workflows to be value: "over 9000!".

    But in expression tag templates, expr interprets hyphens as minus operators. So value: "{{=inputs.parameters.what-it-is}}" looks like a really weird mathematical expression, fails, and isn't substituted. The workaround is to use ['what-it-is'] to access the appropriate map item.

    My guess is that your expression is failing, Argo Workflows is passing the expression to dev-outputs-wft un-replaced, and whatever shell script is receiving that parameter is breaking.

    If I'm right, the fix is easy:

               - name: dev-outputs
                 depends: dev-create.Succeeded
                 templateRef:
                   name: dev-outputs-wft
                   template: main
                 arguments:
                   parameters:
                     - name: devoutputs
    -                   value: "{{=jsonpath(tasks.dev-create.outputs.parameters.devoutputs, '$.alias.value')}}"
    +                   value: "{{=jsonpath(tasks['dev-create'].outputs.parameters.devoutputs, '$.alias.value')}}"