'use strict';
const fs = require('fs');
const util = require('util');
/**
* @typedef {SexPomeloI18n} SexPomeloI18n
* @ignore
*/
const ARRAY_INDEX_RE = /\{(\d+)\}/g;
function formatWithArray (text, values) {
return text.replace(ARRAY_INDEX_RE, function (orignal, matched) {
const index = parseInt(matched);
if (index < values.length) {
return values[index];
}
// not match index, return orignal text
return orignal;
});
}
/** i18n Component
* @class
* @implements {Component}
*/
class SexPomeloI18n{
constructor ( app, opts ){
this.name = '__i18n__';
this.opts = opts || {};
this.locale = this.opts.locale;
this.default = this.opts.default;
this.localeFiled = this.opts.localeFiledName??'locale';
if( !this.locale ){
this.locale = [ this.default ];
}
let localePath = app.getBase() + '/locale';
if( typeof( opts.path ) === 'string' ){
localePath = app.getBase() + '/' + opts.path;
}
this.sexLocale = {};
for( let it of this.locale ){
let langPath = `${localePath}/${it}.js`;
if( fs.existsSync(langPath) === true ){
this.sexLocale[it] = require(langPath);
}
}
this.defLocale = this.sexLocale[ this.default ];
}
/** tr by default lang
*
* @param {string} msg
* @param {...any} paras
* @return {string}
*
*/
tr( msg, ...paras ){
if( !this.defLocale ) {
return msg;
}else{
return this.gettext( this.defLocale,msg,...paras );
}
}
/** tr by lang
*
* @param {string} locale - the locale
* @param {string} msg
* @param {...any} paras
* @return {string}
*
*/
tr1( locale,msg, ...paras ){
let lang = locale;
if( typeof(locale) !== 'string'){
lang = locale.get(this.localeFiled);
if( !lang ) {
lang = this.default;
}
} else {
if( lang === '' ) {
lang = this.default;
}
}
if( !this.sexLocale[lang] ) {
return msg;
}else{
return this.gettext( this.sexLocale[lang],msg,...paras );
}
}
gettext ( resource, key,value ) {
let text = resource[key];
if (text === undefined) {
text = key;
}
if (!text) {
return '';
}
if (arguments.length === 2) {
return text;
}
if (arguments.length === 3) {
if (Array.isArray(value)) {
return formatWithArray(text, value);
}
return util.format(text, value);
}
const args = new Array(arguments.length - 1);
args[0] = text;
for (let i = 2; i < arguments.length; i++) {
args[i - 1] = arguments[i];
}
return util.format.apply(util, args);
}
}
module.exports = function (app, opts) {
return new SexPomeloI18n(app, opts);
};