import path from 'path';
import type { GeneratorContext, GeneratorCore } from '@modern-js/codesmith';
import { AppAPI } from '@modern-js/codesmith-api-app';
import {
  DependenceGenerator,
  i18n as commonI18n,
} from '@modern-js/generator-common';
import {
  fs,
  chalk,
  getGeneratorPath,
  getModernConfigFile,
} from '@modern-js/generator-utils';
import { i18n, localeKeys } from './locale';

const ReactRouter6Type = `/// <reference types='@modern-js/runtime/types/router' />`;

const handleTemplateFile = async (
  context: GeneratorContext,
  generator: GeneratorCore,
  appApi: AppAPI,
) => {
  const { sourceTypeFile, projectPath } = context.config;

  const appDir = context.materials.default.basePath;
  const isTs = fs.existsSync(
    path.join(appDir, projectPath || '', 'tsconfig.json'),
  );
  if (isTs) {
    const typePath = path.join(
      appDir,
      projectPath || '',
      'src',
      sourceTypeFile || 'modern-app-env.d.ts',
    );
    if (fs.existsSync(typePath)) {
      const npmrc = fs.readFileSync(typePath, 'utf-8');
      if (npmrc.includes(ReactRouter6Type)) {
        fs.writeFileSync(
          typePath,
          npmrc.replace(ReactRouter6Type, ''),
          'utf-8',
        );
      }
    }
  }

  await appApi.runSubGenerator(
    getGeneratorPath(DependenceGenerator, context.config.distTag, [__dirname]),
    undefined,
    {
      ...context.config,
      isSubGenerator: true,
    },
  );
};

export default async (context: GeneratorContext, generator: GeneratorCore) => {
  const appApi = new AppAPI(context, generator);

  const { locale } = context.config;
  commonI18n.changeLanguage({ locale });
  appApi.i18n.changeLanguage({ locale });
  i18n.changeLanguage(locale);

  if (!(await appApi.checkEnvironment())) {
    process.exit(1);
  }

  generator.logger.debug(`🚀 [Start Run Router-v5 Generator]`);
  generator.logger.debug(
    '💡 [Current Config]:',
    JSON.stringify(context.config),
  );

  await handleTemplateFile(context, generator, appApi);

  if (!context.config.isSubGenerator) {
    await appApi.runInstall(undefined, { ignoreScripts: true });
    if (!context.config.pluginName) {
      appApi.showSuccessInfo();
    } else {
      const appDir = context.materials.default.basePath;
      const configFile = await getModernConfigFile(appDir);
      const isTS = configFile.endsWith('ts');
      const { pluginName, pluginDependence, shouldUsePluginNameExport } =
        context.config;
      console.info(
        chalk.green(`\n[INFO]`),
        `${i18n.t(localeKeys.success)}`,
        chalk.yellow.bold(`${configFile}`),
        ':',
        '\n',
      );
      if (shouldUsePluginNameExport) {
        console.info(
          chalk.yellow.bold(
            `import { ${pluginName} } from '${pluginDependence}';`,
          ),
        );
      } else {
        console.info(
          chalk.yellow.bold(`import ${pluginName} from '${pluginDependence}';`),
        );
      }
      if (isTS) {
        console.info(`
export default defineConfig({
  ...,
  runtime: {
    ...,
    router: {
      ${chalk.yellow.bold(`mode: 'react-router-5'`)},
    },
  },
  plugins: [..., ${chalk.yellow.bold(`${pluginName}()`)}],
});
`);
      } else {
        console.info(`
module.exports = {
  ...,
  runtime: {
    ...,
    router: {
      ${chalk.yellow.bold(`mode: 'react-router-5'`)},
    },
  },
  plugins: [..., ${chalk.yellow.bold(`${pluginName}()`)}],
};
`);
      }
      console.info(
        `${i18n.t(localeKeys.successTooltip)} ${chalk.yellow.bold(
          `@modern-js/runtime/router-v5`,
        )} ${i18n.t(localeKeys.successTooltipSuffix)}`,
      );
    }
  }
  generator.logger.debug(`🌟 [End Run Repo Generator]`);
};
