интернализация бэкэнда изменение языковой сессии против системы

#node.js #internationalization #i18next

#node.js #интернационализация #i18next

Вопрос:

Итак, мой бэкэнд написан на nodejs, и я использую i18next для интернализации. Я также использую его на интерфейсе. Язык интерфейса определяется доменом. например es.domain.com является испанским и ja.domain.com является японским и т.д.

На серверной части цель состоит в том, чтобы определить язык пользователей через источник домена и изменить язык ответа на их происхождение. По умолчанию будет английский.

Мой вопрос,

Когда я меняю язык, изменится ли язык API по умолчанию или язык сеанса запроса? то есть, если пользователь1 делает запрос на японском языке, который занимает 5 секунд, в то время как пользователь2 делает запрос на английском языке, который занимает 1 секунду сразу после пользователя 1. Пользователь1 случайно получит ответ на английском языке?

Извините, если вопрос неясен / труден для понимания. Пожалуйста, прокомментируйте ниже, и я постараюсь перефразировать это.

 const i18n = require('i18next');

const express     = require('express');
const app         = express();
const port        = 3050;
const bodyParser  = require('body-parser');

app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());
app.use(require('express-useragent').express());

// Internationalization
i18n.init({
  resources: langResources,
  lng: "en",
  fallbackLng: "en",
  interpolation: {
    escapeValue: false
  }
}); 

// Cors
app.use(function(req, res, next) {

  // HERE's where I'll be detecting and changing the language
  i18n.changeLanguage('ja');
  console.log("i18n.t('test')",i18n.t('test',{count:1}));

  
  res.header("Access-Control-Allow-Origin", "*");
  res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept, auth-id, auth-token, x-csrf-token, _csrf");
  res.header('Access-Control-Allow-Methods', 'PATCH, POST, GET, DELETE, OPTIONS');
  next();
}); ```
  

Ответ №1:

Я понял, что могу просто сделать быстрый тест этого вот так.

Я отправил два запроса. У первого было время ожидания 5000 мс и ja lang, в то время как у второго было время ожидания 150 мс и en lang.

 test: async function(req){

      let user = req.query.user;
      let lang = req.query.lang;
      let time = req.query.time;

      // console.log("test 0Ro-> i18n.t('test')",i18n.t('test',{count:1}));

      i18n.changeLanguage(lang);
      console.log("user 1Ro:",user,"lang 1Ro:",lang);
      console.log("test 1Ro-> i18n.t('test')",i18n.t('test',{count:1}));
      await sleep(time)
      console.log("user 2Ro:",user,"lang 2Ro:",lang);
      console.log("test 2Ro-> i18n.t('test')",i18n.t('test',{count:1}));


    },
  

К сожалению, ja язык пользователя вернулся на английском, что означает, что изменение языка не меняет язык сеанса, а вместо этого меняет язык api.

Это ответ на вопрос. Однако я все еще ищу решение.

РЕДАКТИРОВАТЬ: не удалось найти решение i18next, поэтому я просто сделал свое собственное. Вот оно, если вы хотите его использовать. Добавьте express-session свой проект.

app.js — инициализация

 const {t} = require('./translations/i18n').i18n;

process.env.TZ = "Etc/GMT"

const express     = require('express');
const session     = require('express-session');
const app         = express();
const port        = 3050;
const bodyParser  = require('body-parser');

app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());
app.use(require('express-useragent').express());
app.use(session({
  secret: 'keyboard cat',
  resave: false,
  saveUninitialized: true,
  cookie: { secure: true }
}))

// Cors
app.use(async function(req, res, next) {

  let allowOrigins = [
    '(.*my-domain.com)',
  ];

  if(Config.Env !== Environments.Production){
    res.header("Access-Control-Allow-Origin", "*");
  }else{
    res.header("Access-Control-Allow-Origin", Config.FrontEnd.Url);
    var origin = req.get('origin');
    console.log("origin",origin);
    for (let i = 0; i < allowOrigins.length; i  ) {
      const allowOrigin = allowOrigins[i];
      if(origin.match(allowOrigin)){
        res.header("Access-Control-Allow-Origin", origin);
      }
    }
  }

  // example vars
  let user = req.query.user;
  let lang = req.query.lang;
  let time = req.query.time;

  // set language on session
  req.session.language = lang;


  console.log("user 1Ro:",user,"lang 1Ro:",lang);
  t(req,'test',{count: time});
  await sleep(time);
  console.log("user 2Ro:",user,"lang 2Ro:",lang);
  t(req,'test',{count: time});


  res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept, auth-id, auth-token, x-csrf-token, _csrf");
  res.header('Access-Control-Allow-Methods', 'PATCH, POST, GET, DELETE, OPTIONS');
  next();
});

  

all.js — ваши переводы идут здесь.

 // import translation objects here. then add to tranlations object


const convertToSingularLocale = (messages, locale ) => {
  let singleLocale = Object.assign({}, messages)

  for (let property in singleLocale) {
    if (property === locale) {
      return singleLocale[property]
    } else if (typeof singleLocale[property] === 'object') {
      singleLocale[property] = convertToSingularLocale(singleLocale[property], locale)
    }
  }

  return singleLocale
}

const translations = {
  general: {
    languageAbbreviation: {
      de: "de",
      es: "es",
      en: "en",
      ja: "ja",
      fr: "fr",
      zh: "zh",
    },
  },
  test:{
    en: "TEST {{count}}",
    ja: "テスト {{count}}",
  }
}

const english = convertToSingularLocale(translations, 'en')
const japanese = convertToSingularLocale(translations, 'ja')

const langResources = {
  en: english,
  ja: japanese,
}

const availableLanguages = [
  { name: "English", nativeName:"English", code: "en" },
  { name: "Japanese", nativeName:"日本語", code: "ja" },
]

module.exports = {
  langResources: langResources,
  availableLanguages: availableLanguages,
} 
  

i18n.js — простой переводчик

 


const defaultLang = "en";
const {langResources} = require('./all');

const translate = (req,str,args) => {
  let validLang = false;
  let lang = req.session.language;
  for (var key in langResources) {
    if(langResources.hasOwnProperty(key)) {
      validLang = true;
      break
    }
  }
  if(!validLang){
    lang = defaultLang;
  }

  const sourceLang = langResources[lang];

  var keys = str.split(".");

  let source = sourceLang;
  for (let i = 0; i < keys.length; i  ) {
    const key = keys[i];
    source = source[key];
  }

  let text = source;
  for (var key in args) {
    if(args.hasOwnProperty(key)) {
      text = text.replace("{{" key "}}", args[key]);
    }
  }

  return text;
}

const i18n = {
  translate: translate,
  t: translate,
} 

module.exports = {
  i18n: i18n,
}