windmill-labs/windmill · error · Error

validationErrors.join('\n')

Error message

validationErrors.join('\n')

What it means

In frontend/src/lib/components/FlowBuilder.svelte:467, saveFlow() collects client-side validationErrors and throws them joined by newlines, aborting the save. The message is the aggregated list of flow validation problems (missing required fields, invalid module settings, etc.).

Source

Thrown at frontend/src/lib/components/FlowBuilder.svelte:467

			if (flow.value?.modules) {
				const validationErrors: string[] = []
				dfsApply(flow.value.modules, (module) => {
					const error = validateRetryConfig(module.retry)
					if (error) {
						validationErrors.push(`Step '${module.id}': ${error}`)
					}
				})

				if (flow.value.failure_module) {
					// add validation logic here for failure module
				}

				if (flow.value.preprocessor_module) {
					// add validation logic here for preprocessor module
				}

				if (validationErrors.length > 0) {
					throw new Error(validationErrors.join('\n'))
				}
			}
			// console.log('flow', computeUnlockedSteps(flow)) // del
			// loadingSave = false // del
			// return

			// `newFlow` comes from the embedder, and updating a path that has no
			// deployed flow 404s. Confirm with the server before taking the update
			// branch so a first deploy still lands.
			let isNewFlow = newFlow
			if (!isNewFlow) {
				try {
					isNewFlow =
						initialPath === '' ||
						!(await FlowService.existsFlowByPath({ workspace: opWorkspace!, path: initialPath }))
				} catch (err) {
					// Unreachable check: keep the caller's intent rather than failing the deploy.
					console.error('Could not check flow existence', err)

View on GitHub (pinned to e474e8803c)

Solutions

  1. Read the multi-line message — each line is one problem — and fix them in the builder UI
  2. Check required fields on each step (inputs, summary)
  3. Remove/reconnect dangling references to deleted steps
  4. Re-open the flow if the editor state went stale, then re-validate
Defensive patterns

Strategy: try-catch

Validate before calling

const errs = validateFlowLocally(flow.value);
if (errs.length > 0) {
  sendUserToast('Fix validation errors before saving:\n' + errs.join('\n'), true);
  return; // don't call saveFlow
}

Type guard

null

Try / catch

try {
  await saveFlow();
} catch (e) {
  if (typeof e.message === 'string' && e.message.includes('\n')) {
    e.message.split('\n').forEach(showFieldError);
  } else {
    throw e;
  }
}

Prevention

When it happens

Trigger: Clicking save/deploy while the flow has validation problems the builder detected — e.g. required step inputs empty, invalid paths, malformed schedule/suspend settings.

Common situations: Deleting a module a sibling still references; leaving a required input or summary empty; editing JSON forms manually and breaking constraints.

Related errors


AI-assisted analysis of windmill-labs/windmill@e474e8803c (2026-09-03). Data as JSON: /api/errors/144118a22ead34c6. Report an issue: GitHub.