windmill-labs/windmill · error · Error
Invalid note at index ${index}: size must be an object with
Error message
Invalid note at index ${index}: size must be an object with numeric width and height What it means
validateFlowNotes also checks the optional `size` of each flow note: when supplied it must be a plain object with numeric `width` and `height`. The library throws this error to reject sizes given in the wrong shape or with non-numeric values before notes are rendered on the flow.
Source
Thrown at frontend/src/lib/components/copilot/chat/flow/helperUtils.ts:214
typeof p !== 'object' ||
Array.isArray(n.position) ||
typeof p.x !== 'number' ||
typeof p.y !== 'number'
) {
throw new Error(
`Invalid note at index ${index}: position must be an object with numeric x and y`
)
}
}
if (n.size !== undefined && n.size !== null) {
const s = n.size as Record<string, unknown>
if (
typeof s !== 'object' ||
Array.isArray(n.size) ||
typeof s.width !== 'number' ||
typeof s.height !== 'number'
) {
throw new Error(
`Invalid note at index ${index}: size must be an object with numeric width and height`
)
}
}
if (type === 'group' && n.contained_node_ids !== undefined) {
if (
!Array.isArray(n.contained_node_ids) ||
n.contained_node_ids.some((id) => typeof id !== 'string')
) {
throw new Error(
`Invalid note at index ${index}: contained_node_ids must be an array of strings`
)
}
if (moduleIds) {
for (const id of n.contained_node_ids as string[]) {
if (!moduleIds.has(id)) {
throw new Error(
`Invalid note at index ${index}: contained_node_ids "${id}" does not match any flow module`View on GitHub (pinned to e474e8803c)
Solutions
- Coerce to numbers in an object: size: { width: Number(w), height: Number(h) }.
- Strip units from CSS-like strings before passing (parse "200px" to 200).
- Omit `size` to let the validator compute a size from the note text.
- Inspect the note at the reported index for the malformed size field.
Example fix
// before
notes: [{ id: 'n1', text: 'todo', size: { width: '200', height: '100' } }]
// after
notes: [{ id: 'n1', text: 'todo', size: { width: 200, height: 100 } }] Defensive patterns
Strategy: validation
Validate before calling
function hasValidSize(n) {
return n.size == null ||
(typeof n.size === 'object' && !Array.isArray(n.size) &&
typeof n.size.width === 'number' && typeof n.size.height === 'number')
}
notes.forEach((n, i) => { if (!hasValidSize(n)) throw new Error(`note ${i}: bad size`) }) Type guard
function isSize(s): s is { width: number; height: number } {
return typeof s === 'object' && s !== null && !Array.isArray(s) &&
typeof (s as any).width === 'number' && typeof (s as any).height === 'number'
} Try / catch
try {
validateFlowNotes(notes)
} catch (e) {
if (e.message.includes('size')) console.warn('dropping note size, will size from text')
} Prevention
- Use numeric width/height without units
- Parse CSS-like dimension strings into numbers first
- Omit size to let the validator derive it from the note text
When it happens
Trigger: Passing notes[i].size as "200x100", an array [200,100], or {width: "200", height: "100"} (string values), or omitting one of width/height, when invoking the note/flowTools tool.
Common situations: LLM-generated size fields arrive as strings; a caller copies CSS-style dimensions ("200px"); size is passed as a two-element array by habit from canvas APIs.
Related errors
- Invalid note at index ${index}: position must be an object w
- Invalid note at index ${index}: contained_node_ids must be a
- Invalid flow modules:\n${errors.join('\n')}
- Invalid failure_module: only "rawscript" and "script" module
- Flow notes must be an array
AI-assisted analysis of windmill-labs/windmill@e474e8803c (2026-09-03).
Data as JSON: /api/errors/3a0a060f855de4f8.
Report an issue: GitHub.