glass-app-manager
Version:
Informatica's Glass Framework CLI for bootstrapping
138 lines (106 loc) • 3.38 kB
JavaScript
// @flow
import * as files from "../i18n/index";
import he from "he";
const locales = Object.keys(files).filter(locale => locale !== "default");
const __DEV__ = process.env.NODE_ENV === "development";
type Config = {
/**
* The given locale as a string.
*/
locale: string,
/**
* An ordered list of languages to fallback to
* when `locale` cannot be found in one of the translation
* files.
*/
fallbackLanguages: Array<string>,
/**
* An unordered list of available languages.
* This is set by default.
*/
availableLanguages?: Array<string>,
};
type Options = {
/**
* Specify the locale in the `t` function.
*/
locale?: string,
/**
* The default value to fallback to when the
* locale cannot be found.=
*/
defaultValue?: string,
};
const DEFAULT_CONFIG: Config = {
locale: "en",
fallbackLanguages: ["en"],
availableLanguages: Object.keys(files),
};
const getLanguagePartFromCode = (code: string) => {
if (!code || code.indexOf("-") < 0 || code.indexOf("_") < 0) {
return code;
}
return code.split(/-_/).shift();
};
const interpolate = (source: string, targets: {}): string => {
let interpolated = source;
const matches = source.match(/\{\{\w+}}/g);
if (matches) {
matches.map(match => {
const sanitized = match.replace("{{", "").replace("}}", "");
if (targets[sanitized]) {
interpolated = interpolated.replace(match, he.encode(targets[sanitized]));
}
});
}
return interpolated;
};
const getPossibleMatches = (locale, availableLanguages) => {
const possibleMatches = Array.from(availableLanguages).filter(
lang => getLanguagePartFromCode(lang).indexOf(locale) >= 0
);
if (possibleMatches.length) {
return possibleMatches.shift();
} else if (!possibleMatches.length && __DEV__) {
console.warn(`'${locale}' is not a supported language. Defaulting to English`);
}
return DEFAULT_CONFIG.locale;
};
function i18n(config?: Config) {
this.config = {
...DEFAULT_CONFIG,
...config,
};
if (
!this.config.availableLanguages.every(lang => {
const hasLocale = locales.indexOf(lang) >= 0;
if (!hasLocale && __DEV__) {
console.error(`${lang} is missing from list of translation files. Defaulting to English.`);
}
return hasLocale;
})
) {
this.config.locale = DEFAULT_CONFIG.locale;
}
}
i18n.init = function(config?: Config) {
return new i18n(config);
};
i18n.prototype.setLocale = function(locale: string) {
this.config.locale = locale;
};
i18n.prototype.t = function(key: string, options?: Options) {
const language = getPossibleMatches(
options && options.locale ? options.locale : this.config.locale,
this.config.availableLanguages
);
let localized = files[language][key];
if (!localized) {
localized = files[DEFAULT_CONFIG.locale][key] || key;
}
if (options) {
localized = interpolate(localized, options);
}
return localized;
};
export default i18n;