Portal Community

NodeInspectorData Shape

// nodeInspector.ts
export interface NodeInspectorData {
    nodeId        : string;
    nodeLabel     : string;
    status        : NodeExecutionStatus;
    inputData     : unknown;   // What this node received as input
    outputData    : unknown;   // What this node returned as output
    pinnedData    : unknown;   // Pinned data from Process_NodePinnedData (if any)
    logs          : LogEntry[]; // Logs emitted by this node during this execution
    metrics       : NodeMetrics;
}

export interface NodeMetrics {
    executionDurationMs : number | null;
    retryCount          : number;
    spanId              : string | null;  // OTel span ID — links to trace
    traceId             : string | null;
}

Selecting a Node in Execution Mode

// When user clicks a node on the canvas in execution mode:
async function handleNodeClick(nodeId: string) {
    const { executionId } = useExecutionStore.getState();
    if (!executionId) return;

    // Set selected node immediately (shows loading state)
    useExecutionStore.getState().setSelectedNodeId(nodeId);
    useExecutionStore.getState().setNodeInspectorData(null);  // clear previous

    // Fetch inspector data for this node from the API
    const data = await executionApiClient.getNodeInspectorData(executionId, nodeId);

    useExecutionStore.getState().setNodeInspectorData(data);

    // Switch Observer Panel to Inspector tab
    useFlowObserverPanelStore.getState().setActiveTab('node-inspector');
}

Inspector Tab Reading the Data

// NodeInspectorTabContent.tsx
import { shallow } from 'zustand/shallow';

function NodeInspectorTabContent() {
    const { selectedNodeId, nodeInspectorData } = useExecutionStore(
        state => ({
            selectedNodeId   : state.selectedNodeId,
            nodeInspectorData: state.nodeInspectorData
        }),
        shallow
    );

    if (!selectedNodeId)      return <p>Click a node to inspect.</p>;
    if (!nodeInspectorData)   return <Spinner />;

    return (
        <div>
            <h3>{nodeInspectorData.nodeLabel}</h3>
            <StatusBadge status={nodeInspectorData.status.status} />
            <JsonSection title="Input"  data={nodeInspectorData.inputData}  />
            <JsonSection title="Output" data={nodeInspectorData.outputData} />
            {nodeInspectorData.pinnedData &&
                <JsonSection title="Pinned Data" data={nodeInspectorData.pinnedData} />}
        </div>
    );
}