/**
 * generate-playwright-tests.js
 *
 * Generates Playwright + MCP spec files from the editor's test data.
 */

const fs = require('fs');
const path = require('path');
const { loadActionCatalog, getAction } = require('./action-catalog/index.js');

const DATA_FILE = path.join(__dirname, '..', 'data', 'testcases.json');
const OUTPUT_BASE = path.join(__dirname, '..', '..', 'tests', 'generated');

function parseArgs() {
  const args = process.argv.slice(2);
  const options = {};

  for (let i = 0; i < args.length; i++) {
    if (args[i] === '--group' && args[i + 1]) options.group = args[++i];
    if (args[i] === '--dry-run') options.dryRun = true;
  }
  return options;
}

function loadTests() {
  return JSON.parse(fs.readFileSync(DATA_FILE, 'utf-8'));
}

function getTestsToGenerate(tests, options) {
  let filtered = tests.filter(t => t.fullyAutomated === true || t.status === 'automated');

  if (options.group) {
    filtered = filtered.filter(t => t.group === options.group);
  }

  return filtered;
}

function generateSpecFile(group, tests, catalog) {
  let code = `import { test, expect } from '@playwright/test';\n\n`;
  code += `// === AUTOGENERATED BY AUTOTEST EDITOR ===\n`;
  code += `// Group: ${group}\n`;
  code += `// Generated: ${new Date().toISOString()}\n\n`;

  code += `test.describe('${group}', () => {\n`;
  code += `  test.use({ ignoreHTTPSErrors: true });\n\n`;

  for (const test of tests) {
    code += generateSingleTest(test, catalog);
  }

  code += `});\n`;
  return code;
}

function generateSingleTest(test, catalog) {
  let body = '';

  const steps = test.codeSteps && test.codeSteps.length > 0
    ? test.codeSteps
    : (test.steps || []).map(s => ({ stepName: s, actionKey: 'search_for_document' }));

  for (const step of steps) {
    const action = getAction(step.actionKey);
    if (action) {
      let rendered = action.template;
      if (step.params) {
        Object.keys(step.params).forEach(key => {
          rendered = rendered.replace(new RegExp(`{{${key}}}`, 'g'), step.params[key]);
        });
      }
      body += `    await test.step('${step.stepName}', async () => {\n`;
      body += `      ${rendered}\n`;
      body += `    });\n\n`;
    } else {
      body += `    await test.step('${step.stepName}', async () => {\n`;
      body += `      // TODO: Implement action "${step.actionKey}"\n`;
      body += `    });\n\n`;
    }
  }

  let testCode = `  test('${test.id}', async ({ page }, testInfo) => {\n`;
  testCode += `    testInfo.annotations.push({ type: 'automationStatus', description: '${test.status}' });\n`;
  testCode += `    testInfo.annotations.push({ type: 'testType', description: '${test.action}' });\n`;
  testCode += `    testInfo.annotations.push({ type: 'description', description: '${test.description}' });\n\n`;
  testCode += body;
  testCode += `  });\n\n`;

  return testCode;
}

function ensureDir(dir) {
  if (!fs.existsSync(dir)) fs.mkdirSync(dir, { recursive: true });
}

function main() {
  const options = parseArgs();
  const tests = loadTests();
  const catalog = loadActionCatalog();

  const toGenerate = getTestsToGenerate(tests, options);

  if (toGenerate.length === 0) {
    console.log('No automated tests found for the given filters.');
    return;
  }

  const byGroup = {};
  toGenerate.forEach(t => {
    if (!byGroup[t.group]) byGroup[t.group] = [];
    byGroup[t.group].push(t);
  });

  for (const group of Object.keys(byGroup)) {
    const groupTests = byGroup[group];
    const moduleFolder = group.startsWith('core-') ? 'core' : 'pbx';
    const outputDir = path.join(OUTPUT_BASE, moduleFolder);
    ensureDir(outputDir);

    const fileName = group.replace('core-', '').replace('pbx-', '') + '.spec.ts';
    const outputPath = path.join(outputDir, fileName);

    const fileContent = generateSpecFile(group, groupTests, catalog);

    if (options.dryRun) {
      console.log(`\n=== DRY RUN: ${outputPath} ===\n`);
      console.log(fileContent);
    } else {
      fs.writeFileSync(outputPath, fileContent, 'utf-8');
      console.log(`✅ Generated: ${outputPath} (${groupTests.length} tests)`);
    }
  }
}

main();
