mastra-ai/mastra · error
Workflow definition graph must be an array.
Error message
Workflow definition graph must be an array.
What it means
normalizeWorkflowBuilderDefinition first JSON-normalizes the input, then requires `graph` to be an array of step entries. If graph is missing or of another type (object, string, null after deletion), this TypeError is thrown because the workflow's step list cannot be processed.
Solutions
- Ensure the definition includes `graph` as an array of step entries.
- Fix the property name (e.g. rename `steps`/`flow` to `graph`) when hand-writing or migrating definitions.
- Validate stored definitions against the current schema before calling normalizeWorkflowBuilderDefinition, and prefer the builder API (createWorkflow + .then/.map) over hand-built definitions.
Example fix
// before
const def = { id: 'w', name: 'W', steps: [{ type: 'step', id: 'a' }] };
normalizeWorkflowBuilderDefinition(def);
// after
const def = { id: 'w', name: 'W', graph: [{ type: 'step', id: 'a' }] };
normalizeWorkflowBuilderDefinition(def); Defensive patterns
Strategy: validation
Validate before calling
function isValidDefinition(def) {
return def != null && typeof def === 'object' && Array.isArray(def.graph);
}
if (!isValidDefinition(input)) throw new TypeError('Definition must have a graph array'); Type guard
function isWorkflowBuilderDefinition(d: unknown): d is { graph: unknown[] } & Record<string, unknown> {
return typeof d === 'object' && d !== null && Array.isArray((d as any).graph);
} Try / catch
try {
const def = normalizeWorkflowBuilderDefinition(input);
} catch (e) {
if (e instanceof TypeError && e.message.includes('graph must be an array')) {
// repair/replace definition or surface a config error
}
throw e;
} Prevention
- Always build definitions via the builder API rather than hand-writing objects.
- Key the step list as `graph`, not `steps` or `flow`.
- Validate persisted definitions against the current schema after migrations.
- Write a round-trip test: normalize → serialize → normalize.
When it happens
Trigger: Calling normalizeWorkflowBuilderDefinition or createWorkflow with a definition whose `graph` field is undefined, null, an object, or a string — e.g. a hand-written definition `{ id, name, steps: [...] }` that uses the wrong key instead of `graph`.
Common situations: Hand-authoring serialized workflow definitions with the wrong property name; loading a stored definition from an older schema version that used a different field; a migration that dropped `graph`; JSON deserialization that omitted the field.
Understand the failure class
Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.
Related errors
- Request context validation failed for workflow
- Tool must have input and output schemas defined
- WORKFLOW_SCHEMA_VALIDATION_FAILED
- A custom capture schema requires an onExtracted hook that…
- Custom Subconscious observation agent
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/856079f92437c9a1.
Report an issue: GitHub.
Appendix: source
Thrown at packages/core/src/workflows/builder/index.ts:203
}
if ((normalized.type === 'parallel' || normalized.type === 'conditional') && Array.isArray(normalized.steps)) {
normalized.steps = normalized.steps.map(step =>
normalizeEntry(step as Record<string, unknown>),
) as unknown as WorkflowBuilderJsonValue[];
}
if ((normalized.type === 'foreach' || normalized.type === 'loop') && normalized.step) {
normalized.step = normalizeEntry(normalized.step as Record<string, unknown>) as unknown as WorkflowBuilderJsonValue;
}
return normalized as unknown as WorkflowBuilderGraphEntry;
}
export function normalizeWorkflowBuilderDefinition(input: unknown): WorkflowBuilderDefinition {
const normalized = normalizeJsonValue(input, 'workflow definition', new Set()) as WorkflowBuilderJsonObject;
if (normalized.description === null) delete normalized.description;
if (normalized.metadata === null) delete normalized.metadata;
if (normalized.stateSchema === null) delete normalized.stateSchema;
if (normalized.requestContextSchema === null) delete normalized.requestContextSchema;
if (!Array.isArray(normalized.graph)) throw new TypeError('Workflow definition graph must be an array.');
normalized.graph = normalized.graph.map(entry =>
normalizeEntry(entry as Record<string, unknown>),
) as unknown as WorkflowBuilderJsonValue[];
return normalized as unknown as WorkflowBuilderDefinition;
}
export * from './preflight';
export * from './inspection';
export * from './authoring-schema';
export * from './agent';
View on GitHub (pinned to 75dd419e61)