const fs = require('fs');
const path = require('path');
const GraphStore = require('../graph.js');
const { buildSubsystems } = require('../subsystem.js');
const { buildFlowIndex, traceFlow } = require('../flow.js');
const { generateDependencyDiagram, generateFlowDiagram, generateContractDiagram } = require('../diagrams.js');

const FIXTURE_DIR = path.join(__dirname, 'fixtures/system-docs');
const SNAPSHOT = path.join(FIXTURE_DIR, 'snapshot.json');

let passed = 0;
let failed = 0;

function assert(condition, name) {
  if (condition) { passed++; console.log(`  ✓ ${name}`); }
  else { failed++; console.log(`  ✗ ${name}`); }
}

const graph = GraphStore.loadSnapshot(SNAPSHOT);
const subs = buildSubsystems(graph, { minTraffic: 3, crossCuttingThreshold: 0.6 });
const index = buildFlowIndex(graph, subs);

console.log('=== 7E: Diagram Generator Tests ===\n');

// Test 1: Dependency diagram valid Mermaid
console.log('Test 1: Dependency diagram');
const depDiag = generateDependencyDiagram(subs);
assert(depDiag.startsWith('graph TD'), 'Starts with graph TD');
assert(depDiag.includes('gateway'), 'Contains gateway node');
assert(depDiag.includes('-->'), 'Contains edges');
assert(depDiag.includes('shared'), 'Contains shared class for cross-cutting');
assert(!depDiag.includes('undefined'), 'No undefined values');

// Test 2: Flow sequence diagram
console.log('\nTest 2: Flow sequence diagram');
const flow = traceFlow('channels/telegram.ts:onTelegramMessage', index);
const flowDiag = generateFlowDiagram(flow);
assert(flowDiag.startsWith('sequenceDiagram'), 'Starts with sequenceDiagram');
assert(flowDiag.includes('participant channels'), 'Has channels participant');
assert(flowDiag.includes('->>'), 'Has message arrows');
assert(!flowDiag.includes('undefined'), 'No undefined values');

// Test 3: Contract class diagram
console.log('\nTest 3: Contract class diagram');
const contracts = JSON.parse(fs.readFileSync(path.join(FIXTURE_DIR, 'expected-contracts.json'), 'utf8'));
const contractDiag = generateContractDiagram(contracts.contracts);
assert(contractDiag.startsWith('classDiagram'), 'Starts with classDiagram');
assert(contractDiag.includes('GatewayConfig'), 'Contains GatewayConfig');
assert(contractDiag.includes('BaseConfig <|-- GatewayConfig'), 'Contains extends relationship');
assert(contractDiag.includes('<<enumeration>>'), 'Contains enum');
assert(contractDiag.includes('LogLevel'), 'Contains LogLevel enum');
assert(!contractDiag.includes('undefined'), 'No undefined values');

// Test 4: Empty inputs
console.log('\nTest 4: Edge cases');
const emptyDeps = generateDependencyDiagram({ subsystems: [], crossCutting: [], dependencyMatrix: {} });
assert(emptyDeps === 'graph TD\n  classDef shared fill:#f9f,stroke:#333,stroke-dasharray: 5 5', 'Empty dep diagram is valid');

const emptyFlow = generateFlowDiagram({ flow: [], subsystemSequence: [], cyclesDetected: [] });
assert(emptyFlow === 'sequenceDiagram', 'Empty flow diagram is valid');

const emptyContracts = generateContractDiagram([]);
assert(emptyContracts === 'classDiagram', 'Empty contract diagram is valid');

console.log(`\n=== Results: ${passed} passed, ${failed} failed ===`);
process.exit(failed > 0 ? 1 : 0);
