/** * System Flow Manifest — 카테고리별 JSON 병합 + 타입 정의 * * 노드/엣지 데이터는 카테고리별 JSON 파일로 분할 관리되며, * 이 파일에서 import + concat 후 단일 manifest로 export. */ import metaJson from './meta.json'; import ingest from './01-ingest.json'; import pipeline from './02-pipeline.json'; import algorithms from './03-algorithms.json'; import fleet from './04-fleet.json'; import output from './05-output.json'; import storage from './06-storage.json'; import backend from './07-backend.json'; import frontend from './08-frontend.json'; import decision from './09-decision.json'; import external from './10-external.json'; import edgesJson from './edges.json'; // ─── 타입 정의 ────────────────────────────────────────────── export type NodeKind = | 'source' // 원천 데이터 (snpdb 등) | 'cache' // 메모리/Redis 캐시 | 'pipeline' // 7단계 분류 파이프라인 단계 | 'algorithm' // 분석 알고리즘 | 'output' // 출력 모듈 (event_generator 등) | 'storage' // DB 테이블 | 'api' // 백엔드 API 엔드포인트 | 'ui' // 프론트 화면 | 'decision' // 운영자 의사결정 액션 | 'external'; // 외부 시스템 (iran, GPKI 등) export type NodeTrigger = | 'scheduled' // 5분 주기 등 자동 | 'event' // 이벤트 체이닝 | 'user_action' // 운영자 클릭/입력 | 'on_demand'; // 사용자 조회 시 export type NodeStatus = 'implemented' | 'partial' | 'planned' | 'deprecated'; export type EdgeKind = 'data' | 'trigger' | 'feedback'; export interface FlowNode { id: string; label: string; shortDescription: string; stage: string; menu?: string; kind: NodeKind; trigger: NodeTrigger; status: NodeStatus; file?: string; symbol?: string; lineRange?: [number, number]; inputs?: string[]; outputs?: string[]; params?: string[]; rules?: string[]; actor?: string; triggers?: string[]; tags?: string[]; notes?: string; position?: { x: number; y: number }; } export interface FlowEdge { id: string; source: string; target: string; label?: string; detail?: string; kind?: EdgeKind; } export interface FlowMeta { version: string; updatedAt: string; releaseDate?: string; description: string; nodeCount?: number; edgeCount?: number; } export interface FlowManifest { meta: FlowMeta; nodes: FlowNode[]; edges: FlowEdge[]; } // ─── 병합 ────────────────────────────────────────────────── const allNodes: FlowNode[] = [ ...(ingest as FlowNode[]), ...(pipeline as FlowNode[]), ...(algorithms as FlowNode[]), ...(fleet as FlowNode[]), ...(output as FlowNode[]), ...(storage as FlowNode[]), ...(backend as FlowNode[]), ...(frontend as FlowNode[]), ...(decision as FlowNode[]), ...(external as FlowNode[]), ]; const allEdges: FlowEdge[] = edgesJson as FlowEdge[]; export const manifest: FlowManifest = { meta: { ...(metaJson as FlowMeta), nodeCount: allNodes.length, edgeCount: allEdges.length, }, nodes: allNodes, edges: allEdges, }; // ─── stage 색상 매핑 (다크 테마) ────────────────────────── export const STAGE_COLORS: Record = { 수집: '#38bdf8', // sky-400 캐시: '#a78bfa', // violet-400 파이프라인: '#60a5fa', // blue-400 분석: '#c084fc', // purple-400 선단: '#f472b6', // pink-400 출력: '#fb923c', // orange-400 저장소: '#facc15', // yellow-400 API: '#22c55e', // green-500 UI: '#14b8a6', // teal-500 의사결정: '#f59e0b', // amber-500 외부: '#94a3b8', // slate-400 }; export const KIND_LABELS: Record = { source: '원천', cache: '캐시', pipeline: '파이프라인', algorithm: '알고리즘', output: '출력 모듈', storage: '저장소', api: 'API', ui: '화면', decision: '의사결정', external: '외부', }; export const TRIGGER_LABELS: Record = { scheduled: '주기 자동', event: '이벤트', user_action: '사용자 액션', on_demand: '조회 시', }; export const STATUS_LABELS: Record = { implemented: '구현됨', partial: '부분 구현', planned: '계획', deprecated: '폐기 예정', }; export const ALL_STAGES = Array.from(new Set(allNodes.map((n) => n.stage))); export const ALL_MENUS = Array.from( new Set(allNodes.map((n) => n.menu).filter(Boolean) as string[]), );