mirror of
https://github.com/arthur-pbty/flint.git
synced 2026-08-01 20:29:03 +02:00
ajoute du support de toute ces langues :
fr → Français en → Anglais es → Espagnol de → Allemand ja → Japonais pt → Portugais ru → Russe it → Italien nl → Néerlandais pl → Polonais zh → Chinois hi → Hindi ar → Arabe bn → Bengali id → Indonésien tr → Turc
This commit is contained in:
@@ -0,0 +1,139 @@
|
||||
import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs";
|
||||
import path from "node:path";
|
||||
import { fileURLToPath } from "node:url";
|
||||
|
||||
const SUPPORTED_LOCALES = [
|
||||
"en",
|
||||
"es",
|
||||
"de",
|
||||
"ja",
|
||||
"fr",
|
||||
"pt",
|
||||
"ru",
|
||||
"it",
|
||||
"nl",
|
||||
"pl",
|
||||
"zh",
|
||||
"hi",
|
||||
"ar",
|
||||
"bn",
|
||||
"id",
|
||||
"tr",
|
||||
];
|
||||
|
||||
const TARGETS = [
|
||||
{
|
||||
name: "bot",
|
||||
directory: "apps/bot/locales",
|
||||
},
|
||||
{
|
||||
name: "web",
|
||||
directory: "apps/web/locales",
|
||||
},
|
||||
];
|
||||
|
||||
const SCRIPT_DIR = path.dirname(fileURLToPath(import.meta.url));
|
||||
const REPO_ROOT = path.resolve(SCRIPT_DIR, "..", "..");
|
||||
const CHECK_ONLY = process.argv.includes("--check");
|
||||
|
||||
const isObject = (value) => {
|
||||
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
||||
};
|
||||
|
||||
const readJsonFile = (filePath) => {
|
||||
const raw = readFileSync(filePath, "utf-8");
|
||||
return JSON.parse(raw);
|
||||
};
|
||||
|
||||
const writeJsonFile = (filePath, content) => {
|
||||
writeFileSync(filePath, `${JSON.stringify(content, null, 2)}\n`, "utf-8");
|
||||
};
|
||||
|
||||
const shapeFromBase = (base, override) => {
|
||||
if (Array.isArray(base)) {
|
||||
return Array.isArray(override) ? override : base;
|
||||
}
|
||||
|
||||
if (isObject(base)) {
|
||||
const result = {};
|
||||
const overrideObject = isObject(override) ? override : {};
|
||||
|
||||
for (const [key, value] of Object.entries(base)) {
|
||||
result[key] = shapeFromBase(value, overrideObject[key]);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
return typeof override === typeof base ? override : base;
|
||||
};
|
||||
|
||||
const collectLeafPaths = (input, prefix = "", output = []) => {
|
||||
if (isObject(input)) {
|
||||
for (const [key, value] of Object.entries(input)) {
|
||||
const nextPrefix = prefix.length > 0 ? `${prefix}.${key}` : key;
|
||||
collectLeafPaths(value, nextPrefix, output);
|
||||
}
|
||||
return output;
|
||||
}
|
||||
|
||||
output.push(prefix);
|
||||
return output;
|
||||
};
|
||||
|
||||
let hasError = false;
|
||||
|
||||
for (const target of TARGETS) {
|
||||
const targetDirectory = path.resolve(REPO_ROOT, target.directory);
|
||||
const defaultLocalePath = path.join(targetDirectory, "en.json");
|
||||
|
||||
if (!existsSync(defaultLocalePath)) {
|
||||
console.error(`[i18n:${target.name}] missing default locale file: ${defaultLocalePath}`);
|
||||
hasError = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
mkdirSync(targetDirectory, { recursive: true });
|
||||
|
||||
const baseDictionary = readJsonFile(defaultLocalePath);
|
||||
const baseLeafPaths = new Set(collectLeafPaths(baseDictionary));
|
||||
|
||||
for (const locale of SUPPORTED_LOCALES) {
|
||||
const localePath = path.join(targetDirectory, `${locale}.json`);
|
||||
const localeExists = existsSync(localePath);
|
||||
const currentDictionary = localeExists ? readJsonFile(localePath) : {};
|
||||
const normalizedDictionary = shapeFromBase(baseDictionary, currentDictionary);
|
||||
|
||||
const normalizedText = JSON.stringify(normalizedDictionary, null, 2);
|
||||
const currentText = JSON.stringify(currentDictionary, null, 2);
|
||||
|
||||
if (!CHECK_ONLY && (!localeExists || normalizedText !== currentText)) {
|
||||
writeJsonFile(localePath, normalizedDictionary);
|
||||
console.log(`[i18n:${target.name}] synced ${locale}.json`);
|
||||
}
|
||||
|
||||
if (CHECK_ONLY) {
|
||||
const localeLeafPaths = new Set(collectLeafPaths(currentDictionary));
|
||||
|
||||
const missingPaths = [...baseLeafPaths].filter((key) => !localeLeafPaths.has(key));
|
||||
const extraPaths = [...localeLeafPaths].filter((key) => !baseLeafPaths.has(key));
|
||||
|
||||
if (missingPaths.length > 0 || extraPaths.length > 0) {
|
||||
hasError = true;
|
||||
console.error(`[i18n:${target.name}] ${locale}.json is out of sync`);
|
||||
|
||||
if (missingPaths.length > 0) {
|
||||
console.error(` missing keys: ${missingPaths.join(", ")}`);
|
||||
}
|
||||
|
||||
if (extraPaths.length > 0) {
|
||||
console.error(` extra keys: ${extraPaths.join(", ")}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CHECK_ONLY && hasError) {
|
||||
process.exitCode = 1;
|
||||
}
|
||||
Reference in New Issue
Block a user