argoproj/argo-workflows · error
Should specify a node when we get archived logs
Error message
Should specify a node when we get archived logs
What it means
getContainerLogsFromArtifact fetches logs from stored log artifacts instead of live pods. When the workflow has no matching log artifact (hasArtifactLogs is false) and no nodeId was supplied, the service cannot disambiguate which archived pod's logs to fetch, so it throws this error. It guards the archived-logs path where a node identifier is mandatory.
Source
Thrown at ui/src/shared/services/workflows-service.ts:244
},
async isWorkflowNodePendingOrRunning(workflow: Workflow, nodeId?: string) {
// We always refresh the workflow rather than inspecting the state locally since it doubles
// as a check to determine whether or not the API is currently reachable
const updatedWorkflow = await this.get(workflow.metadata.namespace, workflow.metadata.name);
const node = updatedWorkflow.status.nodes[nodeId];
if (!node) {
return !updatedWorkflow.status || ['Pending', 'Running'].includes(updatedWorkflow.status.phase);
}
return isNodePendingOrRunning(node);
},
getContainerLogsFromArtifact(workflow: Workflow, nodeId: string, container: string, grep: string, archived: boolean): Observable<LogEntry> {
return of(hasArtifactLogs(workflow, nodeId, container)).pipe(
switchMap(isArtifactLogs => {
if (!isArtifactLogs) {
if (!nodeId) {
throw new Error('Should specify a node when we get archived logs');
}
throw new Error('no artifact logs are available');
}
return from(requests.get(this.getArtifactLogsPath(workflow, nodeId, container, archived)));
}),
mergeMap(r => r.text.split('\n')),
map(content => ({content, podName: workflow.status.nodes[nodeId].displayName}) as LogEntry),
filter(x => !!x.content.match(grep))
);
},
getContainerLogs(workflow: Workflow, podName: string, nodeId: string, container: string, grep: string, archived: boolean): Observable<LogEntry> {
const getLogsFromArtifact = () => this.getContainerLogsFromArtifact(workflow, nodeId, container, grep, archived);
const getLogsFromCluster = () => this.getContainerLogsFromCluster(workflow, podName, container, grep);
// If our workflow was deleted, try to get logs from artifacts.
if (!isWorkflowInCluster(workflow)) {View on GitHub (pinned to 35bff19146)
Solutions
- Pass the workflow node's ID (workflow.status.nodes[...].id) as the nodeId argument to getLogsFromArtifact.
- Verify the node actually produced log artifacts by checking workflow.status.nodes[nodeId].id for a outputs.artifacts entry with artifactLogs.
- If logs are genuinely absent, show a 'no artifact logs are available' message instead of retrying.
Example fix
// before getLogsFromArtifact(wf, '', 'main', '', true); // after const nodeId = Object.values(wf.status.nodes).find(n => n.templateName === 'main')?.id; getLogsFromArtifact(wf, nodeId, 'main', '', true);
Defensive patterns
Strategy: validation
Validate before calling
if (!nodeId || !workflow.status?.nodes?.[nodeId]) {
throw new Error('nodeId is required to fetch archived logs');
}
getContainerLogsFromArtifact(workflow, nodeId, container, grep, archived); Type guard
function hasNode(wf: Workflow, nodeId: string): boolean {
return !!wf.status?.nodes && nodeId in wf.status.nodes;
} Try / catch
try {
await getLogsFromArtifact(wf, nodeId, container, grep, archived).toPromise();
} catch (e) {
if (e.message.includes('Should specify a node')) {
logger.warn('Cannot fetch archived logs without a node ID');
}
} Prevention
- Always resolve nodeId from workflow.status.nodes before calling archived log APIs.
- Check hasArtifactLogs upstream before switching to the artifact path.
- Keep the original node ID in UI state when workflows are archived.
When it happens
Trigger: Calling getContainerLogsFromArtifact (via getLogsFromArtifact) with archived=true or no live pod available, when hasArtifactLogs returns false AND the nodeId argument is an empty string.
Common situations: Viewing logs for an archived workflow whose node ID was never recorded in the UI state; passing only a pod name or container name while omitting nodeId; resuming a deleted workflow where node IDs were lost.
Understand the failure class
Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.
Related errors
- no artifact logs are available
- cron schedules must consist of 5 values only
- cron schedules must consist of 5 values only
- --since-time and --since cannot be used together
- index template error (err.Error())
AI-assisted analysis of argoproj/argo-workflows@35bff19146 (2026-09-03).
Data as JSON: /api/errors/3a11aa155e4142b6.
Report an issue: GitHub.