( ′∀`)σ≡σ☆))Д′)レ(゚∀゚;)ヘ=З=З=Зε≡(ノ´_ゝ`)ノ
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var tslib_1 = require("tslib");
var commander_1 = require("commander");
var loud_rejection_1 = (0, tslib_1.__importDefault)(require("loud-rejection"));
var extract_1 = (0, tslib_1.__importDefault)(require("./extract"));
var compile_1 = (0, tslib_1.__importDefault)(require("./compile"));
var compile_folder_1 = (0, tslib_1.__importDefault)(require("./compile_folder"));
var fast_glob_1 = require("fast-glob");
var console_utils_1 = require("./console_utils");
var KNOWN_COMMANDS = ['extract'];
function main(argv) {
return (0, tslib_1.__awaiter)(this, void 0, void 0, function () {
var version;
var _this = this;
return (0, tslib_1.__generator)(this, function (_a) {
(0, loud_rejection_1.default)();
version = require('../package.json').version;
commander_1.program
.version(version, '-v, --version')
.usage('<command> [flags]')
.action(function (command) {
if (!KNOWN_COMMANDS.includes(command)) {
commander_1.program.help();
}
});
commander_1.program
.command('help', { isDefault: true })
.description('Show this help message.')
.action(function () { return commander_1.program.help(); });
// Long text wrapping to available terminal columns: https://github.com/tj/commander.js/pull/956
// NOTE: please keep the help text in sync with babel-plugin-formatjs documentation.
commander_1.program
.command('extract [files...]')
.description("Extract string messages from React components that use react-intl.\nThe input language is expected to be TypeScript or ES2017 with JSX.")
.option('--format <path>', "Path to a formatter file that controls the shape of JSON file from `--out-file`.\nThe formatter file must export a function called `format` with the signature\n```\ntype FormatFn = <T = Record<string, MessageDescriptor>>(\n msgs: Record<string, MessageDescriptor>\n) => T\n``` \nThis is especially useful to convert from our extracted format to a TMS-specific format.\n")
.option('--out-file <path>', "The target file path where the plugin will output an aggregated \n`.json` file of all the translations from the `files` supplied.")
.option('--id-interpolation-pattern <pattern>', "If certain message descriptors don't have id, this `pattern` will be used to automatically\ngenerate IDs for them. Default to `[sha512:contenthash:base64:6]` where `contenthash` is the hash of\n`defaultMessage` and `description`.\nSee https://github.com/webpack/loader-utils#interpolatename for sample patterns", '[sha512:contenthash:base64:6]')
.option('--extract-source-location', "Whether the metadata about the location of the message in the source file should be \nextracted. If `true`, then `file`, `start`, and `end` fields will exist for each \nextracted message descriptors.", false)
.option('--remove-default-message', 'Remove `defaultMessage` field in generated js after extraction', false)
.option('--additional-component-names <comma-separated-names>', "Additional component names to extract messages from, e.g: `'FormattedFooBarMessage'`. \n**NOTE**: By default we check for the fact that `FormattedMessage` \nis imported from `moduleSourceName` to make sure variable alias \nworks. This option does not do that so it's less safe.", function (val) { return val.split(','); })
.option('--additional-function-names <comma-separated-names>', "Additional function names to extract messages from, e.g: `'$t'`.", function (val) { return val.split(','); })
.option('--ignore <files...>', 'List of glob paths to **not** extract translations from.')
.option('--throws', 'Whether to throw an exception when we fail to process any file in the batch.')
.option('--pragma <pragma>', "parse specific additional custom pragma. This allows you to tag certain file with metadata such as `project`. For example with this file:\n\n ```\n // @intl-meta project:my-custom-project\n import {FormattedMessage} from 'react-intl';\n\n <FormattedMessage defaultMessage=\"foo\" id=\"bar\" />;\n ```\n\n and with option `{pragma: \"intl-meta\"}`, we'll parse out `// @intl-meta project:my-custom-project` into `{project: 'my-custom-project'}` in the result file.")
.option('--preserve-whitespace', 'Whether to preserve whitespace and newlines.')
.option('--flatten', "Whether to hoist selectors & flatten sentences as much as possible. E.g:\n\"I have {count, plural, one{a dog} other{many dogs}}\"\nbecomes \"{count, plural, one{I have a dog} other{I have many dogs}}\".\nThe goal is to provide as many full sentences as possible since fragmented\nsentences are not translator-friendly.")
.action(function (filePatterns, cmdObj) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () {
var files;
return (0, tslib_1.__generator)(this, function (_a) {
switch (_a.label) {
case 0:
(0, console_utils_1.debug)('File pattern:', filePatterns);
(0, console_utils_1.debug)('Options:', cmdObj);
files = (0, fast_glob_1.sync)(filePatterns, {
ignore: cmdObj.ignore,
});
(0, console_utils_1.debug)('Files to extract:', files);
return [4 /*yield*/, (0, extract_1.default)(files, {
outFile: cmdObj.outFile,
idInterpolationPattern: cmdObj.idInterpolationPattern || '[sha1:contenthash:base64:6]',
extractSourceLocation: cmdObj.extractSourceLocation,
removeDefaultMessage: cmdObj.removeDefaultMessage,
additionalComponentNames: cmdObj.additionalComponentNames,
additionalFunctionNames: cmdObj.additionalFunctionNames,
throws: cmdObj.throws,
pragma: cmdObj.pragma,
format: cmdObj.format,
// It is possible that the glob pattern does NOT match anything.
// But so long as the glob pattern is provided, don't read from stdin.
readFromStdin: filePatterns.length === 0,
preserveWhitespace: cmdObj.preserveWhitespace,
flatten: cmdObj.flatten,
})];
case 1:
_a.sent();
process.exit(0);
return [2 /*return*/];
}
});
}); });
commander_1.program
.command('compile [translation_files...]')
.description("Compile extracted translation file into react-intl consumable JSON\nWe also verify that the messages are valid ICU and not malformed. \n<translation_files> can be a glob like \"foo/**/en.json\"")
.option('--format <path>', "Path to a formatter file that converts `<translation_file>` to `Record<string, string>`\nso we can compile. The file must export a function named `compile` with the signature:\n```\ntype CompileFn = <T = Record<string, MessageDescriptor>>(\n msgs: T\n) => Record<string, string>;\n```\nThis is especially useful to convert from a TMS-specific format back to react-intl format\n")
.option('--out-file <path>', "Compiled translation output file.\nIf this is not provided, result will be printed to stdout")
.option('--ast', "Whether to compile to AST. See https://formatjs.io/docs/guides/advanced-usage#pre-parsing-messages\nfor more information")
.option('--skip-errors', "Whether to continue compiling messages after encountering an error. Any keys with errors will not be included in the output file.")
.option('--pseudo-locale <pseudoLocale>', "Whether to generate pseudo-locale files. See https://formatjs.io/docs/tooling/cli#--pseudo-locale-pseudolocale for possible values. \n\"--ast\" is required for this to work.")
.action(function (filePatterns, opts) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () {
var files;
return (0, tslib_1.__generator)(this, function (_a) {
switch (_a.label) {
case 0:
(0, console_utils_1.debug)('File pattern:', filePatterns);
(0, console_utils_1.debug)('Options:', opts);
files = (0, fast_glob_1.sync)(filePatterns);
if (!files.length) {
throw new Error("No input file found with pattern ".concat(filePatterns));
}
(0, console_utils_1.debug)('Files to compile:', files);
return [4 /*yield*/, (0, compile_1.default)(files, opts)];
case 1:
_a.sent();
return [2 /*return*/];
}
});
}); });
commander_1.program
.command('compile-folder <folder> <outFolder>')
.description("Batch compile all extracted translation JSON files in <folder> to <outFolder> containing\nreact-intl consumable JSON. We also verify that the messages are \nvalid ICU and not malformed.")
.option('--format <path>', "Path to a formatter file that converts JSON files in `<folder>` to `Record<string, string>`\nso we can compile. The file must export a function named `compile` with the signature:\n```\ntype CompileFn = <T = Record<string, MessageDescriptor>>(\n msgs: T\n) => Record<string, string>;\n```\nThis is especially useful to convert from a TMS-specific format back to react-intl format\n")
.option('--ast', "Whether to compile to AST. See https://formatjs.io/docs/guides/advanced-usage#pre-parsing-messages\nfor more information")
.action(function (folder, outFolder, opts) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () {
var files;
return (0, tslib_1.__generator)(this, function (_a) {
switch (_a.label) {
case 0:
(0, console_utils_1.debug)('Folder:', folder);
(0, console_utils_1.debug)('Options:', opts);
files = (0, fast_glob_1.sync)("".concat(folder, "/*.json"));
if (!files.length) {
throw new Error("No JSON file found in ".concat(folder));
}
(0, console_utils_1.debug)('Files to compile:', files);
return [4 /*yield*/, (0, compile_folder_1.default)(files, outFolder, opts)];
case 1:
_a.sent();
return [2 /*return*/];
}
});
}); });
if (argv.length < 3) {
commander_1.program.help();
}
else {
commander_1.program.parse(argv);
}
return [2 /*return*/];
});
});
}
exports.default = main;