import React from 'react'; const NODE_LAYOUT = [ { id: 'draft_internal_memo', label: 'Draft Internal Memo', x: 80, y: 70, tier: 1 }, { id: 'schedule_conversation', label: 'Schedule Conversation', x: 80, y: 190, tier: 1 }, { id: 'review_contract_internally', label: 'Review Contract Internally', x: 80, y: 310, tier: 1 }, { id: 'begin_internal_investigation', label: 'Begin Internal Investigation', x: 80, y: 430, tier: 1 }, { id: 'send_internal_communication', label: 'Send Internal Communication', x: 350, y: 110, tier: 2 }, { id: 'reassign_project_lead', label: 'Reassign Project Lead', x: 350, y: 230, tier: 2 }, { id: 'prepare_response_draft', label: 'Prepare Response Draft', x: 350, y: 350, tier: 2 }, { id: 'align_with_legal', label: 'Align With Legal', x: 350, y: 470, tier: 2 }, { id: 'send_external_communication', label: 'Send External Communication', x: 620, y: 140, tier: 3 }, { id: 'approve_staged_rollout', label: 'Approve Staged Rollout', x: 620, y: 260, tier: 3 }, { id: 'delay_release', label: 'Delay Release', x: 620, y: 380, tier: 3 }, { id: 'issue_public_statement', label: 'Issue Public Statement', x: 620, y: 500, tier: 4 }, { id: 'communicate_resolution_externally', label: 'Communicate Resolution Externally', x: 900, y: 220, tier: 4 }, { id: 'approve_full_launch', label: 'Approve Full Launch', x: 900, y: 340, tier: 4 }, { id: 'initiate_hr_formal_process', label: 'Initiate HR Process', x: 900, y: 460, tier: 5 }, { id: 'update_contract_system', label: 'Update Contract System', x: 1180, y: 210, tier: 5 }, { id: 'update_internal_records', label: 'Update Internal Records', x: 1180, y: 330, tier: 5 }, { id: 'schedule_client_follow_up', label: 'Schedule Client Follow-Up', x: 1180, y: 450, tier: 5 }, ]; const EDGES = [ ['draft_internal_memo', 'send_internal_communication'], ['schedule_conversation', 'reassign_project_lead'], ['review_contract_internally', 'align_with_legal'], ['begin_internal_investigation', 'prepare_response_draft'], ['send_internal_communication', 'send_external_communication'], ['reassign_project_lead', 'approve_staged_rollout'], ['prepare_response_draft', 'issue_public_statement'], ['align_with_legal', 'communicate_resolution_externally'], ['send_external_communication', 'issue_public_statement'], ['approve_staged_rollout', 'approve_full_launch'], ['issue_public_statement', 'communicate_resolution_externally'], ['communicate_resolution_externally', 'update_contract_system'], ['communicate_resolution_externally', 'update_internal_records'], ['communicate_resolution_externally', 'schedule_client_follow_up'], ]; function buildNodeMap(lockedActions = {}) { const lockedKeys = Array.isArray(lockedActions) ? Object.fromEntries(lockedActions.map((actionId) => [actionId, 'Locked by prior irreversible action'])) : lockedActions && typeof lockedActions === 'object' ? lockedActions : {}; const lockLookup = new Set(Object.keys(lockedKeys)); return NODE_LAYOUT.map((node) => { const locked = lockLookup.has(node.id); return { ...node, locked, reason: locked ? lockedKeys[node.id] : '', }; }); } function edgePath(source, target) { const startX = source.x + 190; const startY = source.y + 28; const endX = target.x; const endY = target.y + 28; const c1X = startX + 90; const c1Y = startY; const c2X = endX - 90; const c2Y = endY; return `M ${startX} ${startY} C ${c1X} ${c1Y}, ${c2X} ${c2Y}, ${endX} ${endY}`; } export default function DecisionGraph({ lockedActions = {}, recentActions = [] }) { const nodes = buildNodeMap(lockedActions); const byId = new Map(nodes.map((node) => [node.id, node])); return (
Locked actions turn dark red with causal provenance.