// Planu — Mermaid Diagram Generator
// Generates Mermaid diagrams based on spec type, scope, and project context
/**
 * Generate all applicable diagrams for a spec based on its scope and context.
 */
export function generateDiagrams(spec, knowledge, options) {
    const diagrams = [];
    // Data flow diagram for ALL specs (except trivial)
    if (spec.scope !== 'trivial') {
        diagrams.push(generateDataFlowDiagram(spec, knowledge));
    }
    // ER diagram if database changes
    if (options.hasDatabase) {
        diagrams.push(generateErDiagram(spec, knowledge));
    }
    // Sequence diagram if scope >= cross-module
    if (isScopeAtLeast(spec.scope, 'cross-module')) {
        diagrams.push(generateSequenceDiagram(spec, knowledge));
    }
    // Component diagram if UI
    if (options.hasUi) {
        diagrams.push(generateComponentDiagram(spec, knowledge));
    }
    // State machine diagram if transitions
    if (options.hasTransitions) {
        diagrams.push(generateStateDiagram(spec));
    }
    // Architecture diagram if scope = architectural
    if (spec.scope === 'architectural') {
        diagrams.push(generateArchitectureDiagram(spec, knowledge));
    }
    return diagrams;
}
/**
 * Generate a data flow diagram: Client -> Action -> Service -> Repo -> DB
 */
export function generateDataFlowDiagram(spec, knowledge) {
    const layers = buildLayers(spec.target, knowledge);
    const lines = ['graph LR'];
    layers.forEach((from, i) => {
        const to = layers[i + 1];
        if (to) {
            lines.push(`  ${from.id}[${from.label}] --> ${to.id}[${to.label}]`);
        }
    });
    return {
        type: 'data-flow',
        title: `Data Flow — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: 'Data flow diagram showing how data moves through the system layers.',
    };
}
/**
 * Generate an ER diagram for database changes.
 */
export function generateErDiagram(spec, knowledge) {
    const dbEngine = knowledge?.database ?? 'unknown';
    const lines = [
        'erDiagram',
        `  %% Database: ${dbEngine}`,
        `  %% Spec: ${spec.title}`,
        '  ENTITY_A {',
        '    string id PK',
        '    string name',
        '    datetime created_at',
        '  }',
        '  ENTITY_B {',
        '    string id PK',
        '    string entity_a_id FK',
        '    string value',
        '  }',
        '  ENTITY_A ||--o{ ENTITY_B : "has many"',
    ];
    return {
        type: 'er',
        title: `Entity Relationship — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: 'Entity-relationship diagram for database schema changes. Customize entities to match your domain.',
    };
}
/**
 * Generate a sequence diagram for cross-module interactions.
 */
export function generateSequenceDiagram(spec, knowledge) {
    const participants = buildParticipants(spec.target, knowledge);
    const lines = ['sequenceDiagram'];
    for (const p of participants) {
        lines.push(`  participant ${p.id} as ${p.label}`);
    }
    // Generate basic request-response flow
    const first = participants[0];
    const second = participants[1];
    if (first && second) {
        lines.push(`  ${first.id}->>+${second.id}: Request`);
        const third = participants[2];
        if (third) {
            lines.push(`  ${second.id}->>+${third.id}: Process`);
            lines.push(`  ${third.id}-->>-${second.id}: Result`);
        }
        lines.push(`  ${second.id}-->>-${first.id}: Response`);
    }
    return {
        type: 'sequence',
        title: `Sequence Diagram — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: 'Sequence diagram showing interactions between modules. Customize messages to match your flow.',
    };
}
/**
 * Generate a component diagram for UI specs.
 */
export function generateComponentDiagram(spec, knowledge) {
    const framework = knowledge?.framework ?? 'UI';
    const lines = [
        'graph TD',
        `  Page["${spec.title} Page"]`,
        `  Page --> Header[Header]`,
        `  Page --> Main[Main Content]`,
        `  Page --> Footer[Footer]`,
        `  Main --> CompA["Component A"]`,
        `  Main --> CompB["Component B"]`,
        `  CompA --> Store["${framework} State"]`,
        `  CompB --> Store`,
    ];
    return {
        type: 'component',
        title: `Component Diagram — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: 'UI component hierarchy diagram. Customize components to match your design.',
    };
}
/**
 * Generate a state machine diagram for transitions.
 */
export function generateStateDiagram(spec) {
    const lines = [
        'stateDiagram-v2',
        `  [*] --> Initial`,
        `  Initial --> Processing: Start`,
        `  Processing --> Success: Complete`,
        `  Processing --> Error: Fail`,
        `  Error --> Processing: Retry`,
        `  Success --> [*]`,
    ];
    return {
        type: 'state-machine',
        title: `State Machine — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: 'State machine diagram showing state transitions. Customize states to match your domain.',
    };
}
/**
 * Generate an architecture diagram for architectural specs.
 */
export function generateArchitectureDiagram(spec, knowledge) {
    const arch = knowledge?.architecture;
    const pattern = arch ? arch.primary : 'layered';
    const externalServices = knowledge?.externalServices ?? [];
    const externalLabel = externalServices.length > 0 ? externalServices.slice(0, 2).join(' / ') : 'External Services';
    const lines = [
        'graph TB',
        `  subgraph "${spec.title}"`,
        `    direction TB`,
        `    Client["Client Layer"]`,
        `    API["API Gateway"]`,
        `    Service["Service Layer"]`,
        `    Data["Data Layer"]`,
        `    Client --> API`,
        `    API --> Service`,
        `    Service --> Data`,
        `  end`,
        `  External["${externalLabel}"]`,
        `  Service --> External`,
        `  %% Architecture: ${pattern}`,
    ];
    return {
        type: 'architecture',
        title: `Architecture — ${spec.title}`,
        format: 'mermaid',
        content: lines.join('\n'),
        description: `Architecture diagram using ${pattern} pattern. Customize to match your system.`,
    };
}
/**
 * Format diagrams as Mermaid code blocks for inclusion in markdown.
 */
export function formatDiagramsAsMarkdown(diagrams) {
    if (diagrams.length === 0) {
        return '';
    }
    const sections = [];
    for (const diagram of diagrams) {
        sections.push(`### ${diagram.title}`);
        sections.push('');
        sections.push(`> ${diagram.description}`);
        sections.push('');
        sections.push('```mermaid');
        sections.push(diagram.content);
        sections.push('```');
        sections.push('');
    }
    return sections.join('\n');
}
// === Internal helpers ===
function isScopeAtLeast(scope, threshold) {
    const order = {
        trivial: 0,
        feature: 1,
        'cross-module': 2,
        architectural: 3,
    };
    return order[scope] >= order[threshold];
}
function buildLayers(target, knowledge) {
    // If knowledge has real architecture layers, prefer them over target-inferred ones
    if (knowledge && knowledge.architecture.layers.length > 0) {
        return knowledge.architecture.layers.map((l) => ({
            id: l.name.replace(/[^a-zA-Z0-9]/g, '_'),
            label: l.name,
        }));
    }
    const framework = knowledge?.framework ?? '';
    const layers = [];
    if (target === 'frontend' || target === 'fullstack') {
        layers.push({ id: 'Client', label: framework ? `Client (${framework})` : 'Client' });
    }
    if (target !== 'database' && target !== 'infrastructure') {
        layers.push({ id: 'Action', label: 'Action/Controller' });
        layers.push({ id: 'Service', label: 'Service' });
    }
    if (target === 'backend' || target === 'fullstack' || target === 'database') {
        layers.push({ id: 'Repo', label: 'Repository' });
        const dbRaw = knowledge?.database ?? 'DB';
        const db = dbRaw === 'unknown' ? 'DB' : dbRaw;
        layers.push({ id: 'DB', label: db });
    }
    if (target === 'infrastructure') {
        layers.push({ id: 'Infra', label: 'Infrastructure' });
        layers.push({ id: 'Cloud', label: 'Cloud Provider' });
    }
    // Fallback if empty
    if (layers.length === 0) {
        layers.push({ id: 'Input', label: 'Input' }, { id: 'Process', label: 'Process' }, { id: 'Output', label: 'Output' });
    }
    return layers;
}
function buildParticipants(target, knowledge) {
    const participants = [];
    if (target === 'frontend' || target === 'fullstack') {
        participants.push({ id: 'UI', label: 'UI' });
    }
    participants.push({ id: 'API', label: 'API' });
    participants.push({ id: 'SVC', label: 'Service' });
    if (target === 'backend' || target === 'fullstack' || target === 'database') {
        const db = knowledge?.database ?? 'DB';
        participants.push({ id: 'DB', label: db });
    }
    return participants;
}
//# sourceMappingURL=mermaid-generator.js.map