import { getViteConfig } from 'astro/config';
import react from '@astrojs/react';
import { fileURLToPath } from 'node:url';
import { defineConfig, mergeConfig } from 'vitest/config';

const DB_SHIM = fileURLToPath(new URL('./src/test/w5-db-shim.mts', import.meta.url));
const SETTINGS_SHIM = fileURLToPath(new URL('./src/test/w5-settings-shim.mts', import.meta.url));
const CF_SHIM = fileURLToPath(new URL('./src/test/cf-workers-shim.mts', import.meta.url));

function needsDbSettingsShim(importer: string | undefined): boolean {
  if (!importer) return false;
  return (
    importer.includes('layouts/Base.astro') ||
    importer.includes('lib/appearance-server') ||
    importer.includes('pages/post/[slug].astro')
  );
}

const BODY_COMPONENT_RENDER_TESTS = [
  'src/themes/**/*IndexBody.test.ts',
  'src/themes/**/*SearchBody.test.ts',
  'src/themes/**/*NotFoundBody.test.ts',
  'src/themes/**/*PostBody.test.ts',
] as const;

const RENDER_TESTS = [
  'src/themes/render.container.test.tsx',
  'src/themes/render.test.ts',
  'src/themes/magazine.render.test.ts',
  'src/themes/registry.test.ts',
  'src/pages/install/_preview.test.ts',
  ...BODY_COMPONENT_RENDER_TESTS,
] as const;

/** AstroContainer harness — `render` vitest project (wired via vitest.config.ts `test.projects`). */
const astroViteConfig = getViteConfig({
  plugins: [
    {
      name: 'w5-render-verify-mocks',
      enforce: 'pre',
      resolveId(source, importer) {
        if (source === 'cloudflare:workers') return CF_SHIM;
        if (needsDbSettingsShim(importer)) {
          if (source === '../lib/db' || source === '../lib/db.js') return DB_SHIM;
          if (source === '../../lib/db' || source === '../../lib/db.js') return DB_SHIM;
          if (source === '../lib/settings' || source === '../lib/settings.js') return SETTINGS_SHIM;
          if (source === '../../lib/settings' || source === '../../lib/settings.js') return SETTINGS_SHIM;
        }
        return null;
      },
    },
  ],
}, { configFile: false, integrations: [react()] });

export default defineConfig(async (configEnv) =>
  mergeConfig(
    await astroViteConfig(configEnv),
    defineConfig({
      test: {
        name: 'render',
        setupFiles: ['./src/test/cf-workers-mock.ts', './src/test/w5-render-setup.ts', './vitest.setup.ts'],
        include: [...RENDER_TESTS],
        hookTimeout: 120_000,
        testTimeout: 60_000,
        maxWorkers: 1,
      },
    }),
  ),
);
