File

libs/nx/src/generators/journey-src/lib/update-project-internationalization/extract-internationalization-configs.ts

Indexable

[locale: string]: literal type
import { joinPathFragments, logger } from '@nx/devkit';
import { basename } from 'path';

// eslint-disable-next-line @typescript-eslint/consistent-indexed-object-style
interface GenerateAndServeConfiguration {
  [locale: string]: {
    serveTarget: string;
  };
}

// eslint-disable-next-line @typescript-eslint/consistent-indexed-object-style
interface BuildTargetConfiguration {
  [locale: string]: {
    localize: string[];
  };
}

interface InternationalizationConfiguration {
  sourceLocale: SourceLocaleConfiguration;
  locales: LocaleConfiguration;
}

interface SourceLocaleConfiguration {
  code: string;
  baseHref: string;
}

// eslint-disable-next-line @typescript-eslint/consistent-indexed-object-style
interface LocaleConfiguration {
  [locale: string]: {
    translation: string;
    baseHref: string;
  };
}

export function extractInternationalizationGenerateAndServeConfigurations(
  locales: string[],
  projectName: string
): GenerateAndServeConfiguration {
  return locales.reduce((acc, locale: string) => {
    return {
      ...acc,
      [locale]: {
        serveTarget: `${projectName}:serve-generated-app:${locale}`
      }
    };
  }, {});
}

export function extractInternationalizationBuildConfigurations(
  locales: string[],
  localesDestinationFolder: string
): BuildTargetConfiguration {
  return locales.reduce((acc, locale: string) => {
    return {
      ...acc,
      [locale]: {
        localize: [locale],
        fileReplacements: [
          {
            replace: joinPathFragments(localesDestinationFolder, 'locale.ts'),
            with: joinPathFragments(localesDestinationFolder, `locale.${locale}.ts`)
          }
        ]
      }
    };
  }, {});
}

export function extractInternationalizationServeConfigurations(
  locales: string[],
  projectName: string
): BuildTargetConfiguration {
  return locales.reduce((acc, locale: string) => {
    return {
      ...acc,
      [locale]: {
        buildTarget: `${projectName}:build-generated-app:${locale}`
      }
    };
  }, {});
}

export function extractInternationalizationRootConfiguration(
  sourceLocale: SourceLocaleConfiguration | undefined,
  localeFilePaths: string[],
  stripLocaleBaseHref = false
): InternationalizationConfiguration {
  const localeConfig: LocaleConfiguration = localeFilePaths.reduce((acc, localeFilePath) => {
    const locale = extractLocaleFromFilePath(localeFilePath);
    if (!locale) {
      return acc;
    }

    return {
      ...acc,
      [locale]: {
        translation: localeFilePath,
        baseHref: stripLocaleBaseHref ? '' : `/${locale}/`
      }
    };
  }, {});

  let updatedSourceLocale: SourceLocaleConfiguration;
  const defaultSourceLocaleCode = 'en-US';
  const defaultSourceLocaleConflictsWithTranslations = localeFilePaths.some((localesValue) =>
    localesValue.includes(defaultSourceLocaleCode)
  );
  const configuredSourceLocaleConflictsWithTranslations = sourceLocale?.code
    ? localeFilePaths.some((localesValue) => localesValue.includes(sourceLocale.code))
    : false;

  if (sourceLocale?.code && !configuredSourceLocaleConflictsWithTranslations) {
    updatedSourceLocale = {
      code: sourceLocale.code,
      baseHref: stripLocaleBaseHref ? '' : sourceLocale.baseHref
    };
  } else if (
    configuredSourceLocaleConflictsWithTranslations ||
    defaultSourceLocaleConflictsWithTranslations
  ) {
    if (configuredSourceLocaleConflictsWithTranslations) {
      logger.warn(
        `⚠️ The existent "sourceLocale.code" ${
          // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
          sourceLocale!.code
        } conflicts with one of the translation files and was therefore removed by TALY. Please set the "sourceLocale.code" manually.`
      );
    } else {
      logger.warn(
        `⚠️ The default "sourceLocale.code" ${defaultSourceLocaleCode} could not be set by TALY, since it conflicts with one of the translation files. Please set the "sourceLocale.code" manually.`
      );
    }

    // set sourceLocale to empty string if sourceLocale conflicts with translation files
    updatedSourceLocale = {
      code: '',
      baseHref: ''
    };
  } else {
    // set sourceLocales to default en-US if there is no preset value
    updatedSourceLocale = {
      code: defaultSourceLocaleCode,
      baseHref: stripLocaleBaseHref ? '' : `/${defaultSourceLocaleCode}/`
    };
  }

  return {
    sourceLocale: updatedSourceLocale,
    locales: localeConfig
  };
}

export function extractLocalesFromFileNames(localeFilePaths: string[]): string[] {
  return localeFilePaths
    .map(extractLocaleFromFilePath)
    .filter((locale): locale is string => Boolean(locale));
}

function extractLocaleFromFilePath(filePath: string): string | undefined {
  const fileName = basename(filePath);

  //ignore dotfiles
  if (fileName.startsWith('.')) {
    return undefined;
  }

  const fileNameParts = fileName.match(/^[a-z-]+\.([a-z-]+)\.[a-z-]+$/i);
  if (fileNameParts === null) {
    throw new Error(
      `The given file name ${fileName} is not an accepted file name for translations. Please use the format: "messages.[locale].[extension]".`
    );
  }

  return fileNameParts[1];
}

results matching ""

    No results matching ""