Description
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