@tduniec/plugin-template-designer-foundation 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (78) hide show
  1. package/CHANGELOG.md +13 -0
  2. package/README.md +13 -0
  3. package/dist/api/useScaffolderActions.esm.js +59 -0
  4. package/dist/api/useScaffolderActions.esm.js.map +1 -0
  5. package/dist/components/FieldEditorDialog.esm.js +55 -0
  6. package/dist/components/FieldEditorDialog.esm.js.map +1 -0
  7. package/dist/components/Nodes/ActionNode.esm.js +613 -0
  8. package/dist/components/Nodes/ActionNode.esm.js.map +1 -0
  9. package/dist/components/Nodes/OutputNode.esm.js +373 -0
  10. package/dist/components/Nodes/OutputNode.esm.js.map +1 -0
  11. package/dist/components/Nodes/ParameterInputNode.esm.js +320 -0
  12. package/dist/components/Nodes/ParameterInputNode.esm.js.map +1 -0
  13. package/dist/components/Nodes/ParameterTitlesNode.esm.js +251 -0
  14. package/dist/components/Nodes/ParameterTitlesNode.esm.js.map +1 -0
  15. package/dist/components/Nodes/ParametersNode.esm.js +147 -0
  16. package/dist/components/Nodes/ParametersNode.esm.js.map +1 -0
  17. package/dist/components/Nodes/action/schema.esm.js +68 -0
  18. package/dist/components/Nodes/action/schema.esm.js.map +1 -0
  19. package/dist/components/Nodes/action/useActionInputs.esm.js +71 -0
  20. package/dist/components/Nodes/action/useActionInputs.esm.js.map +1 -0
  21. package/dist/components/Nodes/common/AutoWidthPopper.esm.js +11 -0
  22. package/dist/components/Nodes/common/AutoWidthPopper.esm.js.map +1 -0
  23. package/dist/components/Nodes/common/nodeInteraction.esm.js +20 -0
  24. package/dist/components/Nodes/common/nodeInteraction.esm.js.map +1 -0
  25. package/dist/components/Nodes/output/useOutputController.esm.js +125 -0
  26. package/dist/components/Nodes/output/useOutputController.esm.js.map +1 -0
  27. package/dist/components/TemplateDesigner/TemplateLanding.esm.js +157 -0
  28. package/dist/components/TemplateDesigner/TemplateLanding.esm.js.map +1 -0
  29. package/dist/components/TemplateDesigner/TemplateWorkspace.esm.js +416 -0
  30. package/dist/components/TemplateDesigner/TemplateWorkspace.esm.js.map +1 -0
  31. package/dist/components/TemplateDesigner/codemirrorTheme.esm.js +30 -0
  32. package/dist/components/TemplateDesigner/codemirrorTheme.esm.js.map +1 -0
  33. package/dist/components/TemplateDesigner/useFieldEditor.esm.js +95 -0
  34. package/dist/components/TemplateDesigner/useFieldEditor.esm.js.map +1 -0
  35. package/dist/components/TemplateDesignerIcon.esm.js +33 -0
  36. package/dist/components/TemplateDesignerIcon.esm.js.map +1 -0
  37. package/dist/components/designerFlowConfig.esm.js +13 -0
  38. package/dist/components/designerFlowConfig.esm.js.map +1 -0
  39. package/dist/designerFlow/DesignerFlow.esm.js +828 -0
  40. package/dist/designerFlow/DesignerFlow.esm.js.map +1 -0
  41. package/dist/designerFlow/handlers.esm.js +317 -0
  42. package/dist/designerFlow/handlers.esm.js.map +1 -0
  43. package/dist/designerFlow/model.esm.js +166 -0
  44. package/dist/designerFlow/model.esm.js.map +1 -0
  45. package/dist/designerFlow/nodeLayout.esm.js +108 -0
  46. package/dist/designerFlow/nodeLayout.esm.js.map +1 -0
  47. package/dist/designerFlow/parameterTransforms.esm.js +124 -0
  48. package/dist/designerFlow/parameterTransforms.esm.js.map +1 -0
  49. package/dist/designerFlow/utils/stableComparators.esm.js +69 -0
  50. package/dist/designerFlow/utils/stableComparators.esm.js.map +1 -0
  51. package/dist/foundation/actionNodeCustomization.esm.js +20 -0
  52. package/dist/foundation/actionNodeCustomization.esm.js.map +1 -0
  53. package/dist/foundation/actionNodeRegistry.esm.js +30 -0
  54. package/dist/foundation/actionNodeRegistry.esm.js.map +1 -0
  55. package/dist/foundation/featureFlags.esm.js +6 -0
  56. package/dist/foundation/featureFlags.esm.js.map +1 -0
  57. package/dist/foundation/templateSources.esm.js +16 -0
  58. package/dist/foundation/templateSources.esm.js.map +1 -0
  59. package/dist/index.d.ts +382 -0
  60. package/dist/index.esm.js +25 -0
  61. package/dist/index.esm.js.map +1 -0
  62. package/dist/state/templateUtils.esm.js +46 -0
  63. package/dist/state/templateUtils.esm.js.map +1 -0
  64. package/dist/state/useParameterSections.esm.js +162 -0
  65. package/dist/state/useParameterSections.esm.js.map +1 -0
  66. package/dist/state/useTemplateState.esm.js +627 -0
  67. package/dist/state/useTemplateState.esm.js.map +1 -0
  68. package/dist/types/flowNodes.esm.js +8 -0
  69. package/dist/types/flowNodes.esm.js.map +1 -0
  70. package/dist/utils/createSequentialEdges.esm.js +15 -0
  71. package/dist/utils/createSequentialEdges.esm.js.map +1 -0
  72. package/dist/utils/mocks/mocks.esm.js +120 -0
  73. package/dist/utils/mocks/mocks.esm.js.map +1 -0
  74. package/dist/utils/sampleTemplate.esm.js +40 -0
  75. package/dist/utils/sampleTemplate.esm.js.map +1 -0
  76. package/dist/utils/yamlJsonConversion.esm.js +47 -0
  77. package/dist/utils/yamlJsonConversion.esm.js.map +1 -0
  78. package/package.json +103 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DesignerFlow.esm.js","sources":["../../src/designerFlow/DesignerFlow.tsx"],"sourcesContent":["import {\n useCallback,\n useEffect,\n useMemo,\n useRef,\n useState,\n ComponentType,\n createElement,\n} from \"react\";\nimport type { MouseEvent as ReactMouseEvent } from \"react\";\nimport {\n ReactFlow,\n applyNodeChanges,\n applyEdgeChanges,\n addEdge,\n Node,\n Edge,\n NodeChange,\n EdgeChange,\n useNodesState,\n ReactFlowInstance,\n NodeProps,\n NodeTypes,\n Viewport,\n OnMoveEnd,\n OnMove,\n} from \"@xyflow/react\";\nimport \"@xyflow/react/dist/style.css\";\nimport type {\n ScaffolderTaskOutput,\n TaskStep,\n} from \"@backstage/plugin-scaffolder-common\";\nimport type {\n ActionNodeData,\n OutputNodeData,\n ParametersNodeData,\n TemplateParametersValue,\n} from \"../types/flowNodes\";\nimport {\n buildNodesFromModel,\n collectParameterReferences,\n collectStepOutputReferences,\n stableStringify,\n extractStepsFromNodes,\n extractParametersFromNodes,\n extractOutputFromNodes,\n} from \"./model\";\nimport { createSequentialEdges } from \"../utils/createSequentialEdges\";\nimport {\n buildEdgeHashMap,\n buildNodeHashMap,\n mergeEdgesWithStability,\n mergeNodesWithStability,\n} from \"./utils/stableComparators\";\nimport {\n createHandleAddNode,\n createHandleRemoveNode,\n createHandleRemoveInputKey,\n createHandleReorderAndAlignNodes,\n createHandleUpdateField,\n createHandleUpdateInput,\n createHandleUpdateOutput,\n createHandleUpdateSections,\n} from \"./handlers\";\nimport { alignNodes, resolveNodeHeightForTracking } from \"./nodeLayout\";\nimport {\n FLOW_LAYOUT,\n nodeDefaults as baseNodeDefaults,\n} from \"../components/designerFlowConfig\";\nimport { useScaffolderActions } from \"../api/useScaffolderActions\";\n\nconst EMPTY_EDGES: Edge[] = [];\nconst EMIT_DEBOUNCE_MS = 1200; // Emit only after user pauses typing for a bit (more relaxed UX).\nconst VIEWPORT_TUNING = {\n alignDebounceMs: 120, // Debounce view/align updates so typing isn't interrupted by layout thrash.\n centerDurationMs: 280,\n fitFallbackDelayMs: 50,\n};\n\n// Prevent benign ResizeObserver loop errors from bubbling to the dev overlay.\nif (\n typeof window !== \"undefined\" &&\n !(window as any).__rfResizeObserverPatched\n) {\n (window as any).__rfResizeObserverPatched = true;\n // Wrap ResizeObserver callbacks in rAF to avoid sync measurement loops that trigger the warning.\n if (typeof window.ResizeObserver === \"function\") {\n const OriginalResizeObserver = window.ResizeObserver;\n window.ResizeObserver = class extends OriginalResizeObserver {\n constructor(callback: ResizeObserverCallback) {\n super((entries, observer) => {\n window.requestAnimationFrame(() => callback(entries, observer));\n });\n }\n } as typeof ResizeObserver;\n }\n const shouldSwallow = (message: unknown) =>\n typeof message === \"string\" &&\n message.includes(\"ResizeObserver loop completed with undelivered\");\n const swallowResizeObserverError = (event: ErrorEvent) => {\n const message =\n event?.message || (event as any)?.error?.message || String(event);\n if (shouldSwallow(message)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n return true;\n }\n return undefined;\n };\n const swallowResizeObserverRejection = (event: PromiseRejectionEvent) => {\n const message = (event.reason as any)?.message ?? String(event.reason);\n if (shouldSwallow(message)) {\n event.preventDefault();\n event.stopImmediatePropagation();\n return true;\n }\n return undefined;\n };\n const swallowLoopEvent = (event: Event) => {\n event.preventDefault();\n event.stopImmediatePropagation();\n };\n const originalOnError = window.onerror;\n window.onerror = function handleResizeObserverOnError(\n message,\n source,\n lineno,\n colno,\n error\n ): boolean | void {\n if (\n shouldSwallow(\n typeof message === \"string\"\n ? message\n : (error as any)?.message ?? String(message)\n )\n ) {\n return true;\n }\n if (typeof originalOnError === \"function\") {\n return originalOnError(message, source, lineno, colno, error);\n }\n return undefined;\n };\n const originalOnUnhandledRejection = window.onunhandledrejection;\n window.onunhandledrejection = function handleResizeObserverOnUnhandled(\n event\n ) {\n const reason = (event as any)?.reason;\n const message =\n (reason as any)?.message ?? (typeof reason === \"string\" ? reason : \"\");\n if (shouldSwallow(message)) {\n return true;\n }\n if (typeof originalOnUnhandledRejection === \"function\") {\n return (originalOnUnhandledRejection as any)(event);\n }\n return undefined;\n };\n window.addEventListener(\"error\", swallowResizeObserverError, true);\n window.addEventListener(\n \"unhandledrejection\",\n swallowResizeObserverRejection,\n true\n );\n window.addEventListener(\n \"resizeobserverlooperror\" as any,\n swallowLoopEvent,\n true\n );\n}\n\nconst shallowArrayEqual = (a?: string[], b?: string[]) => {\n if (a === b) {\n return true;\n }\n if (!a || !b || a.length !== b.length) {\n return false;\n }\n for (let i = 0; i < a.length; i += 1) {\n if (a[i] !== b[i]) {\n return false;\n }\n }\n return true;\n};\n\n// Main orchestration component that renders and synchronizes the Designer flow.\n\nconst FIXED_X_POSITION = FLOW_LAYOUT.fixedXPosition;\nconst VERTICAL_SPACING = FLOW_LAYOUT.verticalSpacing;\n\nexport type DesignerFlowProps = {\n steps?: TaskStep[];\n parameters?: TemplateParametersValue;\n output?: ScaffolderTaskOutput | null;\n onStepsChange?: (steps: TaskStep[]) => void;\n onParametersChange?: (parameters: TemplateParametersValue) => void;\n onOutputChange?: (output: ScaffolderTaskOutput | undefined) => void;\n actionNodeComponent: ComponentType<{ data: ActionNodeData }>;\n parametersNodeComponent: ComponentType<{ data: ParametersNodeData }>;\n outputNodeComponent: ComponentType<{ data: OutputNodeData }>;\n decorateNodes?: (nodes: Node[]) => Node[];\n decorateEdges?: (edges: Edge[], nodes: Node[]) => Edge[];\n nodeDefaults?: Partial<Node>;\n};\n\nexport default function DesignerFlow({\n steps = [],\n parameters,\n output,\n onStepsChange,\n onParametersChange,\n onOutputChange,\n actionNodeComponent,\n parametersNodeComponent,\n outputNodeComponent,\n decorateNodes,\n decorateEdges,\n nodeDefaults = baseNodeDefaults,\n}: DesignerFlowProps) {\n const nodeDataHashRef = useRef<Record<string, string>>({});\n const edgeDataHashRef = useRef<Record<string, string>>({});\n const scaffolderActionsCache = useScaffolderActions();\n\n const {\n ids: scaffolderActionIds,\n inputsById: scaffolderActionInputsById,\n outputsById: scaffolderActionOutputsById,\n inputRequiredById: scaffolderActionInputRequiredById,\n } = scaffolderActionsCache;\n\n const normalizedParametersProp = parameters ?? undefined;\n const normalizedOutputProp = output ?? null;\n const pendingFocusNodeIdRef = useRef<string | null>(null);\n const hasMountedRef = useRef(false);\n const lastNodeCountRef = useRef(0);\n\n const initialNodes = useMemo(() => {\n const built = buildNodesFromModel(\n steps,\n normalizedParametersProp,\n normalizedOutputProp,\n {\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n }\n );\n const nodes = decorateNodes ? decorateNodes(built) : built;\n nodeDataHashRef.current = buildNodeHashMap(nodes);\n return nodes;\n }, [\n steps,\n normalizedParametersProp,\n normalizedOutputProp,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n decorateNodes,\n ]);\n\n const [nodes, setNodes] = useNodesState(initialNodes);\n const initialEdges = useMemo(() => {\n const edges = decorateEdges\n ? decorateEdges(createSequentialEdges(initialNodes), initialNodes)\n : createSequentialEdges(initialNodes);\n edgeDataHashRef.current = buildEdgeHashMap(edges);\n lastNodeCountRef.current = initialNodes.length;\n return edges;\n }, [decorateEdges, initialNodes]);\n\n const [edges, setEdges] = useState<Edge[]>(initialEdges);\n\n const modelHash = useMemo(\n () =>\n stableStringify({\n steps,\n parameters: normalizedParametersProp,\n output: normalizedOutputProp,\n }),\n [steps, normalizedParametersProp, normalizedOutputProp]\n );\n\n const cacheFingerprint = useMemo(\n () =>\n stableStringify({\n ids: scaffolderActionIds,\n inputs: scaffolderActionInputsById,\n outputs: scaffolderActionOutputsById,\n inputRequired: scaffolderActionInputRequiredById,\n }),\n [\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n ]\n );\n\n const lastAppliedModelHashRef = useRef<string | null>(null);\n const lastEmittedModelHashRef = useRef<string | null>(null);\n const lastCacheFingerprintRef = useRef<string | null>(null);\n const nodeHeightsRef = useRef<Record<string, number>>({});\n const lastViewportRef = useRef<Viewport | null>(null);\n const emitDebounceRef = useRef<ReturnType<typeof setTimeout> | null>(null);\n const isDraggingRef = useRef(false);\n const [isDragging, setIsDragging] = useState(false);\n const emitAfterDragRef = useRef(false);\n const pendingInitialFitRef = useRef(true);\n const userMovedViewportRef = useRef(false);\n const layoutInitializedRef = useRef(false);\n const [viewport, setViewport] = useState<Viewport | null>(() => {\n const existing = lastViewportRef.current;\n if (existing) {\n return existing;\n }\n const fallback = { x: 0, y: 0, zoom: 1 };\n lastViewportRef.current = fallback;\n return fallback;\n });\n const fitViewRafRef = useRef<number | null>(null);\n const fitViewTimeoutRef = useRef<ReturnType<typeof setTimeout> | null>(null);\n const alignDebounceRef = useRef<ReturnType<typeof setTimeout> | null>(null);\n\n const setViewportIfChanged = useCallback((next: Viewport | null) => {\n if (!next) {\n return;\n }\n const prev = lastViewportRef.current;\n if (\n prev &&\n prev.x === next.x &&\n prev.y === next.y &&\n prev.zoom === next.zoom\n ) {\n return;\n }\n lastViewportRef.current = next;\n setViewport(next);\n }, []);\n useEffect(() => {\n const isCacheChanged = cacheFingerprint !== lastCacheFingerprintRef.current;\n\n if (modelHash === lastAppliedModelHashRef.current && !isCacheChanged) {\n return;\n }\n\n const builtNodes = buildNodesFromModel(\n steps,\n normalizedParametersProp,\n normalizedOutputProp,\n {\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n }\n );\n\n const nextNodes = decorateNodes ? decorateNodes(builtNodes) : builtNodes;\n const isInitialMount = !hasMountedRef.current;\n\n lastAppliedModelHashRef.current = modelHash;\n lastCacheFingerprintRef.current = cacheFingerprint;\n lastEmittedModelHashRef.current = modelHash;\n\n setNodes((currentNodes) => {\n const merged = mergeNodesWithStability(\n currentNodes,\n nextNodes,\n nodeDataHashRef\n );\n return merged;\n });\n setEdges((currentEdges) => {\n const newEdges = decorateEdges\n ? decorateEdges(createSequentialEdges(nextNodes), nextNodes)\n : createSequentialEdges(nextNodes);\n const merged = mergeEdgesWithStability(\n currentEdges,\n newEdges,\n edgeDataHashRef\n );\n return merged;\n });\n hasMountedRef.current = true;\n lastNodeCountRef.current = nextNodes.length;\n if (isInitialMount) {\n pendingInitialFitRef.current = true;\n }\n }, [\n steps,\n normalizedParametersProp,\n normalizedOutputProp,\n modelHash,\n cacheFingerprint,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n decorateNodes,\n decorateEdges,\n setNodes,\n setEdges,\n ]);\n\n useEffect(() => {\n if (!nodes.length) {\n return;\n }\n\n if (nodes.some((node) => node.dragging)) {\n return;\n }\n\n const activeNodeIds = new Set<string>();\n let hasMeasuredChange = false;\n\n nodes.forEach((node) => {\n activeNodeIds.add(node.id);\n const measuredHeight = resolveNodeHeightForTracking(node);\n if (typeof measuredHeight !== \"number\") {\n return;\n }\n const previousHeight = nodeHeightsRef.current[node.id];\n const heightDelta = Math.abs(\n (previousHeight ?? measuredHeight) - measuredHeight\n );\n if (heightDelta >= 1) {\n // Ignore tiny size jitter; only react when node height meaningfully changes.\n nodeHeightsRef.current[node.id] = measuredHeight;\n hasMeasuredChange = true;\n }\n });\n\n Object.keys(nodeHeightsRef.current).forEach((id) => {\n if (!activeNodeIds.has(id)) {\n delete nodeHeightsRef.current[id];\n }\n });\n\n if (!hasMeasuredChange) {\n return;\n }\n\n if (!layoutInitializedRef.current) {\n // Skip the first post-measure align to avoid initial jump; positions are already close to target.\n layoutInitializedRef.current = true;\n return;\n }\n\n if (alignDebounceRef.current) {\n clearTimeout(alignDebounceRef.current);\n }\n alignDebounceRef.current = setTimeout(() => {\n alignDebounceRef.current = null;\n setNodes((currentNodes) => {\n const alignedNodes = alignNodes(\n currentNodes,\n FIXED_X_POSITION,\n VERTICAL_SPACING\n );\n const positionsChanged = alignedNodes.some((node, index) => {\n const previousNode = currentNodes[index];\n if (!previousNode) {\n return true;\n }\n return (\n node.position.x !== previousNode.position.x ||\n node.position.y !== previousNode.position.y\n );\n });\n\n return positionsChanged ? alignedNodes : currentNodes;\n });\n }, VIEWPORT_TUNING.alignDebounceMs);\n }, [nodes, setNodes]);\n\n const parameterReferences = useMemo(\n () => collectParameterReferences(normalizedParametersProp),\n [normalizedParametersProp]\n );\n\n const stepOutputReferencesByNode = useMemo(\n () => collectStepOutputReferences(nodes, parameterReferences),\n [nodes, parameterReferences]\n );\n\n const onNodesChange = useCallback(\n (changes: NodeChange<Node>[]) =>\n setNodes((ns) => {\n if (\n changes.some(\n (change) => change.type === \"position\" && change.dragging\n )\n ) {\n isDraggingRef.current = true;\n setIsDragging(true);\n } else if (\n changes.some(\n (change) => change.type === \"position\" && change.dragging === false\n )\n ) {\n const stillDragging = ns.some((node) => node.dragging);\n isDraggingRef.current = stillDragging;\n setIsDragging(stillDragging);\n }\n return applyNodeChanges(changes, ns);\n }),\n [setNodes]\n );\n\n const onEdgesChange = useCallback(\n (changes: EdgeChange<Edge>[]) =>\n setEdges((es) => applyEdgeChanges(changes, es)),\n [setEdges]\n );\n\n const resolvedNodeTypes = useMemo<NodeTypes>(\n () => ({\n parametersNode: ((props: NodeProps) =>\n createElement(parametersNodeComponent, {\n data: props.data as ParametersNodeData,\n })) as ComponentType<NodeProps>,\n actionNode: ((props: NodeProps) =>\n createElement(actionNodeComponent, {\n data: props.data as ActionNodeData,\n })) as ComponentType<NodeProps>,\n outputNode: ((props: NodeProps) =>\n createElement(outputNodeComponent, {\n data: props.data as OutputNodeData,\n })) as ComponentType<NodeProps>,\n }),\n [actionNodeComponent, outputNodeComponent, parametersNodeComponent]\n );\n\n const onConnect = useCallback(\n (params: any) => setEdges((es) => addEdge(params, es)),\n [setEdges]\n );\n\n const reorderAndAlignNodes = useMemo(\n () =>\n createHandleReorderAndAlignNodes(setNodes, setEdges, {\n fixedXPosition: FIXED_X_POSITION,\n verticalSpacing: VERTICAL_SPACING,\n }),\n [setNodes, setEdges]\n );\n\n const onNodeDragStop = useCallback(\n (_: ReactMouseEvent, node: Node) => {\n isDraggingRef.current = false;\n setIsDragging(false);\n reorderAndAlignNodes(node);\n },\n [reorderAndAlignNodes]\n );\n\n const onUpdateField = useMemo(\n () => createHandleUpdateField(setNodes),\n [setNodes]\n );\n\n const onUpdateInput = useMemo(\n () => createHandleUpdateInput(setNodes),\n [setNodes]\n );\n\n const onRemoveInputKey = useMemo(\n () => createHandleRemoveInputKey(setNodes),\n [setNodes]\n );\n\n const onUpdateOutput = useMemo(\n () => createHandleUpdateOutput(setNodes),\n [setNodes]\n );\n\n const onUpdateSections = useMemo(\n () => createHandleUpdateSections(setNodes),\n [setNodes]\n );\n\n const handleAddNode = useMemo(\n () =>\n createHandleAddNode(setNodes, setEdges, {\n fixedXPosition: FIXED_X_POSITION,\n verticalSpacing: VERTICAL_SPACING,\n nodeDefaults,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionInputRequiredById,\n scaffolderActionOutputsById,\n onNodeAdded: (rfId: string) => {\n pendingFocusNodeIdRef.current = rfId;\n // Keep current zoom/viewport; focus will center on the new node.\n pendingInitialFitRef.current = false;\n },\n }),\n [\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n nodeDefaults,\n setNodes,\n setEdges,\n ]\n );\n\n const handleRemoveNode = useMemo(\n () =>\n createHandleRemoveNode(setNodes, setEdges, {\n fixedXPosition: FIXED_X_POSITION,\n verticalSpacing: VERTICAL_SPACING,\n }),\n [setNodes, setEdges]\n );\n\n const emitChanges = useCallback(() => {\n if (!onStepsChange && !onParametersChange && !onOutputChange) {\n return;\n }\n const stepsFromNodes = extractStepsFromNodes(nodes);\n const parametersFromNodes = extractParametersFromNodes(nodes);\n const outputFromNodes = extractOutputFromNodes(nodes);\n\n const nextHash = stableStringify({\n steps: stepsFromNodes,\n parameters: parametersFromNodes,\n output: outputFromNodes,\n });\n\n if (nextHash === lastEmittedModelHashRef.current) {\n return;\n }\n\n lastEmittedModelHashRef.current = nextHash;\n onStepsChange?.(stepsFromNodes);\n onParametersChange?.(parametersFromNodes);\n onOutputChange?.(outputFromNodes);\n }, [\n nodes,\n onOutputChange,\n onParametersChange,\n onStepsChange,\n lastEmittedModelHashRef,\n ]);\n\n const emitChangesDeferred = useCallback(() => {\n if (emitDebounceRef.current) {\n clearTimeout(emitDebounceRef.current);\n }\n emitDebounceRef.current = setTimeout(() => {\n emitChanges();\n emitDebounceRef.current = null;\n }, EMIT_DEBOUNCE_MS);\n }, [emitChanges]);\n\n const flushPendingEmit = useCallback(() => {\n if (emitDebounceRef.current) {\n clearTimeout(emitDebounceRef.current);\n emitDebounceRef.current = null;\n }\n emitChanges();\n }, [emitChanges]);\n\n // Hoist handler/data refs into state so ReactFlow sees unchanged node objects when nothing relevant changed.\n const ensureNodeDataStability = useCallback(\n (node: Node): Node => {\n if (node.type === \"actionNode\") {\n const data = node.data as ActionNodeData;\n const nextRefs =\n stepOutputReferencesByNode[node.id] ?? data.stepOutputReferences;\n const refsUnchanged = shallowArrayEqual(\n data.stepOutputReferences,\n nextRefs\n );\n\n const hasSameHandlers =\n data.onAddNode === handleAddNode &&\n data.onRemoveNode === handleRemoveNode &&\n data.onUpdateField === onUpdateField &&\n data.onUpdateInput === onUpdateInput &&\n data.onRemoveInputKey === onRemoveInputKey;\n const hasSameCaches =\n data.scaffolderActionIds === scaffolderActionIds &&\n data.scaffolderActionInputsById === scaffolderActionInputsById &&\n data.scaffolderActionOutputsById === scaffolderActionOutputsById &&\n data.scaffolderActionInputRequiredById ===\n scaffolderActionInputRequiredById;\n\n if (hasSameHandlers && hasSameCaches && refsUnchanged) {\n return node;\n }\n\n return {\n ...node,\n data: {\n ...data,\n onAddNode: handleAddNode,\n onRemoveNode: handleRemoveNode,\n onUpdateField,\n onUpdateInput,\n onRemoveInputKey,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n stepOutputReferences: refsUnchanged\n ? data.stepOutputReferences\n : nextRefs,\n },\n };\n }\n\n if (node.type === \"outputNode\") {\n const data = node.data as OutputNodeData;\n const nextRefs =\n stepOutputReferencesByNode[node.id] ?? data.stepOutputReferences;\n const refsUnchanged = shallowArrayEqual(\n data.stepOutputReferences,\n nextRefs\n );\n const hasSameHandlers =\n data.onUpdateOutput === onUpdateOutput &&\n data.onRemoveNode === handleRemoveNode &&\n data.onAddNode === handleAddNode;\n\n const hasSameCaches =\n data.scaffolderActionIds === scaffolderActionIds &&\n data.scaffolderActionInputsById === scaffolderActionInputsById &&\n data.scaffolderActionOutputsById === scaffolderActionOutputsById &&\n data.scaffolderActionInputRequiredById ===\n scaffolderActionInputRequiredById;\n\n if (hasSameHandlers && hasSameCaches && refsUnchanged) {\n return node;\n }\n\n return {\n ...node,\n data: {\n ...data,\n onUpdateOutput,\n onRemoveNode: handleRemoveNode,\n onAddNode: handleAddNode,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n stepOutputReferences: refsUnchanged\n ? data.stepOutputReferences\n : nextRefs,\n },\n };\n }\n\n if (node.type === \"parametersNode\") {\n const data = node.data as ParametersNodeData;\n const hasSameHandlers =\n data.onUpdateSections === onUpdateSections &&\n data.onRemoveNode === handleRemoveNode &&\n data.onAddNode === handleAddNode;\n const hasSameCaches =\n data.scaffolderActionIds === scaffolderActionIds &&\n data.scaffolderActionInputsById === scaffolderActionInputsById &&\n data.scaffolderActionOutputsById === scaffolderActionOutputsById &&\n data.scaffolderActionInputRequiredById ===\n scaffolderActionInputRequiredById;\n\n if (hasSameHandlers && hasSameCaches) {\n return node;\n }\n\n return {\n ...node,\n data: {\n ...data,\n onUpdateSections,\n onRemoveNode: handleRemoveNode,\n onAddNode: handleAddNode,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n },\n };\n }\n\n return node;\n },\n [\n handleAddNode,\n handleRemoveNode,\n onUpdateField,\n onUpdateInput,\n onRemoveInputKey,\n onUpdateOutput,\n onUpdateSections,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionOutputsById,\n scaffolderActionInputRequiredById,\n stepOutputReferencesByNode,\n ]\n );\n\n useEffect(() => {\n setNodes((currentNodes) => {\n let changed = false;\n const nextNodes = currentNodes.map((node) => {\n const updated = ensureNodeDataStability(node);\n if (updated !== node) {\n changed = true;\n }\n return updated;\n });\n\n // Returning the same array keeps ReactFlow nodes prop stable unless something truly changed.\n return changed ? nextNodes : currentNodes;\n });\n }, [ensureNodeDataStability, setNodes]);\n\n useEffect(() => {\n emitChangesDeferred();\n }, [nodes, emitChangesDeferred]);\n\n useEffect(() => {\n // Force next emit to run even if hash matches, so input edits flush to YAML.\n lastEmittedModelHashRef.current = null;\n }, [nodes]);\n\n useEffect(() => {\n if (!nodes.length) {\n return;\n }\n emitChangesDeferred();\n }, [emitChangesDeferred, modelHash, nodes]);\n\n useEffect(() => {\n return () => {\n if (emitDebounceRef.current) {\n clearTimeout(emitDebounceRef.current);\n }\n if (fitViewRafRef.current !== null) {\n cancelAnimationFrame(fitViewRafRef.current);\n fitViewRafRef.current = null;\n }\n if (fitViewTimeoutRef.current) {\n clearTimeout(fitViewTimeoutRef.current);\n fitViewTimeoutRef.current = null;\n }\n if (alignDebounceRef.current) {\n clearTimeout(alignDebounceRef.current);\n }\n flushPendingEmit();\n };\n }, [flushPendingEmit]);\n\n const [reactFlowInstance, setReactFlowInstance] =\n useState<ReactFlowInstance | null>(null);\n const fitFlowToView = useCallback(() => {\n if (!reactFlowInstance || !nodes.length) {\n return;\n }\n if (fitViewRafRef.current !== null) {\n return;\n }\n if (userMovedViewportRef.current && !pendingInitialFitRef.current) {\n // Respect user navigation; don't snap back after they moved the camera.\n return;\n }\n const nodeWithWidth = nodes.find((node) => node.width);\n const nodeWidth = nodeWithWidth?.width ?? 760;\n const padding = Math.max((window.innerWidth - nodeWidth) / 2 - 24, 60);\n const viewOptions = {\n padding,\n minZoom: 0.2,\n };\n // Delay fitView to the next frame to avoid ResizeObserver loops while nodes mount/measure.\n fitViewRafRef.current = window.requestAnimationFrame(() => {\n fitViewRafRef.current = null;\n try {\n reactFlowInstance.fitView(viewOptions);\n setViewportIfChanged(reactFlowInstance.getViewport());\n } catch {\n // Swallow rare layout timing errors; the next change will try again.\n }\n });\n // Fallback in case RAF is skipped (tab in background).\n if (fitViewTimeoutRef.current) {\n clearTimeout(fitViewTimeoutRef.current);\n }\n fitViewTimeoutRef.current = setTimeout(() => {\n fitViewTimeoutRef.current = null;\n try {\n reactFlowInstance.fitView(viewOptions);\n setViewportIfChanged(reactFlowInstance.getViewport());\n } catch {\n // Ignore; typically triggered only during tab throttling.\n }\n }, VIEWPORT_TUNING.fitFallbackDelayMs);\n }, [nodes, reactFlowInstance, setViewportIfChanged]);\n\n useEffect(() => {\n if (!reactFlowInstance) {\n return;\n }\n if (viewport === null) {\n setViewportIfChanged(viewport);\n }\n if (!pendingInitialFitRef.current) {\n return;\n }\n pendingInitialFitRef.current = false;\n fitFlowToView();\n }, [\n fitFlowToView,\n nodes,\n edges,\n reactFlowInstance,\n viewport,\n setViewportIfChanged,\n ]);\n\n useEffect(() => {\n const swallowResizeObserverError = (event: ErrorEvent) => {\n const message =\n event?.message || (event as any)?.error?.message || String(event);\n if (\n typeof message === \"string\" &&\n message.includes(\"ResizeObserver loop\")\n ) {\n // Prevent dev overlay noise for benign ResizeObserver timing loops that appear after fitView/layout.\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n };\n const swallowResizeObserverRejection = (event: PromiseRejectionEvent) => {\n const message = (event.reason as any)?.message ?? String(event.reason);\n if (\n typeof message === \"string\" &&\n message.includes(\"ResizeObserver loop\")\n ) {\n event.preventDefault();\n event.stopImmediatePropagation();\n }\n };\n window.addEventListener(\"error\", swallowResizeObserverError, true);\n window.addEventListener(\n \"unhandledrejection\",\n swallowResizeObserverRejection,\n true\n );\n // Chrome/FF dispatch a dedicated event for this condition; capture it to prevent overlay noise.\n const swallowLoopErrorEvent = (event: Event) => {\n event.preventDefault();\n event.stopImmediatePropagation();\n };\n window.addEventListener(\n \"resizeobserverlooperror\" as any,\n swallowLoopErrorEvent,\n true\n );\n return () => {\n window.removeEventListener(\"error\", swallowResizeObserverError, true);\n window.removeEventListener(\n \"unhandledrejection\",\n swallowResizeObserverRejection,\n true\n );\n window.removeEventListener(\n \"resizeobserverlooperror\" as any,\n swallowLoopErrorEvent,\n true\n );\n };\n }, []);\n\n useEffect(() => {\n if (!reactFlowInstance) {\n return undefined;\n }\n window.addEventListener(\"resize\", fitFlowToView);\n return () => {\n window.removeEventListener(\"resize\", fitFlowToView);\n };\n }, [fitFlowToView, reactFlowInstance]);\n\n useEffect(() => {\n if (!isDragging) {\n if (emitAfterDragRef.current) {\n emitAfterDragRef.current = false;\n lastEmittedModelHashRef.current = null;\n }\n // Trigger emit cycle after drag ends so external state is up to date.\n lastEmittedModelHashRef.current = null;\n }\n }, [isDragging]);\n\n const handleMoveEnd: OnMoveEnd = useCallback(\n (_event, nextViewport: Viewport) => {\n // Keep zoom stable to optionally cull edges when zoomed out.\n setViewportIfChanged(nextViewport);\n },\n [setViewportIfChanged]\n );\n\n const handleMove: OnMove = useCallback(\n (_, nextViewport) => {\n userMovedViewportRef.current = true;\n setViewportIfChanged(nextViewport);\n },\n [setViewportIfChanged]\n );\n\n const shouldCullEdges =\n edges.length > 300 && (viewport?.zoom ?? 1) < 0.3 && !isDragging;\n const renderedEdges = useMemo(\n () =>\n shouldCullEdges\n ? EMPTY_EDGES // Dropping edges when zoomed out keeps canvas responsive with huge graphs.\n : edges,\n [edges, shouldCullEdges]\n );\n\n useEffect(() => {\n if (!reactFlowInstance) {\n return;\n }\n const pendingId = pendingFocusNodeIdRef.current;\n if (!pendingId) {\n return;\n }\n const target = nodes.find((node) => node.id === pendingId);\n if (!target) {\n return;\n }\n pendingFocusNodeIdRef.current = null;\n const nodeCenterX = target.position.x + (target.width ?? 0) / 2;\n const nodeCenterY = target.position.y + (target.height ?? 0) / 2;\n const zoom = viewport?.zoom ?? lastViewportRef.current?.zoom ?? undefined;\n try {\n reactFlowInstance.setCenter(nodeCenterX, nodeCenterY, {\n zoom,\n duration: VIEWPORT_TUNING.centerDurationMs,\n });\n window.requestAnimationFrame(() => {\n setViewportIfChanged(reactFlowInstance.getViewport());\n });\n } catch {\n // ignore\n }\n }, [nodes, reactFlowInstance, viewport, setViewportIfChanged]);\n\n return (\n <div style={{ width: \"100%\", height: \"100%\", minHeight: \"100%\" }}>\n <ReactFlow\n nodes={nodes}\n edges={renderedEdges}\n nodeTypes={resolvedNodeTypes}\n defaultViewport={\n viewport ?? {\n x: 0,\n y: 0,\n zoom: 1,\n }\n }\n viewport={viewport ?? undefined}\n onNodesChange={onNodesChange}\n onEdgesChange={onEdgesChange}\n onNodeDragStop={onNodeDragStop}\n onConnect={onConnect}\n onMove={handleMove}\n onlyRenderVisibleElements\n onInit={setReactFlowInstance}\n onMoveEnd={handleMoveEnd}\n />\n </div>\n );\n}\n"],"names":["nodeDefaults","baseNodeDefaults","nodes","edges"],"mappings":"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"}
@@ -0,0 +1,317 @@
1
+ import { createSequentialEdges } from '../utils/createSequentialEdges.esm.js';
2
+ import { sectionsToParametersValue, normalizeParametersToSections } from './parameterTransforms.esm.js';
3
+ import { alignNodes } from './nodeLayout.esm.js';
4
+
5
+ const orderNodes = (parameterNodes, actionNodes, outputNodes) => [...parameterNodes, ...actionNodes, ...outputNodes];
6
+ const setSequentialEdgesIfChanged = (setEdges, alignedNodes) => {
7
+ setEdges((prevEdges) => {
8
+ const nextEdges = createSequentialEdges(alignedNodes);
9
+ if (prevEdges.length === nextEdges.length && prevEdges.every(
10
+ (edge, index) => edge.source === nextEdges[index]?.source && edge.target === nextEdges[index]?.target
11
+ )) {
12
+ return prevEdges;
13
+ }
14
+ return nextEdges;
15
+ });
16
+ };
17
+ const createHandleAddNode = (setNodes, setEdges, options) => {
18
+ const {
19
+ fixedXPosition,
20
+ verticalSpacing,
21
+ nodeDefaults,
22
+ scaffolderActionIds,
23
+ scaffolderActionInputsById,
24
+ scaffolderActionInputRequiredById,
25
+ scaffolderActionOutputsById
26
+ } = options;
27
+ return (config) => {
28
+ const {
29
+ afterRfId,
30
+ type = "actionNode",
31
+ stepTemplate,
32
+ outputTemplate,
33
+ parametersTemplate
34
+ } = config;
35
+ const nodeType = type;
36
+ setNodes((nodes) => {
37
+ const parameterNodes = nodes.filter((n) => n.type === "parametersNode");
38
+ const actionNodes = nodes.filter((n) => n.type === "actionNode");
39
+ const outputNodes = nodes.filter((n) => n.type === "outputNode");
40
+ const composeAndAlign = (nextParameters, nextActions2, nextOutputs) => {
41
+ const ordered = orderNodes(nextParameters, nextActions2, nextOutputs);
42
+ const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);
43
+ setSequentialEdgesIfChanged(setEdges, aligned);
44
+ return aligned;
45
+ };
46
+ if (nodeType === "parametersNode") {
47
+ if (parameterNodes.length > 0) {
48
+ return composeAndAlign(parameterNodes, actionNodes, outputNodes);
49
+ }
50
+ const rfParametersId = "rf-parameters";
51
+ const initialParameters = parametersTemplate !== void 0 ? JSON.parse(
52
+ JSON.stringify(parametersTemplate)
53
+ ) : void 0;
54
+ return composeAndAlign(
55
+ [
56
+ {
57
+ id: rfParametersId,
58
+ type: "parametersNode",
59
+ position: { x: fixedXPosition, y: 0 },
60
+ data: {
61
+ rfId: rfParametersId,
62
+ parameters: initialParameters,
63
+ sections: initialParameters !== void 0 ? normalizeParametersToSections(initialParameters) : [],
64
+ scaffolderActionIds,
65
+ scaffolderActionInputsById,
66
+ scaffolderActionInputRequiredById,
67
+ scaffolderActionOutputsById
68
+ },
69
+ ...nodeDefaults
70
+ }
71
+ ],
72
+ actionNodes,
73
+ outputNodes
74
+ );
75
+ }
76
+ if (nodeType === "outputNode") {
77
+ if (outputNodes.length > 0) {
78
+ return composeAndAlign(parameterNodes, actionNodes, outputNodes);
79
+ }
80
+ const rfOutputId = "rf-output";
81
+ const initialOutput = outputTemplate ? JSON.parse(JSON.stringify(outputTemplate)) : {};
82
+ return composeAndAlign(parameterNodes, actionNodes, [
83
+ {
84
+ id: rfOutputId,
85
+ type: "outputNode",
86
+ position: { x: fixedXPosition, y: 0 },
87
+ data: {
88
+ rfId: rfOutputId,
89
+ output: initialOutput,
90
+ scaffolderActionIds,
91
+ scaffolderActionInputsById,
92
+ scaffolderActionInputRequiredById,
93
+ scaffolderActionOutputsById
94
+ },
95
+ ...nodeDefaults
96
+ }
97
+ ]);
98
+ }
99
+ const rfActionId = `rf-action-${Math.random().toString(36).slice(2, 6)}`;
100
+ const newStep = {
101
+ id: stepTemplate?.id ?? `step-id-${Math.random().toString(36).slice(2, 8)}`,
102
+ name: stepTemplate?.name ?? "",
103
+ action: stepTemplate?.action ?? "",
104
+ input: { ...stepTemplate?.input ?? {} },
105
+ ...stepTemplate ?? {}
106
+ };
107
+ const nextActions = [...actionNodes];
108
+ const insertAfterOutput = outputNodes.some(
109
+ (node) => node.id === afterRfId
110
+ );
111
+ let targetIndex = nextActions.length;
112
+ if (afterRfId) {
113
+ if (insertAfterOutput) {
114
+ targetIndex = nextActions.length;
115
+ } else {
116
+ targetIndex = Math.max(
117
+ nextActions.findIndex((node) => node.id === afterRfId) + 1,
118
+ 0
119
+ );
120
+ }
121
+ }
122
+ nextActions.splice(targetIndex, 0, {
123
+ id: rfActionId,
124
+ type: "actionNode",
125
+ position: { x: fixedXPosition, y: 0 },
126
+ data: {
127
+ rfId: rfActionId,
128
+ step: newStep,
129
+ scaffolderActionIds,
130
+ scaffolderActionInputsById,
131
+ scaffolderActionInputRequiredById,
132
+ scaffolderActionOutputsById
133
+ },
134
+ ...nodeDefaults
135
+ });
136
+ options.onNodeAdded?.(rfActionId);
137
+ return composeAndAlign(parameterNodes, nextActions, outputNodes);
138
+ });
139
+ };
140
+ };
141
+ const createHandleUpdateField = (setNodes) => {
142
+ return (rfId, field, value) => {
143
+ setNodes(
144
+ (nodes) => nodes.map(
145
+ (node) => node.id !== rfId ? node : {
146
+ ...node,
147
+ data: {
148
+ ...node.data,
149
+ step: {
150
+ ...node.data.step,
151
+ [field]: value
152
+ }
153
+ }
154
+ }
155
+ )
156
+ );
157
+ };
158
+ };
159
+ const createHandleUpdateInput = (setNodes) => {
160
+ return (rfId, key, value) => {
161
+ setNodes(
162
+ (nodes) => nodes.map((node) => {
163
+ if (node.id !== rfId) {
164
+ return node;
165
+ }
166
+ const data = node.data;
167
+ const baseInput = data.step?.input ?? {};
168
+ const nextInput = {};
169
+ Object.entries(baseInput).forEach(([existingKey, existingValue]) => {
170
+ if (existingValue !== void 0) {
171
+ nextInput[existingKey] = existingValue;
172
+ }
173
+ });
174
+ if (value !== void 0) {
175
+ nextInput[key] = value;
176
+ }
177
+ return {
178
+ ...node,
179
+ data: {
180
+ ...data,
181
+ step: { ...data.step, input: nextInput }
182
+ }
183
+ };
184
+ })
185
+ );
186
+ };
187
+ };
188
+ const createHandleRemoveInputKey = (setNodes) => {
189
+ return (rfId, key) => setNodes(
190
+ (nodes) => nodes.map((node) => {
191
+ if (node.id !== rfId) {
192
+ return node;
193
+ }
194
+ const data = node.data;
195
+ const nextInput = { ...data.step?.input ?? {} };
196
+ delete nextInput[key];
197
+ return {
198
+ ...node,
199
+ data: {
200
+ ...data,
201
+ step: { ...data.step, input: nextInput }
202
+ }
203
+ };
204
+ })
205
+ );
206
+ };
207
+ const createHandleUpdateOutput = (setNodes) => {
208
+ return (rfId, updater) => {
209
+ setNodes(
210
+ (nodes) => nodes.map((node) => {
211
+ if (node.id !== rfId) {
212
+ return node;
213
+ }
214
+ const data = node.data;
215
+ const nextOutput = updater(data.output ?? {});
216
+ return {
217
+ ...node,
218
+ data: {
219
+ ...data,
220
+ output: nextOutput
221
+ }
222
+ };
223
+ })
224
+ );
225
+ };
226
+ };
227
+ const createHandleUpdateSections = (setNodes) => {
228
+ return (rfId, updater) => {
229
+ setNodes(
230
+ (nodes) => nodes.map((node) => {
231
+ if (node.id !== rfId) {
232
+ return node;
233
+ }
234
+ const data = node.data;
235
+ const nextSections = updater(data.sections ?? []);
236
+ return {
237
+ ...node,
238
+ data: {
239
+ ...data,
240
+ sections: nextSections,
241
+ parameters: sectionsToParametersValue(nextSections)
242
+ }
243
+ };
244
+ })
245
+ );
246
+ };
247
+ };
248
+ const createHandleRemoveNode = (setNodes, setEdges, options) => {
249
+ const { fixedXPosition, verticalSpacing } = options;
250
+ return (rfId) => {
251
+ setNodes((nodes) => {
252
+ const parameterNodes = nodes.filter((n) => n.type === "parametersNode");
253
+ const actionNodes = nodes.filter(
254
+ (n) => n.type === "actionNode" && n.id !== rfId
255
+ );
256
+ const outputNodes = nodes.filter((n) => n.type === "outputNode");
257
+ const ordered = orderNodes(parameterNodes, actionNodes, outputNodes);
258
+ const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);
259
+ setSequentialEdgesIfChanged(setEdges, aligned);
260
+ return aligned;
261
+ });
262
+ };
263
+ };
264
+ const createHandleReorderAndAlignNodes = (setNodes, setEdges, options) => {
265
+ const { fixedXPosition, verticalSpacing } = options;
266
+ return (node) => {
267
+ if (!node) {
268
+ return;
269
+ }
270
+ setNodes((nodes) => {
271
+ const parameterNodes = nodes.filter((n) => n.type === "parametersNode");
272
+ const actionNodes = nodes.filter((n) => n.type === "actionNode");
273
+ const outputNodes = nodes.filter((n) => n.type === "outputNode");
274
+ if (node.type === "parametersNode") {
275
+ return alignNodes(
276
+ orderNodes(
277
+ [node, ...parameterNodes.filter((n) => n.id !== node.id)],
278
+ actionNodes,
279
+ outputNodes
280
+ ),
281
+ fixedXPosition,
282
+ verticalSpacing
283
+ );
284
+ }
285
+ if (node.type === "outputNode") {
286
+ return alignNodes(
287
+ orderNodes(parameterNodes, actionNodes, [
288
+ node,
289
+ ...outputNodes.filter((n) => n.id !== node.id)
290
+ ]),
291
+ fixedXPosition,
292
+ verticalSpacing
293
+ );
294
+ }
295
+ const filteredActionNodes = actionNodes.filter((n) => n.id !== node.id);
296
+ const targetIndex = filteredActionNodes.findIndex(
297
+ (n) => n.position.y > node.position.y
298
+ );
299
+ if (targetIndex === -1) {
300
+ filteredActionNodes.push(node);
301
+ } else {
302
+ filteredActionNodes.splice(targetIndex, 0, node);
303
+ }
304
+ const ordered = orderNodes(
305
+ parameterNodes,
306
+ filteredActionNodes,
307
+ outputNodes
308
+ );
309
+ const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);
310
+ setSequentialEdgesIfChanged(setEdges, aligned);
311
+ return aligned;
312
+ });
313
+ };
314
+ };
315
+
316
+ export { createHandleAddNode, createHandleRemoveInputKey, createHandleRemoveNode, createHandleReorderAndAlignNodes, createHandleUpdateField, createHandleUpdateInput, createHandleUpdateOutput, createHandleUpdateSections };
317
+ //# sourceMappingURL=handlers.esm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"handlers.esm.js","sources":["../../src/designerFlow/handlers.ts"],"sourcesContent":["import type { Dispatch, SetStateAction } from \"react\";\nimport type { Edge, Node } from \"@xyflow/react\";\nimport type {\n ScaffolderTaskOutput,\n TaskStep,\n} from \"@backstage/plugin-scaffolder-common\";\nimport type { JsonValue } from \"@backstage/types\";\nimport type {\n ActionNodeData,\n AddNodeConfig,\n DesignerNodeType,\n OutputNodeData,\n ParametersNodeData,\n ParameterSectionDisplay,\n TemplateParametersValue,\n} from \"../types/flowNodes\";\nimport { createSequentialEdges } from \"../utils/createSequentialEdges\";\nimport {\n normalizeParametersToSections,\n sectionsToParametersValue,\n} from \"./parameterTransforms\";\nimport { alignNodes } from \"./nodeLayout\";\n\ntype SetNodes = Dispatch<SetStateAction<Node[]>>;\ntype SetEdges = Dispatch<SetStateAction<Edge[]>>;\n\ninterface CreateHandleAddNodeOptions {\n fixedXPosition: number;\n verticalSpacing: number;\n nodeDefaults: Partial<Node>;\n scaffolderActionIds: string[];\n scaffolderActionInputsById: Record<string, Record<string, unknown>>;\n scaffolderActionInputRequiredById: Record<string, string[]>;\n scaffolderActionOutputsById: Record<string, Record<string, unknown>>;\n onNodeAdded?: (rfId: string) => void;\n}\n\ninterface CreateHandleRemoveNodeOptions {\n fixedXPosition: number;\n verticalSpacing: number;\n}\n\nconst orderNodes = (\n parameterNodes: Node[],\n actionNodes: Node[],\n outputNodes: Node[]\n) => [...parameterNodes, ...actionNodes, ...outputNodes];\n\nconst setSequentialEdgesIfChanged = (\n setEdges: SetEdges,\n alignedNodes: Node[]\n) => {\n setEdges((prevEdges) => {\n const nextEdges = createSequentialEdges(alignedNodes);\n if (\n prevEdges.length === nextEdges.length &&\n prevEdges.every(\n (edge, index) =>\n edge.source === nextEdges[index]?.source &&\n edge.target === nextEdges[index]?.target\n )\n ) {\n return prevEdges;\n }\n return nextEdges;\n });\n};\n\nexport const createHandleAddNode = (\n setNodes: SetNodes,\n setEdges: SetEdges,\n options: CreateHandleAddNodeOptions\n) => {\n const {\n fixedXPosition,\n verticalSpacing,\n nodeDefaults,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionInputRequiredById,\n scaffolderActionOutputsById,\n } = options;\n\n return (config: AddNodeConfig) => {\n const {\n afterRfId,\n type = \"actionNode\",\n stepTemplate,\n outputTemplate,\n parametersTemplate,\n } = config;\n const nodeType: DesignerNodeType = type;\n\n setNodes((nodes) => {\n const parameterNodes = nodes.filter((n) => n.type === \"parametersNode\");\n const actionNodes = nodes.filter((n) => n.type === \"actionNode\");\n const outputNodes = nodes.filter((n) => n.type === \"outputNode\");\n\n const composeAndAlign = (\n nextParameters: Node[],\n nextActions: Node[],\n nextOutputs: Node[]\n ) => {\n const ordered = orderNodes(nextParameters, nextActions, nextOutputs);\n const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);\n setSequentialEdgesIfChanged(setEdges, aligned);\n return aligned;\n };\n\n if (nodeType === \"parametersNode\") {\n if (parameterNodes.length > 0) {\n return composeAndAlign(parameterNodes, actionNodes, outputNodes);\n }\n\n const rfParametersId = \"rf-parameters\";\n const initialParameters =\n parametersTemplate !== undefined\n ? (JSON.parse(\n JSON.stringify(parametersTemplate)\n ) as TemplateParametersValue)\n : undefined;\n\n return composeAndAlign(\n [\n {\n id: rfParametersId,\n type: \"parametersNode\",\n position: { x: fixedXPosition, y: 0 },\n data: {\n rfId: rfParametersId,\n parameters: initialParameters,\n sections:\n initialParameters !== undefined\n ? normalizeParametersToSections(initialParameters)\n : [],\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionInputRequiredById,\n scaffolderActionOutputsById,\n },\n ...nodeDefaults,\n },\n ],\n actionNodes,\n outputNodes\n );\n }\n\n if (nodeType === \"outputNode\") {\n if (outputNodes.length > 0) {\n return composeAndAlign(parameterNodes, actionNodes, outputNodes);\n }\n\n const rfOutputId = \"rf-output\";\n const initialOutput = outputTemplate\n ? (JSON.parse(JSON.stringify(outputTemplate)) as any)\n : {};\n return composeAndAlign(parameterNodes, actionNodes, [\n {\n id: rfOutputId,\n type: \"outputNode\",\n position: { x: fixedXPosition, y: 0 },\n data: {\n rfId: rfOutputId,\n output: initialOutput,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionInputRequiredById,\n scaffolderActionOutputsById,\n } satisfies OutputNodeData,\n ...nodeDefaults,\n },\n ]);\n }\n\n // Default: add an action node\n const rfActionId = `rf-action-${Math.random().toString(36).slice(2, 6)}`;\n const newStep = {\n id:\n stepTemplate?.id ??\n `step-id-${Math.random().toString(36).slice(2, 8)}`,\n name: stepTemplate?.name ?? \"\",\n action: stepTemplate?.action ?? \"\",\n input: { ...(stepTemplate?.input ?? {}) },\n ...(stepTemplate ?? {}),\n } satisfies TaskStep;\n\n const nextActions = [...actionNodes];\n const insertAfterOutput = outputNodes.some(\n (node) => node.id === afterRfId\n );\n let targetIndex = nextActions.length;\n if (afterRfId) {\n if (insertAfterOutput) {\n targetIndex = nextActions.length; // When triggered from OutputNode \"Add Action Above\", append to preserve end position.\n } else {\n targetIndex = Math.max(\n nextActions.findIndex((node) => node.id === afterRfId) + 1,\n 0\n );\n }\n }\n nextActions.splice(targetIndex, 0, {\n id: rfActionId,\n type: \"actionNode\",\n position: { x: fixedXPosition, y: 0 },\n data: {\n rfId: rfActionId,\n step: newStep,\n scaffolderActionIds,\n scaffolderActionInputsById,\n scaffolderActionInputRequiredById,\n scaffolderActionOutputsById,\n } satisfies ActionNodeData,\n ...nodeDefaults,\n });\n\n options.onNodeAdded?.(rfActionId);\n return composeAndAlign(parameterNodes, nextActions, outputNodes);\n });\n };\n};\n\nexport const createHandleUpdateField = (setNodes: SetNodes) => {\n return (rfId: string, field: keyof TaskStep, value: string) => {\n setNodes((nodes) =>\n nodes.map((node) =>\n node.id !== rfId\n ? node\n : ({\n ...node,\n data: {\n ...node.data,\n step: {\n ...(node.data as ActionNodeData).step,\n [field]: value,\n },\n },\n } as Node)\n )\n );\n };\n};\n\nexport const createHandleUpdateInput = (setNodes: SetNodes) => {\n return (rfId: string, key: string, value: JsonValue | undefined) => {\n setNodes((nodes) =>\n nodes.map((node) => {\n if (node.id !== rfId) {\n return node;\n }\n const data = node.data as ActionNodeData;\n const baseInput = data.step?.input ?? {};\n const nextInput: Record<string, JsonValue> = {};\n Object.entries(baseInput).forEach(([existingKey, existingValue]) => {\n if (existingValue !== undefined) {\n nextInput[existingKey] = existingValue as JsonValue;\n }\n });\n if (value !== undefined) {\n nextInput[key] = value;\n }\n return {\n ...node,\n data: {\n ...data,\n step: { ...data.step, input: nextInput },\n },\n };\n })\n );\n };\n};\n\nexport const createHandleRemoveInputKey = (setNodes: SetNodes) => {\n return (rfId: string, key: string) =>\n setNodes((nodes) =>\n nodes.map((node) => {\n if (node.id !== rfId) {\n return node;\n }\n const data = node.data as ActionNodeData;\n const nextInput = { ...(data.step?.input ?? {}) };\n delete (nextInput as Record<string, JsonValue>)[key];\n return {\n ...node,\n data: {\n ...data,\n step: { ...data.step, input: nextInput },\n },\n };\n })\n );\n};\n\nexport const createHandleUpdateOutput = (setNodes: SetNodes) => {\n return (\n rfId: string,\n updater: (prev: ScaffolderTaskOutput) => ScaffolderTaskOutput\n ) => {\n setNodes((nodes) =>\n nodes.map((node) => {\n if (node.id !== rfId) {\n return node;\n }\n const data = node.data as OutputNodeData;\n const nextOutput = updater(data.output ?? {});\n return {\n ...node,\n data: {\n ...data,\n output: nextOutput,\n },\n };\n })\n );\n };\n};\n\nexport const createHandleUpdateSections = (setNodes: SetNodes) => {\n return (\n rfId: string,\n updater: (prev: ParameterSectionDisplay[]) => ParameterSectionDisplay[]\n ) => {\n setNodes((nodes) =>\n nodes.map((node) => {\n if (node.id !== rfId) {\n return node;\n }\n const data = node.data as ParametersNodeData;\n const nextSections = updater(data.sections ?? []);\n return {\n ...node,\n data: {\n ...data,\n sections: nextSections,\n parameters: sectionsToParametersValue(nextSections),\n },\n };\n })\n );\n };\n};\n\nexport const createHandleUpdateInputRequiredKeys = (setNodes: SetNodes) => {\n return (rfId: string, keys: string[]) =>\n setNodes((nodes) =>\n nodes.map((node) => {\n if (node.id !== rfId) {\n return node;\n }\n const data = node.data as ActionNodeData;\n return {\n ...node,\n data: {\n ...data,\n scaffolderActionInputRequiredById: {\n ...(data.scaffolderActionInputRequiredById ?? {}),\n [data.step?.action ?? \"\"]: keys,\n },\n },\n };\n })\n );\n};\n\nexport const createHandleRemoveNode = (\n setNodes: SetNodes,\n setEdges: SetEdges,\n options: CreateHandleRemoveNodeOptions\n) => {\n const { fixedXPosition, verticalSpacing } = options;\n return (rfId: string) => {\n setNodes((nodes) => {\n const parameterNodes = nodes.filter((n) => n.type === \"parametersNode\");\n const actionNodes = nodes.filter(\n (n) => n.type === \"actionNode\" && n.id !== rfId\n );\n const outputNodes = nodes.filter((n) => n.type === \"outputNode\");\n\n const ordered = orderNodes(parameterNodes, actionNodes, outputNodes);\n const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);\n setSequentialEdgesIfChanged(setEdges, aligned);\n return aligned;\n });\n };\n};\n\nexport const createHandleReorderAndAlignNodes = (\n setNodes: SetNodes,\n setEdges: SetEdges,\n options: CreateHandleRemoveNodeOptions\n) => {\n const { fixedXPosition, verticalSpacing } = options;\n return (node: Node) => {\n if (!node) {\n return;\n }\n setNodes((nodes) => {\n const parameterNodes = nodes.filter((n) => n.type === \"parametersNode\");\n const actionNodes = nodes.filter((n) => n.type === \"actionNode\");\n const outputNodes = nodes.filter((n) => n.type === \"outputNode\");\n\n if (node.type === \"parametersNode\") {\n return alignNodes(\n orderNodes(\n [node, ...parameterNodes.filter((n) => n.id !== node.id)],\n actionNodes,\n outputNodes\n ),\n fixedXPosition,\n verticalSpacing\n );\n }\n\n if (node.type === \"outputNode\") {\n return alignNodes(\n orderNodes(parameterNodes, actionNodes, [\n node,\n ...outputNodes.filter((n) => n.id !== node.id),\n ]),\n fixedXPosition,\n verticalSpacing\n );\n }\n\n const filteredActionNodes = actionNodes.filter((n) => n.id !== node.id);\n const targetIndex = filteredActionNodes.findIndex(\n (n) => n.position.y > node.position.y\n );\n if (targetIndex === -1) {\n filteredActionNodes.push(node);\n } else {\n filteredActionNodes.splice(targetIndex, 0, node);\n }\n\n const ordered = orderNodes(\n parameterNodes,\n filteredActionNodes,\n outputNodes\n );\n const aligned = alignNodes(ordered, fixedXPosition, verticalSpacing);\n setSequentialEdgesIfChanged(setEdges, aligned);\n return aligned;\n });\n };\n};\n"],"names":["nextActions"],"mappings":";;;;AA0CA,MAAM,UAAA,GAAa,CACjB,cAAA,EACA,WAAA,EACA,WAAA,KACG,CAAC,GAAG,cAAA,EAAgB,GAAG,WAAA,EAAa,GAAG,WAAW,CAAA;AAEvD,MAAM,2BAAA,GAA8B,CAClC,QAAA,EACA,YAAA,KACG;AACH,EAAA,QAAA,CAAS,CAAC,SAAA,KAAc;AACtB,IAAA,MAAM,SAAA,GAAY,sBAAsB,YAAY,CAAA;AACpD,IAAA,IACE,SAAA,CAAU,MAAA,KAAW,SAAA,CAAU,MAAA,IAC/B,SAAA,CAAU,KAAA;AAAA,MACR,CAAC,IAAA,EAAM,KAAA,KACL,IAAA,CAAK,MAAA,KAAW,SAAA,CAAU,KAAK,CAAA,EAAG,MAAA,IAClC,IAAA,CAAK,MAAA,KAAW,SAAA,CAAU,KAAK,CAAA,EAAG;AAAA,KACtC,EACA;AACA,MAAA,OAAO,SAAA;AAAA,IACT;AACA,IAAA,OAAO,SAAA;AAAA,EACT,CAAC,CAAA;AACH,CAAA;AAEO,MAAM,mBAAA,GAAsB,CACjC,QAAA,EACA,QAAA,EACA,OAAA,KACG;AACH,EAAA,MAAM;AAAA,IACJ,cAAA;AAAA,IACA,eAAA;AAAA,IACA,YAAA;AAAA,IACA,mBAAA;AAAA,IACA,0BAAA;AAAA,IACA,iCAAA;AAAA,IACA;AAAA,GACF,GAAI,OAAA;AAEJ,EAAA,OAAO,CAAC,MAAA,KAA0B;AAChC,IAAA,MAAM;AAAA,MACJ,SAAA;AAAA,MACA,IAAA,GAAO,YAAA;AAAA,MACP,YAAA;AAAA,MACA,cAAA;AAAA,MACA;AAAA,KACF,GAAI,MAAA;AACJ,IAAA,MAAM,QAAA,GAA6B,IAAA;AAEnC,IAAA,QAAA,CAAS,CAAC,KAAA,KAAU;AAClB,MAAA,MAAM,iBAAiB,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,gBAAgB,CAAA;AACtE,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,YAAY,CAAA;AAC/D,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,YAAY,CAAA;AAE/D,MAAA,MAAM,eAAA,GAAkB,CACtB,cAAA,EACAA,YAAAA,EACA,WAAA,KACG;AACH,QAAA,MAAM,OAAA,GAAU,UAAA,CAAW,cAAA,EAAgBA,YAAAA,EAAa,WAAW,CAAA;AACnE,QAAA,MAAM,OAAA,GAAU,UAAA,CAAW,OAAA,EAAS,cAAA,EAAgB,eAAe,CAAA;AACnE,QAAA,2BAAA,CAA4B,UAAU,OAAO,CAAA;AAC7C,QAAA,OAAO,OAAA;AAAA,MACT,CAAA;AAEA,MAAA,IAAI,aAAa,gBAAA,EAAkB;AACjC,QAAA,IAAI,cAAA,CAAe,SAAS,CAAA,EAAG;AAC7B,UAAA,OAAO,eAAA,CAAgB,cAAA,EAAgB,WAAA,EAAa,WAAW,CAAA;AAAA,QACjE;AAEA,QAAA,MAAM,cAAA,GAAiB,eAAA;AACvB,QAAA,MAAM,iBAAA,GACJ,kBAAA,KAAuB,MAAA,GAClB,IAAA,CAAK,KAAA;AAAA,UACJ,IAAA,CAAK,UAAU,kBAAkB;AAAA,SACnC,GACA,MAAA;AAEN,QAAA,OAAO,eAAA;AAAA,UACL;AAAA,YACE;AAAA,cACE,EAAA,EAAI,cAAA;AAAA,cACJ,IAAA,EAAM,gBAAA;AAAA,cACN,QAAA,EAAU,EAAE,CAAA,EAAG,cAAA,EAAgB,GAAG,CAAA,EAAE;AAAA,cACpC,IAAA,EAAM;AAAA,gBACJ,IAAA,EAAM,cAAA;AAAA,gBACN,UAAA,EAAY,iBAAA;AAAA,gBACZ,UACE,iBAAA,KAAsB,MAAA,GAClB,6BAAA,CAA8B,iBAAiB,IAC/C,EAAC;AAAA,gBACP,mBAAA;AAAA,gBACA,0BAAA;AAAA,gBACA,iCAAA;AAAA,gBACA;AAAA,eACF;AAAA,cACA,GAAG;AAAA;AACL,WACF;AAAA,UACA,WAAA;AAAA,UACA;AAAA,SACF;AAAA,MACF;AAEA,MAAA,IAAI,aAAa,YAAA,EAAc;AAC7B,QAAA,IAAI,WAAA,CAAY,SAAS,CAAA,EAAG;AAC1B,UAAA,OAAO,eAAA,CAAgB,cAAA,EAAgB,WAAA,EAAa,WAAW,CAAA;AAAA,QACjE;AAEA,QAAA,MAAM,UAAA,GAAa,WAAA;AACnB,QAAA,MAAM,aAAA,GAAgB,iBACjB,IAAA,CAAK,KAAA,CAAM,KAAK,SAAA,CAAU,cAAc,CAAC,CAAA,GAC1C,EAAC;AACL,QAAA,OAAO,eAAA,CAAgB,gBAAgB,WAAA,EAAa;AAAA,UAClD;AAAA,YACE,EAAA,EAAI,UAAA;AAAA,YACJ,IAAA,EAAM,YAAA;AAAA,YACN,QAAA,EAAU,EAAE,CAAA,EAAG,cAAA,EAAgB,GAAG,CAAA,EAAE;AAAA,YACpC,IAAA,EAAM;AAAA,cACJ,IAAA,EAAM,UAAA;AAAA,cACN,MAAA,EAAQ,aAAA;AAAA,cACR,mBAAA;AAAA,cACA,0BAAA;AAAA,cACA,iCAAA;AAAA,cACA;AAAA,aACF;AAAA,YACA,GAAG;AAAA;AACL,SACD,CAAA;AAAA,MACH;AAGA,MAAA,MAAM,UAAA,GAAa,CAAA,UAAA,EAAa,IAAA,CAAK,MAAA,EAAO,CAAE,QAAA,CAAS,EAAE,CAAA,CAAE,KAAA,CAAM,CAAA,EAAG,CAAC,CAAC,CAAA,CAAA;AACtE,MAAA,MAAM,OAAA,GAAU;AAAA,QACd,EAAA,EACE,YAAA,EAAc,EAAA,IACd,CAAA,QAAA,EAAW,IAAA,CAAK,MAAA,EAAO,CAAE,QAAA,CAAS,EAAE,CAAA,CAAE,KAAA,CAAM,CAAA,EAAG,CAAC,CAAC,CAAA,CAAA;AAAA,QACnD,IAAA,EAAM,cAAc,IAAA,IAAQ,EAAA;AAAA,QAC5B,MAAA,EAAQ,cAAc,MAAA,IAAU,EAAA;AAAA,QAChC,OAAO,EAAE,GAAI,YAAA,EAAc,KAAA,IAAS,EAAC,EAAG;AAAA,QACxC,GAAI,gBAAgB;AAAC,OACvB;AAEA,MAAA,MAAM,WAAA,GAAc,CAAC,GAAG,WAAW,CAAA;AACnC,MAAA,MAAM,oBAAoB,WAAA,CAAY,IAAA;AAAA,QACpC,CAAC,IAAA,KAAS,IAAA,CAAK,EAAA,KAAO;AAAA,OACxB;AACA,MAAA,IAAI,cAAc,WAAA,CAAY,MAAA;AAC9B,MAAA,IAAI,SAAA,EAAW;AACb,QAAA,IAAI,iBAAA,EAAmB;AACrB,UAAA,WAAA,GAAc,WAAA,CAAY,MAAA;AAAA,QAC5B,CAAA,MAAO;AACL,UAAA,WAAA,GAAc,IAAA,CAAK,GAAA;AAAA,YACjB,YAAY,SAAA,CAAU,CAAC,SAAS,IAAA,CAAK,EAAA,KAAO,SAAS,CAAA,GAAI,CAAA;AAAA,YACzD;AAAA,WACF;AAAA,QACF;AAAA,MACF;AACA,MAAA,WAAA,CAAY,MAAA,CAAO,aAAa,CAAA,EAAG;AAAA,QACjC,EAAA,EAAI,UAAA;AAAA,QACJ,IAAA,EAAM,YAAA;AAAA,QACN,QAAA,EAAU,EAAE,CAAA,EAAG,cAAA,EAAgB,GAAG,CAAA,EAAE;AAAA,QACpC,IAAA,EAAM;AAAA,UACJ,IAAA,EAAM,UAAA;AAAA,UACN,IAAA,EAAM,OAAA;AAAA,UACN,mBAAA;AAAA,UACA,0BAAA;AAAA,UACA,iCAAA;AAAA,UACA;AAAA,SACF;AAAA,QACA,GAAG;AAAA,OACJ,CAAA;AAED,MAAA,OAAA,CAAQ,cAAc,UAAU,CAAA;AAChC,MAAA,OAAO,eAAA,CAAgB,cAAA,EAAgB,WAAA,EAAa,WAAW,CAAA;AAAA,IACjE,CAAC,CAAA;AAAA,EACH,CAAA;AACF;AAEO,MAAM,uBAAA,GAA0B,CAAC,QAAA,KAAuB;AAC7D,EAAA,OAAO,CAAC,IAAA,EAAc,KAAA,EAAuB,KAAA,KAAkB;AAC7D,IAAA,QAAA;AAAA,MAAS,CAAC,UACR,KAAA,CAAM,GAAA;AAAA,QAAI,CAAC,IAAA,KACT,IAAA,CAAK,EAAA,KAAO,OACR,IAAA,GACC;AAAA,UACC,GAAG,IAAA;AAAA,UACH,IAAA,EAAM;AAAA,YACJ,GAAG,IAAA,CAAK,IAAA;AAAA,YACR,IAAA,EAAM;AAAA,cACJ,GAAI,KAAK,IAAA,CAAwB,IAAA;AAAA,cACjC,CAAC,KAAK,GAAG;AAAA;AACX;AACF;AACF;AACN,KACF;AAAA,EACF,CAAA;AACF;AAEO,MAAM,uBAAA,GAA0B,CAAC,QAAA,KAAuB;AAC7D,EAAA,OAAO,CAAC,IAAA,EAAc,GAAA,EAAa,KAAA,KAAiC;AAClE,IAAA,QAAA;AAAA,MAAS,CAAC,KAAA,KACR,KAAA,CAAM,GAAA,CAAI,CAAC,IAAA,KAAS;AAClB,QAAA,IAAI,IAAA,CAAK,OAAO,IAAA,EAAM;AACpB,UAAA,OAAO,IAAA;AAAA,QACT;AACA,QAAA,MAAM,OAAO,IAAA,CAAK,IAAA;AAClB,QAAA,MAAM,SAAA,GAAY,IAAA,CAAK,IAAA,EAAM,KAAA,IAAS,EAAC;AACvC,QAAA,MAAM,YAAuC,EAAC;AAC9C,QAAA,MAAA,CAAO,OAAA,CAAQ,SAAS,CAAA,CAAE,OAAA,CAAQ,CAAC,CAAC,WAAA,EAAa,aAAa,CAAA,KAAM;AAClE,UAAA,IAAI,kBAAkB,MAAA,EAAW;AAC/B,YAAA,SAAA,CAAU,WAAW,CAAA,GAAI,aAAA;AAAA,UAC3B;AAAA,QACF,CAAC,CAAA;AACD,QAAA,IAAI,UAAU,MAAA,EAAW;AACvB,UAAA,SAAA,CAAU,GAAG,CAAA,GAAI,KAAA;AAAA,QACnB;AACA,QAAA,OAAO;AAAA,UACL,GAAG,IAAA;AAAA,UACH,IAAA,EAAM;AAAA,YACJ,GAAG,IAAA;AAAA,YACH,MAAM,EAAE,GAAG,IAAA,CAAK,IAAA,EAAM,OAAO,SAAA;AAAU;AACzC,SACF;AAAA,MACF,CAAC;AAAA,KACH;AAAA,EACF,CAAA;AACF;AAEO,MAAM,0BAAA,GAA6B,CAAC,QAAA,KAAuB;AAChE,EAAA,OAAO,CAAC,MAAc,GAAA,KACpB,QAAA;AAAA,IAAS,CAAC,KAAA,KACR,KAAA,CAAM,GAAA,CAAI,CAAC,IAAA,KAAS;AAClB,MAAA,IAAI,IAAA,CAAK,OAAO,IAAA,EAAM;AACpB,QAAA,OAAO,IAAA;AAAA,MACT;AACA,MAAA,MAAM,OAAO,IAAA,CAAK,IAAA;AAClB,MAAA,MAAM,YAAY,EAAE,GAAI,KAAK,IAAA,EAAM,KAAA,IAAS,EAAC,EAAG;AAChD,MAAA,OAAQ,UAAwC,GAAG,CAAA;AACnD,MAAA,OAAO;AAAA,QACL,GAAG,IAAA;AAAA,QACH,IAAA,EAAM;AAAA,UACJ,GAAG,IAAA;AAAA,UACH,MAAM,EAAE,GAAG,IAAA,CAAK,IAAA,EAAM,OAAO,SAAA;AAAU;AACzC,OACF;AAAA,IACF,CAAC;AAAA,GACH;AACJ;AAEO,MAAM,wBAAA,GAA2B,CAAC,QAAA,KAAuB;AAC9D,EAAA,OAAO,CACL,MACA,OAAA,KACG;AACH,IAAA,QAAA;AAAA,MAAS,CAAC,KAAA,KACR,KAAA,CAAM,GAAA,CAAI,CAAC,IAAA,KAAS;AAClB,QAAA,IAAI,IAAA,CAAK,OAAO,IAAA,EAAM;AACpB,UAAA,OAAO,IAAA;AAAA,QACT;AACA,QAAA,MAAM,OAAO,IAAA,CAAK,IAAA;AAClB,QAAA,MAAM,UAAA,GAAa,OAAA,CAAQ,IAAA,CAAK,MAAA,IAAU,EAAE,CAAA;AAC5C,QAAA,OAAO;AAAA,UACL,GAAG,IAAA;AAAA,UACH,IAAA,EAAM;AAAA,YACJ,GAAG,IAAA;AAAA,YACH,MAAA,EAAQ;AAAA;AACV,SACF;AAAA,MACF,CAAC;AAAA,KACH;AAAA,EACF,CAAA;AACF;AAEO,MAAM,0BAAA,GAA6B,CAAC,QAAA,KAAuB;AAChE,EAAA,OAAO,CACL,MACA,OAAA,KACG;AACH,IAAA,QAAA;AAAA,MAAS,CAAC,KAAA,KACR,KAAA,CAAM,GAAA,CAAI,CAAC,IAAA,KAAS;AAClB,QAAA,IAAI,IAAA,CAAK,OAAO,IAAA,EAAM;AACpB,UAAA,OAAO,IAAA;AAAA,QACT;AACA,QAAA,MAAM,OAAO,IAAA,CAAK,IAAA;AAClB,QAAA,MAAM,YAAA,GAAe,OAAA,CAAQ,IAAA,CAAK,QAAA,IAAY,EAAE,CAAA;AAChD,QAAA,OAAO;AAAA,UACL,GAAG,IAAA;AAAA,UACH,IAAA,EAAM;AAAA,YACJ,GAAG,IAAA;AAAA,YACH,QAAA,EAAU,YAAA;AAAA,YACV,UAAA,EAAY,0BAA0B,YAAY;AAAA;AACpD,SACF;AAAA,MACF,CAAC;AAAA,KACH;AAAA,EACF,CAAA;AACF;AAwBO,MAAM,sBAAA,GAAyB,CACpC,QAAA,EACA,QAAA,EACA,OAAA,KACG;AACH,EAAA,MAAM,EAAE,cAAA,EAAgB,eAAA,EAAgB,GAAI,OAAA;AAC5C,EAAA,OAAO,CAAC,IAAA,KAAiB;AACvB,IAAA,QAAA,CAAS,CAAC,KAAA,KAAU;AAClB,MAAA,MAAM,iBAAiB,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,gBAAgB,CAAA;AACtE,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA;AAAA,QACxB,CAAC,CAAA,KAAM,CAAA,CAAE,IAAA,KAAS,YAAA,IAAgB,EAAE,EAAA,KAAO;AAAA,OAC7C;AACA,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,YAAY,CAAA;AAE/D,MAAA,MAAM,OAAA,GAAU,UAAA,CAAW,cAAA,EAAgB,WAAA,EAAa,WAAW,CAAA;AACnE,MAAA,MAAM,OAAA,GAAU,UAAA,CAAW,OAAA,EAAS,cAAA,EAAgB,eAAe,CAAA;AACnE,MAAA,2BAAA,CAA4B,UAAU,OAAO,CAAA;AAC7C,MAAA,OAAO,OAAA;AAAA,IACT,CAAC,CAAA;AAAA,EACH,CAAA;AACF;AAEO,MAAM,gCAAA,GAAmC,CAC9C,QAAA,EACA,QAAA,EACA,OAAA,KACG;AACH,EAAA,MAAM,EAAE,cAAA,EAAgB,eAAA,EAAgB,GAAI,OAAA;AAC5C,EAAA,OAAO,CAAC,IAAA,KAAe;AACrB,IAAA,IAAI,CAAC,IAAA,EAAM;AACT,MAAA;AAAA,IACF;AACA,IAAA,QAAA,CAAS,CAAC,KAAA,KAAU;AAClB,MAAA,MAAM,iBAAiB,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,gBAAgB,CAAA;AACtE,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,YAAY,CAAA;AAC/D,MAAA,MAAM,cAAc,KAAA,CAAM,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,SAAS,YAAY,CAAA;AAE/D,MAAA,IAAI,IAAA,CAAK,SAAS,gBAAA,EAAkB;AAClC,QAAA,OAAO,UAAA;AAAA,UACL,UAAA;AAAA,YACE,CAAC,IAAA,EAAM,GAAG,cAAA,CAAe,MAAA,CAAO,CAAC,CAAA,KAAM,CAAA,CAAE,EAAA,KAAO,IAAA,CAAK,EAAE,CAAC,CAAA;AAAA,YACxD,WAAA;AAAA,YACA;AAAA,WACF;AAAA,UACA,cAAA;AAAA,UACA;AAAA,SACF;AAAA,MACF;AAEA,MAAA,IAAI,IAAA,CAAK,SAAS,YAAA,EAAc;AAC9B,QAAA,OAAO,UAAA;AAAA,UACL,UAAA,CAAW,gBAAgB,WAAA,EAAa;AAAA,YACtC,IAAA;AAAA,YACA,GAAG,YAAY,MAAA,CAAO,CAAC,MAAM,CAAA,CAAE,EAAA,KAAO,KAAK,EAAE;AAAA,WAC9C,CAAA;AAAA,UACD,cAAA;AAAA,UACA;AAAA,SACF;AAAA,MACF;AAEA,MAAA,MAAM,mBAAA,GAAsB,YAAY,MAAA,CAAO,CAAC,MAAM,CAAA,CAAE,EAAA,KAAO,KAAK,EAAE,CAAA;AACtE,MAAA,MAAM,cAAc,mBAAA,CAAoB,SAAA;AAAA,QACtC,CAAC,CAAA,KAAM,CAAA,CAAE,QAAA,CAAS,CAAA,GAAI,KAAK,QAAA,CAAS;AAAA,OACtC;AACA,MAAA,IAAI,gBAAgB,EAAA,EAAI;AACtB,QAAA,mBAAA,CAAoB,KAAK,IAAI,CAAA;AAAA,MAC/B,CAAA,MAAO;AACL,QAAA,mBAAA,CAAoB,MAAA,CAAO,WAAA,EAAa,CAAA,EAAG,IAAI,CAAA;AAAA,MACjD;AAEA,MAAA,MAAM,OAAA,GAAU,UAAA;AAAA,QACd,cAAA;AAAA,QACA,mBAAA;AAAA,QACA;AAAA,OACF;AACA,MAAA,MAAM,OAAA,GAAU,UAAA,CAAW,OAAA,EAAS,cAAA,EAAgB,eAAe,CAAA;AACnE,MAAA,2BAAA,CAA4B,UAAU,OAAO,CAAA;AAC7C,MAAA,OAAO,OAAA;AAAA,IACT,CAAC,CAAA;AAAA,EACH,CAAA;AACF;;;;"}
@@ -0,0 +1,166 @@
1
+ import { alignNodes } from './nodeLayout.esm.js';
2
+ import { normalizeParametersToSections } from './parameterTransforms.esm.js';
3
+ import { nodeDefaults, FLOW_LAYOUT } from '../components/designerFlowConfig.esm.js';
4
+
5
+ const sanitizeForRfId = (value) => value.replace(/[^a-zA-Z0-9-_.:]/g, "_");
6
+ const buildRfId = (step, index) => {
7
+ if (step && typeof step.id === "string" && step.id.trim().length > 0) {
8
+ return `rf-${sanitizeForRfId(step.id)}-${index}`;
9
+ }
10
+ return `rf-${index + 1}`;
11
+ };
12
+ const cloneStep = (step) => JSON.parse(JSON.stringify(step ?? {}));
13
+ const cloneOutput = (output) => JSON.parse(JSON.stringify(output ?? {}));
14
+ const cloneParameters = (parameters) => parameters === void 0 ? void 0 : JSON.parse(JSON.stringify(parameters));
15
+ const buildNodesFromModel = (steps, parameters, output, options) => {
16
+ const {
17
+ scaffolderActionIds,
18
+ scaffolderActionInputsById,
19
+ scaffolderActionOutputsById,
20
+ scaffolderActionInputRequiredById
21
+ } = options;
22
+ const parameterSections = normalizeParametersToSections(parameters);
23
+ const nodes = [];
24
+ const rfParametersId = "rf-parameters";
25
+ nodes.push({
26
+ id: rfParametersId,
27
+ type: "parametersNode",
28
+ position: { x: FLOW_LAYOUT.fixedXPosition, y: 0 },
29
+ data: {
30
+ rfId: rfParametersId,
31
+ parameters: cloneParameters(parameters),
32
+ sections: parameterSections,
33
+ scaffolderActionIds,
34
+ scaffolderActionInputsById,
35
+ scaffolderActionInputRequiredById,
36
+ scaffolderActionOutputsById
37
+ },
38
+ ...nodeDefaults
39
+ });
40
+ const rfOutputId = "rf-output";
41
+ nodes.push({
42
+ id: rfOutputId,
43
+ type: "outputNode",
44
+ position: {
45
+ x: FLOW_LAYOUT.fixedXPosition,
46
+ y: FLOW_LAYOUT.verticalSpacing * (steps.length + 1)
47
+ },
48
+ data: {
49
+ rfId: rfOutputId,
50
+ output: cloneOutput(output),
51
+ scaffolderActionIds,
52
+ scaffolderActionInputsById,
53
+ scaffolderActionInputRequiredById,
54
+ scaffolderActionOutputsById
55
+ },
56
+ ...nodeDefaults
57
+ });
58
+ steps.forEach((step, index) => {
59
+ const rfId = buildRfId(step, index);
60
+ nodes.splice(index + 1, 0, {
61
+ id: rfId,
62
+ type: "actionNode",
63
+ position: {
64
+ x: FLOW_LAYOUT.fixedXPosition,
65
+ y: FLOW_LAYOUT.verticalSpacing * (index + 1)
66
+ },
67
+ data: {
68
+ rfId,
69
+ step: cloneStep(step),
70
+ scaffolderActionIds,
71
+ scaffolderActionInputsById,
72
+ scaffolderActionInputRequiredById,
73
+ scaffolderActionOutputsById
74
+ },
75
+ ...nodeDefaults
76
+ });
77
+ });
78
+ return alignNodes(
79
+ nodes,
80
+ FLOW_LAYOUT.fixedXPosition,
81
+ FLOW_LAYOUT.verticalSpacing
82
+ );
83
+ };
84
+ const extractStepsFromNodes = (nodes) => {
85
+ const actionNodes = nodes.filter(
86
+ (node) => node.type === "actionNode"
87
+ );
88
+ return actionNodes.map((node) => cloneStep(node.data.step));
89
+ };
90
+ const extractParametersFromNodes = (nodes) => {
91
+ const parametersNode = nodes.find(
92
+ (node) => node.type === "parametersNode"
93
+ );
94
+ if (!parametersNode) {
95
+ return [];
96
+ }
97
+ return cloneParameters(parametersNode.data.parameters);
98
+ };
99
+ const extractOutputFromNodes = (nodes) => {
100
+ const outputNode = nodes.find((node) => node.type === "outputNode");
101
+ if (!outputNode) {
102
+ return void 0;
103
+ }
104
+ return cloneOutput(outputNode.data.output);
105
+ };
106
+ const collectParameterReferences = (parameters) => {
107
+ if (!parameters || !Array.isArray(parameters)) {
108
+ return [];
109
+ }
110
+ return parameters.flatMap(
111
+ (param) => Object.keys(param?.properties ?? {}).map(
112
+ (propKey) => `parameters.${propKey}`
113
+ )
114
+ );
115
+ };
116
+ const collectStepOutputReferences = (nodes, parameterReferences) => {
117
+ const formatRef = (ref) => `\${{ ${ref} }}`;
118
+ const actionNodes = nodes.filter(
119
+ (node) => node.type === "actionNode"
120
+ );
121
+ const outputNode = nodes.find((node) => node.type === "outputNode");
122
+ const references = {};
123
+ actionNodes.forEach((node, index) => {
124
+ const priorSteps = actionNodes.slice(0, index).map((n) => n.data?.step?.id).filter(Boolean);
125
+ const priorStepRefs = priorSteps.map(
126
+ (id) => formatRef(`steps.${id}.output`)
127
+ );
128
+ const priorIds = priorSteps.map((id) => formatRef(`steps.${id}.id`));
129
+ const parameterRefs = parameterReferences.map((ref) => formatRef(ref));
130
+ const thisStepId = node.data?.step?.id;
131
+ if (!thisStepId) {
132
+ references[node.id] = [...parameterRefs, ...priorStepRefs, ...priorIds];
133
+ return;
134
+ }
135
+ const outputRefs = [
136
+ formatRef(`steps.${thisStepId}.output`),
137
+ ...priorStepRefs,
138
+ ...parameterRefs
139
+ ];
140
+ references[node.id] = Array.from(new Set(outputRefs));
141
+ });
142
+ if (outputNode) {
143
+ const allSteps = actionNodes.map((n) => n.data?.step?.id).filter(Boolean);
144
+ const refs = [
145
+ ...allSteps.map((id) => formatRef(`steps.${id}.output`)),
146
+ ...parameterReferences.map((ref) => formatRef(ref))
147
+ ];
148
+ references[outputNode.id] = Array.from(new Set(refs));
149
+ }
150
+ return references;
151
+ };
152
+ const stableStringify = (value) => JSON.stringify(value, (_key, v) => {
153
+ if (Array.isArray(v)) {
154
+ return v;
155
+ }
156
+ if (v && typeof v === "object") {
157
+ return Object.keys(v).sort().reduce((acc, k) => {
158
+ acc[k] = v[k];
159
+ return acc;
160
+ }, {});
161
+ }
162
+ return v;
163
+ });
164
+
165
+ export { buildNodesFromModel, cloneOutput, cloneParameters, cloneStep, collectParameterReferences, collectStepOutputReferences, extractOutputFromNodes, extractParametersFromNodes, extractStepsFromNodes, stableStringify };
166
+ //# sourceMappingURL=model.esm.js.map