Validation Rules

Checking a diagram, saving it and editing it report each problem with a code, the element it concerns when there is one, and a one-line fix. This page lists every code those calls return and what to change for each.

For the rules and refusals below, fix is the first sentence of the message in the table, cut at 160 characters, where {name} stands for the value that fills it in. Drawing warnings and Mermaid notes give the whole line shown.

The Zindex skill covers what an agent does when a call fails or warns.

Scene and operation rules

A create and a check run these rules on the scene sent. An edit checks its operations against the diagram’s current revision, then checks the revision it makes. The diagram family rules apply only when the scene declares diagramFamily.

Document shape

CodeSeverityMessageWhat to change
SCHEMA_VALIDATION_ERRORerror{path}: {what the schema expects}Change the field at the path the fix names to what the schema allows: scene.schema.json for a scene, ops.schema.json for operations. An unknown property’s fix lists the valid ones.
OP_REMOVEDerror{op} was removed: {what to send instead}Drop the operation and do what the fix says. normalizeScene is gone because every save normalizes and lays out the diagram.

Size limits

CodeSeverityMessageWhat to change
CONTENT_LIMIT_EXCEEDEDerrorScene has {count} elements, exceeding limit of {maxElements}.Make the diagram smaller, or split it into several. The limits are 1,000 elements, 2,000 edges, containers nested 10 deep, 10,000 characters of text in one label or text element, and a canvas of 20,000 by 20,000.

IDs and styles

CodeSeverityMessageWhat to change
ELEMENT_ID_DUPLICATEerrorDuplicate element ID: ‘{id}’.Give each element its own id. The error has no element; the fix names the ID.
STYLE_NOT_FOUNDerrorStyle token ‘{style}’ not found in style registry.Add the token to the scene’s styles, or give the element an inline style object.

References

CodeSeverityMessageWhat to change
CHILD_ELEMENT_NOT_FOUNDerrorChild element ‘{child}’ referenced by {kind} ‘{id}’ does not exist.Create the child, or remove its ID from the container’s children.
EDGE_ENDPOINT_MISSINGerrorEdge ‘{id}’ is missing a ‘from’ endpoint with an elementId.Give the edge both from and to, each with an elementId.
EDGE_ENDPOINT_ELEMENT_NOT_FOUNDerrorEdge ‘{id}’ from-endpoint references element ‘{element}’ which does not exist.Point the endpoint at an element that exists. In an edit, create the element before the edge, in the same ops.
PORT_NOT_FOUNDerrorPort ‘{port}’ not found on node ‘{element}’.Use a port the node lists in ports, or one of left, right, top, bottom and center, or leave portId out.
EDGE_COLUMN_NOT_FOUNDwarningEdge ‘{edge}’ {side}-endpoint references column ‘{column}’ on element ‘{element}’, but no such column is declared in extensions.columns{available columns}.Set the endpoint’s column to one the fix lists, or remove it. Without it the edge meets the middle of the entity’s side.

Groups and frames

CodeSeverityMessageWhat to change
SELF_CONTAINMENTerrorContainer ‘{id}’ cannot contain itself.Remove the container’s own ID from its children.
INVALID_CHILD_KIND_FOR_CONTAINERerrorGuide element ‘{child}’ cannot be a child of {kind} ‘{id}’.Remove the guide from children. Guides can’t be grouped or framed.
MULTIPLE_GROUP_MEMBERSHIPerrorElement ‘{child}’ belongs to multiple groups: {groups}.Keep the element in the children of one group only.
MULTIPLE_FRAME_MEMBERSHIPerrorElement ‘{child}’ belongs to multiple frames: {frames}.Keep the element in the children of one frame only. To nest frames, list the inner frame in the outer frame’s children.
CONTAINMENT_CYCLEerrorContainment cycle detected involving ‘{node}’.Break the loop: no container may contain, directly or through others, a container that contains it.

Layout

CodeSeverityMessageWhat to change
RELATIVE_SELF_REFERENCEerrorElement ‘{id}’ references itself in relative placement.Place the element relative to another element.
RELATIVE_TARGET_NOT_FOUNDerrorRelative placement target ‘{target}’ does not exist.Name an element that exists in place, or give the element an absolute layout.
INVALID_INSIDE_TARGETerror’inside’ target ‘{target}’ is ‘{kind}’, not a container (group, frame, or container node).inside takes a group, a frame or a container node. Point it at one, or use rightOf, leftOf, above or below.
INVALID_ELEMENT_DIMENSIONSwarningElement ‘{id}’ has zero-size dimensions.Give the element a width and height above 0, or set visible: false to hide it.
RELATIVE_LAYOUT_CYCLEerrorRelative layout cycle detected involving ‘{node}’.Break the chain: give one of its elements an absolute layout, or remove the relative layouts and let layoutStrategy place them.

Constraints

CodeSeverityMessageWhat to change
CONSTRAINT_TARGET_NOT_FOUNDerrorOrder constraint references nonexistent element ‘{source}’.Name elements that exist, or remove the missing ones from the constraint.
ORDER_CONSTRAINT_SELF_REFERENCEerrorOrder constraint source and target are the same element ‘{source}’.Give the order constraint two different elements as source and target.
CONSTRAINT_INSUFFICIENT_MEMBERSwarningConstraint ‘{type}’ should have at least 2 elements, got {count}.List at least two elements, or remove the constraint.
CONSTRAINT_DUPLICATE_MEMBERwarningElement ‘{id}’ appears more than once in constraint.List each element once.
ORDER_CONSTRAINT_CYCLEwarningOrder constraints form a cycle involving: {cycleNodes}. Layout will degrade gracefully.Remove one of the order constraints in the loop. Until then the layout ignores the ones it can’t satisfy.
ORDER_CONSTRAINT_CONTRADICTIONwarningOrder constraints contradict: ‘{source}’ and ‘{target}’ have both sameRank and a directional ordering.Keep either the sameRank constraint or the directional one for the pair.

Edges, ports, icons and images

CodeSeverityMessageWhat to change
ASSET_NOT_FOUNDerrorAsset ‘{assetRef}’ referenced by image ‘{id}’ not found.Add the asset to the scene’s assets, or point assetRef at one that exists.
ASSET_KIND_MISMATCHwarningImage ‘{id}’ references asset ‘{assetRef}’ of kind ‘{kind}’, expected ‘image’.Point assetRef at an asset whose kind is image.
EMPTY_TEXT_WARNINGwarningText element ‘{id}’ has empty text.Give the element some text, or delete it.
PORTS_NOT_ALLOWED_ON_KINDwarningPorts are not allowed on ‘{kind}’ element ‘{id}’. Only nodes should define ports.Remove ports. Only nodes have ports.
PORT_ID_DUPLICATEerrorDuplicate port ID ‘{port}’ on node ‘{id}’.Give each port on the node its own id.
ICON_KEY_INVALID_FORMATwarningIcon key ‘{icon}’ does not match expected format ‘{family}:{identifier}’ (e.g. ‘lucide:database’).Use family:name, such as lucide:database or aws:lambda, or an image URL.
EDGE_ENDPOINT_KIND_INVALIDwarningEdge ‘{id}’ connects from ‘{kind}’ element ‘{element}’ which is not a connectable kind.Connect the edge to a node. An edge to a frame or group is drawn to its border, so keep it when the edge means the whole container.
SELF_LOOP_EDGE_WARNINGwarningEdge ‘{id}’ is a self-loop on element ‘{element}’.Keep it when the element really calls itself, as a sequence diagram’s self-message does. Otherwise point one end at another element.
ASSET_URI_POLICY_VIOLATIONwarningAsset ‘{asset}’ uses remote URI ‘{uri}’ but remote assets are not allowed by policy.Embed the image as a data: URI. Remote assets aren’t fetched.

Diagram family rules

CodeSeverityMessageWhat to change
FAMILY_WORKFLOW_NO_STARTwarningWorkflow diagram has no start node. Consider adding workflow.start or workflow.messageStart.Add a workflow.start or workflow.messageStart node.
FAMILY_WORKFLOW_NO_ENDwarningWorkflow diagram has no end node. Consider adding workflow.end, workflow.terminate, or workflow.messageEnd.Add a workflow.end, workflow.terminate or workflow.messageEnd node.
FAMILY_WORKFLOW_DECISION_FEW_OUTPUTSwarningDecision/gateway node ‘{node}’ has {count} outgoing edge(s). Expected ≥2.Give the gateway a second outgoing flow, or make it a workflow.task.
FAMILY_WORKFLOW_TERMINATE_HAS_OUTGOINGwarningTerminate end event ‘{node}’ has outgoing edges. Terminate events should end the process.Remove the flows leaving the terminate event, or make it a workflow.end.
FAMILY_WORKFLOW_EVENT_GATEWAY_FEW_OUTPUTSwarningEvent-based gateway ‘{gateway}’ has {count} outgoing edge(s). Expected ≥2.Give the event-based gateway an outgoing flow for each event it waits for, at least two.
FAMILY_ER_ISOLATED_ENTITYwarningER entity ‘{entity}’ has no connected edges.Connect the entity to another with an er.relationship edge, or remove it.
FAMILY_ER_MISSING_CARDINALITYwarningER edge ‘{edge}’ has no cardinality at {where}: set cardinality there, or anchor it at a column marked pk or fk so it’s inferred.Set cardinality on the end it names (one, many, zero-or-one, zero-or-many or one-or-many), or anchor that end at a column with from.column or to.column: a pk column is inferred as one, an fk column as many (zero-or-many if nullable, one if unique). An end without a column on an entity with a single primary key anchors at that key.
FAMILY_SEQ_NO_LIFELINESwarningSequence diagram has no lifeline or actor nodes.Add sequence.lifeline or sequence.actor nodes.
FAMILY_SEQ_ORPHAN_MESSAGEwarningSequence message ‘{edge}’ references a non-lifeline node.Connect both ends of the message to lifelines or actors.
FAMILY_SEQ_NO_MESSAGESwarningSequence diagram has lifelines but no messages.Add messages: sequence.* edges between the lifelines.
FAMILY_SEQ_EMPTY_FRAGMENTwarningCombined fragment ‘{frame}’ has no children.List the fragment’s messages in its children, or remove the fragment.
FAMILY_SEQ_NOTE_INVALID_ANCHORwarningsequence.note ‘{note}’ has no extensions.anchor; it will not be positioned.Set the note’s extensions.anchor to a lifeline ID, or to an array of two or more lifeline IDs for a note across them.
FAMILY_SEQ_NOTE_ANCHOR_NOT_FOUNDwarningsequence.note ‘{note}’ anchor ‘{anchor}’ is not a sequence.lifeline / sequence.actor in this scene.Anchor the note to lifelines or actors that exist.
FAMILY_SEQ_NOTE_ANCHOR_TOO_SHORTwarningsequence.note ‘{note}’ anchor array has length {count}; use a single string for “right of” semantics or an array of >= 2 lifeline ids for “over” span semantics.Use one lifeline ID as a string, or two or more in the array.
FAMILY_ORG_NO_PEOPLEwarningOrg chart has no org.person or org.role nodes.Add org.person or org.role nodes.
FAMILY_UI_NO_SCREENSwarningUI flow diagram has no uiflow.screen nodes.Add uiflow.screen nodes.
FAMILY_UI_NO_ENTRYwarningUI flow diagram has no uiflow.entry node.Add a uiflow.entry node where the flow starts.
FAMILY_UI_ORPHAN_SCREENwarningScreen ‘{screen}’ has no connected edges.Connect the screen to the flow with an edge, or remove it.

Operations (edits only)

CodeSeverityMessageWhat to change
OP_ID_ALREADY_EXISTSerrorElement ID ‘{id}’ already exists in scene or was created earlier in this batch.Use a new ID, or change the existing element with updateNode or updateEdge.
OP_TARGET_NOT_FOUNDerrorTarget element ‘{id}’ does not exist.Read the diagram again for its current IDs, or create the element earlier in the same ops.
OP_TARGET_KIND_MISMATCHerrorOperation ‘{op}’ expects target kind ‘{expectedKind}’ but ‘{id}’ is ‘{kind}’.Use the operation for the element’s kind: updateNode for a node, updateEdge for an edge.
TEXT_OPERATION_KIND_INVALIDerrorsetText not supported on element kind ‘{kind}’.setText changes nodes, edges and text elements only.
RESIZE_NOT_SUPPORTEDerrorresizeElement not supported on element kind ‘{kind}’.resizeElement changes nodes, frames, images and text elements only.
MOVE_NOT_ALLOWED_FOR_RELATIVE_LAYOUTerrorCannot move element ‘{id}’ which has relative layout.Change the element’s layout with updateNode instead of moving it.
STYLE_OPERATION_NO_EFFECTwarningsetStyle on ‘{id}’ has no effect: its style is already ‘{style}’.Drop the operation: the element already has that style.
AUTO_LAYOUT_SELECTION_EMPTYerrorautoLayout with scope=‘selection’ requires a non-empty ‘elements’ array.List the elements to lay out in elements, or use another scope.

What drawing notices

A valid scene is also laid out and drawn, when it is checked, saved or edited. These warnings come from that drawing, and their fix gives the figures you need.

CodeSeverityMessageWhat to change
LABEL_DUPLICATION_DETECTEDwarningEdges {edges} share the label ‘{label}’: merge them or give each its own label.Give one of the edges a more specific label with updateEdge, such as “route to users” instead of “route”, or merge the edges. Sequence messages may repeat a label at different times.
NODE_OVERLAP_DETECTEDwarningIt overlaps ‘{other node}’: move one of them, or set its layout x and y to 0 so the engine places it in free space.Move one of the two nodes with updateNode, or give one of them layout.x: 0 and layout.y: 0 with updateNode: a node at exactly (0, 0) counts as not placed, and the engine places it next to its neighbours, clear of other nodes.
TEXT_OVERFLOWwarningIts text needs about {requiredHeight}px of height and has {availableHeight}px: make it taller or wider, or wrap the text.Make the element as tall as the fix says, or wider, or wrap its text with textStyle.wrap: "word". Leaving layout off lets the engine size the node.

Laying out a scene notices more than this, such as a canvas it had to grow. The engine handles those cases itself, and the API doesn’t return them; Rendering: Render diagnostics describes what it does.

When an edit can’t be applied

An edit that passes the rules can still fail when it runs. These come back in errors with 422 VALIDATION_FAILED, and nothing is saved.

CodeSeverityMessageWhat to change
RESTORE_NOT_ALONEerrorrestoreRevision must be the only operation in its edit.Send restoreRevision in an edit of its own, or use the edit’s restoreRevision argument instead of ops.
RESTORE_REVISION_INVALIDerrorrestoreRevision needs a revision number (1 or more).Give the restoreRevision operation a revision number. To restore by date, use the edit’s restoreRevision: { "asOf": ... } argument.
REVISION_NOT_FOUNDerrorRevision {target} of scene ‘{scene}’ not found.Restore a revision that exists: diagram_history lists them.
OP_APPLY_FAILEDerrorTarget element ‘{id}’ not found for operation ‘{op}‘Read the diagram again for its current IDs and send the edit with the new baseRevision.

A stale baseRevision, a reused requestId and a missing diagram have error codes of their own: REVISION_CONFLICT, REQUEST_ID_REUSED and NOT_FOUND. Diagrams API: Errors lists them.

Mermaid notes

A create, check or edit sent as Mermaid adds a note to warnings for each part of the text that Zindex draws differently or leaves out. None of them blocks a save. A read with view=mermaid returns notes of the same shape in notes.

CodeMessageWhat to change
FENCE_USEDThe first ```mermaid block in the text was used.Nothing to change. Send the Mermaid alone to drop the note.
COMMENT_NOT_SHOWNAttribute comments on {name} are kept but not drawn.Nothing to change: the comment stays with the column.
CONSTRUCT_DROPPEDA relationship between {a} and {b} refers to an entity that wasn’t found, so it was left out.Declare the entity a relationship names, or leave the relationship out. Invisible links (~~~) are always left out.
CARDINALITY_APPROXIMATEDThe cardinality {cardB}/{cardA} isn’t drawn exactly; the engine infers it from the columns instead.Nothing to change, or set the edge’s cardinality with updateEdge after saving.
SHAPE_APPROXIMATEDMermaid shape ‘{shape}’ is drawn as {nodeType}.Nothing to change, or set the node’s shape with updateNode after saving.
LABEL_MARKUP_REMOVEDHTML or Markdown in the label was removed.Write the label as plain text.
ARROW_APPROXIMATEDMermaid arrow ‘{type}’ is drawn with a {end} end.Nothing to change, or set the edge’s endpoints with updateEdge after saving.
SUBGRAPH_DROPPEDSubgraph ‘{subgraph}’ was left out; its {count} nodes were kept. Zindex doesn’t draw Mermaid subgraphs yet.Nothing to change: the nodes are kept. To group them, add a frame with createFrame after saving.
STYLE_DROPPEDMermaid styles (style, classDef, class) were left out; set styles on the elements instead.Style the elements with setStyle after saving.
FRAMES_NOT_CHANGEDA Mermaid edit doesn’t change frames or groups yet, so the subgraph changes to {named}{more} were not made. Change frames with ops (createFrame, groupElements, deleteElement).Change frames and groups with operations (createFrame, groupElements, deleteElement). A Mermaid edit leaves them as they are.