@lingui/cli
Version:
Lingui CLI to extract messages, compile catalogs, and manage translation workflows
81 lines (80 loc) • 3.53 kB
JavaScript
import { writeCompiled } from "../catalog.js";
import { styleText } from "node:util";
import { getMergedCatalogPath } from "../catalog/getCatalogs.js";
import { ProgramExit } from "../ProgramExit.js";
import { createCompiledCatalog } from "../compile.js";
import normalizePath from "normalize-path";
import nodepath from "path";
import { createCompilationErrorMessage } from "../messages.js";
import { getTranslationsForCatalog } from "../catalog/getTranslationsForCatalog.js";
export async function compileLocale(catalogs, locale, options, config, doMerge, logger) {
let mergedCatalogs = {};
for (const catalog of catalogs) {
const { messages, missing: missingMessages } = await getTranslationsForCatalog(catalog, locale, {
fallbackLocales: config.fallbackLocales,
sourceLocale: config.sourceLocale,
});
if (!options.allowEmpty &&
locale !== config.pseudoLocale &&
missingMessages.length > 0) {
logger.error(styleText("red", `Error: Failed to compile catalog for locale ${styleText("bold", locale)}!`));
if (options.verbose) {
logger.error(styleText("red", "Missing translations:"));
missingMessages.forEach((missing) => {
const source = missing.source || missing.source === missing.id
? `: (${missing.source})`
: "";
logger.error(`${missing.id}${source}`);
});
}
else {
logger.error(styleText("red", `Missing ${missingMessages.length} translation(s)`));
}
logger.error("");
throw new ProgramExit();
}
if (doMerge) {
mergedCatalogs = { ...mergedCatalogs, ...messages };
}
else {
if (!(await compileAndWrite(locale, config, options, catalog.path, messages, logger))) {
throw new ProgramExit();
}
}
}
if (doMerge) {
const result = await compileAndWrite(locale, config, options, await getMergedCatalogPath(config), mergedCatalogs, logger);
if (!result) {
throw new ProgramExit();
}
}
}
async function compileAndWrite(locale, config, options, writePath, messages, logger) {
const namespace = options.typescript
? "ts"
: options.namespace || config.compileNamespace;
const { source: compiledCatalog, errors } = createCompiledCatalog(locale, messages, {
strict: false,
namespace,
outputPrefix: options.outputPrefix,
pseudoLocale: config.pseudoLocale,
compilerBabelOptions: config.compilerBabelOptions,
});
if (errors.length) {
let message = createCompilationErrorMessage(locale, errors);
if (options.failOnCompileError) {
message += `These errors fail command execution because \`--strict\` option passed`;
logger.error(styleText("red", message));
return false;
}
else {
message += `You can fail command execution on these errors by passing \`--strict\` option`;
logger.error(styleText("red", message));
}
}
let compiledPath = await writeCompiled(writePath, locale, compiledCatalog, namespace);
compiledPath = normalizePath(nodepath.relative(config.rootDir, compiledPath));
options.verbose &&
logger.error(styleText("green", `${locale} ⇒ ${compiledPath}`));
return true;
}