@gramio/i18n
Version:
i18n plugin for GramIO with type-safety
80 lines (75 loc) • 2.79 kB
JavaScript
;
var gramio = require('gramio');
var fs = require('node:fs');
var path = require('node:path');
var bundle = require('@fluent/bundle');
function getFluentClient(options) {
const directory = options?.directory ?? "locales";
const bundles = /* @__PURE__ */ new Map();
for (const entry of fs.readdirSync(directory, { withFileTypes: true })) {
if (!entry.isFile() || !entry.name.endsWith(".ftl")) continue;
const lang = entry.name.slice(0, -4);
const source = fs.readFileSync(path.resolve(directory, entry.name)).toString();
const bundle$1 = new bundle.FluentBundle(lang);
const resource = new bundle.FluentResource(source);
bundle$1.addResource(resource);
bundles.set(lang, bundle$1);
}
const defaultLocale = options?.defaultLocale ?? bundles.keys().next().value;
if (!defaultLocale)
throw new Error("Please specify one or more translations");
let currentLanguage = defaultLocale;
return {
languages: {
bundles,
fallback: defaultLocale,
all: Array.from(bundles.keys()),
current: currentLanguage,
change: (language) => {
if (!bundles.has(language))
throw new Error(`No ${language} language found`);
currentLanguage = language;
}
},
t: (id, args) => {
const bundle = bundles.get(currentLanguage);
if (!bundle) throw new Error(`No ${currentLanguage} language found`);
const message = bundle.getMessage(id);
if (!message?.value) throw new Error(`No message found for ${id}`);
return bundle.formatPattern(message.value, args);
}
};
}
function i18n(options) {
const client = options && "t" in options ? options : getFluentClient(options);
return new gramio.Plugin("@gramio/i18n").derive(() => {
let language = client.languages.current;
return {
/** Object with localization utils and settings */
i18n: {
/** All languages */
locales: client.languages.all,
/** Current user locale */
locale: language,
/** Set locale to current user */
setLocale: (lang, strict = false) => {
if (!client.languages.all.includes(lang)) {
if (strict) throw new Error(`No ${language} language found`);
language = client.languages.fallback;
return;
}
language = lang;
}
},
t: (id, args) => {
const bundle = client.languages.bundles.get(language);
if (!bundle) throw new Error(`No ${language} language found`);
const message = bundle.getMessage(id);
if (!message?.value) throw new Error(`No message found for ${id}`);
return bundle.formatPattern(message.value, args);
}
};
});
}
exports.getFluentClient = getFluentClient;
exports.i18n = i18n;