diff --git a/packages/tools/lib/i18n/toJSON.js b/packages/tools/lib/i18n/toJSON.js index 6fef316fe523..6802ed32c7b5 100644 --- a/packages/tools/lib/i18n/toJSON.js +++ b/packages/tools/lib/i18n/toJSON.js @@ -14,8 +14,31 @@ const assets = require('../../assets-meta.js'); const allLanguages = assets.languages.all; +/** + * The translation system has a configuration whether to return UTF-8 sequences + * or the actual characters. This function inlines UTF-8 sequences to actual characters. + * + * For example, it converts "Keine Produkte erf\u00FCgbar" to "Keine Produkte verfügbar" + * This makes the JSON files more readable and smaller. + */ +function inlineUTF(properties) { + for (const key in properties) { + if (Object.prototype.hasOwnProperty.call(properties, key)) { + try { + // escape double quotes to avoid JSON parse error + const escaped = properties[key].replaceAll("\"", "\\\""); + properties[key] = JSON.parse(`"${escaped}"`); // utilize JSON parser to decode UTF-8 sequences + } catch (e) { + // in case of error, just keep the original string + console.log(`Warning: failed to inline UTF-8 for key "${key}" with value "${properties[key]}"`); + } + } + } + return properties; +} + const convertToJSON = async (file, distPath) => { - const properties = PropertiesReader(file)._properties; + const properties = inlineUTF(PropertiesReader(file)._properties); const filename = path.basename(file, path.extname(file)); const language = filename.match(/^messagebundle_(.*?)$/)[1]; if (!allLanguages.includes(language)) {