Skip to content

Artifact "Cycle" Crashes UI #13395

Closed
@andrewm-aero

Description

@andrewm-aero

Pre-requisites

  • I have double-checked my configuration
  • I have tested with the :latest image tag (i.e. quay.io/argoproj/workflow-controller:latest) and can confirm the issue still exists on :latest. If not, I have explained why, in detail, in my description below.
  • I have searched existing issues and could not find a match for this bug
  • I'd like to contribute the fix myself (see contributing guide)

What happened? What did you expect to happen?

When viewing a workflow in the UI that has an "artifact cycle", that is, an input artifact is later overwritten as an output artifact of a later step/task, the UI crashes with the following error

Maximum call stack size exceeded
 [Reload this page](javascript:document.location.reload();) to try again.

Stack Trace
RangeError: Maximum call stack size exceeded
    at Map.forEach (<anonymous>)
    at e.outgoingEdges (https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1859902)
    at e.visit (https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841652)
    at https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841699
    at Array.forEach (<anonymous>)
    at e.visit (https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841669)
    at https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841699
    at Array.forEach (<anonymous>)
    at e.visit (https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841669)
    at https://<redacted>/main.1e7905924d7399ee8ad2.js:2:1841699
Component Stack

    in Fn
    in t
    in Ri
    in div
    in div
    in div
    in div
    in div
    in Mr
    in us
    in t
    in t
    in component
    in t
    in t
    in t
    in div
    in div
    in Pt
    in t
    in t
    in rl
    in al

While this is baseless speculation, I suspect the issue is that whatever code is (correctly) assuming that the node graph is acyclic, is also (incorrectly) assuming that artifacts are acyclic.

For context, this pattern is useful to record a "high watermark", and have the workflow terminate or skip steps if e.g. no new data is available for processing, but update the same object with a new watermark after processing new data. This is particularly useful when combined with a CronWorkflow that periodically checks for and processes new data.

The attached workflow crashes the only ONLY when the "use faster, but less pretty ..." and "toggle artifacts" options are selected, and was tested with the initials contents of the s3 artifact as {"this": "is a test file"}.

Version(s)

v3.5.8

Paste a minimal workflow that reproduces the issue. We must be able to run the workflow; don't enter a workflows that uses private images.

apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
  generateName: stack-overflow-test-
spec:
  podGC:
    strategy: OnWorkflowCompletion
  entrypoint: main
  templates:
    # Main function
    - name: main
      steps:
      - - name: step-a
          template: step-a
          arguments:
            artifacts:
              - name: test
                archive:
                  none: {}
                s3:
                  accessKeySecret:
                    key: AWS_ACCESS_KEY_ID
                    name: <redacted>
                  bucket: <redacted>
                  endpoint: <redacted>
                  insecure: false
                  key: stack-overflow-test
                  region: <redacted>
                  secretKeySecret:
                    key: AWS_SECRET_ACCESS_KEY
                    name: <redacted>
      
      - - name: step-b
          template: step-b
          arguments:
            parameters:
            - name: test
              value: "{{=sprig.fromJson(steps['step-a'].outputs.parameters['test'])['this']}}"
          

      - - name: step-c
          when: "{{=steps['step-b'].outputs.parameters['test'] != ''}}"
          template: step-c
          arguments:
            parameters:
            - name: test
              value: "{{=sprig.fromJson(steps['step-b'].outputs.parameters['test'])['that']}}"
          

      - - name: step-d
          when: "{{=steps['step-b'].outputs.parameters['test'] != ''}}"
          arguments:
            artifacts:
            - name: test
              from: '{{steps.step-b.outputs.artifacts.test}}' 
          inline: 
            inputs:
              artifacts:
              - name: test
                path: /tmp/test
                archive:
                  none: {}
            outputs:
              artifacts:
              - name: test
                path: /tmp/test
                archive:
                  none: {}
                s3:
                  accessKeySecret:
                    key: AWS_ACCESS_KEY_ID
                    name: <redacted>
                  bucket: <redacted>
                  endpoint: <redacted>
                  insecure: false
                  key: stack-overflow-test
                  region: <redacted>
                  secretKeySecret:
                    key: AWS_SECRET_ACCESS_KEY
                    name: <redacted>
            container:
              image: docker.io/argoproj/argosay:v2
              command: [/argosay, echo, 'This is a test']

    - name: step-a
      inputs:
        artifacts:
        - name: test
          path: /tmp/test
          archive:
            none: {}
      outputs:
        artifacts:
        - name: test
          path: /tmp/test
          archive:
            none: {}
        parameters:
        - name: test
          valueFrom:
            path: /tmp/test
      container:
        image: docker.io/argoproj/argosay:v2
        command: [/argosay, echo, 'This is a test']
    - name: step-b
      inputs:
        parameters:
        - name: test
      outputs:
        artifacts:
        - name: test
          path: /tmp/test
          archive:
            none: {}
        parameters:
        - name: test
          valueFrom:
            path: /tmp/test
      script:
        image: docker.io/library/alpine:3
        command: [/bin/sh, -xec]
        env:
        - name: TEST
          value: '{{inputs.parameters.test}}'
        args:
        - |
          echo '{"that": "'"${TEST}"'"}' > /tmp/test
    - name: step-c
      inputs:
        parameters:
        - name: test
      
      container:
        image: docker.io/argoproj/argosay:v2
        command: [/argosay, echo, 'This is a test']
      

Logs from the workflow controller

N/A

Logs from in your workflow's wait container

N/A

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions