diff --git a/packages/app-shell/src/app-shell.js b/packages/app-shell/src/app-shell.js index ecf3fd383336c0edb26a21278997b321e8b93898..0c7d2a8805f13dafeeabff56f604b1d3a618fcb9 100644 --- a/packages/app-shell/src/app-shell.js +++ b/packages/app-shell/src/app-shell.js @@ -1,4 +1,4 @@ -import {createInstance, fetchOverridestoSessionStorage} from './i18n.js'; +import {createInstance} from './i18n.js'; import {html, css} from 'lit'; import {ScopedElementsMixin} from '@open-wc/scoped-elements'; import {LanguageSelect} from '@dbp-toolkit/language-select'; @@ -168,11 +168,6 @@ export class AppShell extends ScopedElementsMixin(DBPLitElement) { this.metadata = metadata; this.routes = routes; - // fetch translations - for(let lng of this._i18n.languages) { - fetchOverridestoSessionStorage(this.langDir, lng); - } - // Switch to the first route if none is selected if (!this.activeView) this.switchComponent(routes[0]); else this.switchComponent(this.activeView); diff --git a/packages/app-shell/src/i18n.js b/packages/app-shell/src/i18n.js index 090a555c3e911f4a00f19b411f6817081187c368..0c6fedc883e4f02965df30acfb47fa37e11a268c 100644 --- a/packages/app-shell/src/i18n.js +++ b/packages/app-shell/src/i18n.js @@ -1,4 +1,4 @@ -import {createInstance as _createInstance, fetchOverridestoSessionStorage} from '@dbp-toolkit/common/i18next.js'; +import {createInstance as _createInstance} from '@dbp-toolkit/common/i18next.js'; import de from './i18n/de/translation.json'; import en from './i18n/en/translation.json'; @@ -6,5 +6,3 @@ import en from './i18n/en/translation.json'; export function createInstance() { return _createInstance({en: en, de: de}, 'de', 'en'); } - -export {fetchOverridestoSessionStorage} diff --git a/packages/common/i18next.js b/packages/common/i18next.js index 74e8659dc692893414b028a41d4324ca148cb5c6..d72b9abcc272045f9d50fff1928d33f6eb8358fa 100644 --- a/packages/common/i18next.js +++ b/packages/common/i18next.js @@ -125,35 +125,17 @@ export function setOverrides(i18n, element, overrides) { i18n.setDefaultNamespace(hasOverrides ? overrideNamespace : namespace); } -async function fetchOverridesByLanguage(overrides, lng) { - let result = await - fetch(overrides + lng +'/translation.json', { - headers: {'Content-Type': 'application/json'}, - }); - let json = await result.json(); - return json; -} - -export async function fetchOverridestoSessionStorage(overridesFile, lng) { - // use local cache for translation file - if (sessionStorage.getItem("translation-overrides-" + lng) === null) { - // get translation.json for each lang - let response = await fetchOverridesByLanguage(overridesFile, lng); - sessionStorage.setItem("translation-overrides-" + lng, JSON.stringify(response)); - - } -} - /** * Sets translation overrides for the given i18next instance. Any previously * applied overrides will be removed first. So calling this with an empty overrides * object is equal to removing all overrides. + * Expects overrides as promise and requests update after overrides have been set. * * @param {i18next.i18n} i18n - The i18next instance * @param {HTMLElement} element - The element at which the overrides are targeted - * @param {string} overridesFile - Path to the translation file containing the overrides + * @param {object} overrides - The override data as promise */ -export async function setOverridesByFile(i18n, element, overridesFile, keyName) { +export async function setOverridesByPromise(i18n, element, overrides) { // We add a special namespace which gets used with priority and falls back // to the original one. This way we an change the overrides at runtime // and can even remove them. @@ -164,24 +146,13 @@ export async function setOverridesByFile(i18n, element, overridesFile, keyName) let overrideNamespace = getOverrideNamespace(namespace); let hasOverrides = false; for (let lng of i18n.languages) { - - await fetchOverridestoSessionStorage(overridesFile, lng); - - let response = JSON.parse(sessionStorage.getItem("translation-overrides-" + lng)); - - // remove old language + overrides[lng] = await overrides[lng]; i18n.removeResourceBundle(lng, overrideNamespace); - // if no new translation is available, skip - if (response === undefined || response[tagName] === undefined) return; - // get new translation - let resource = {}; - resource[keyName] = response[tagName][keyName]; + if (overrides[lng] === undefined || overrides[lng][tagName] === undefined) continue; + let resources = overrides[lng][tagName]; hasOverrides = true; - - // set new translation - i18n.addResourceBundle(lng, overrideNamespace, resource); + i18n.addResourceBundle(lng, overrideNamespace, resources); } - i18n.setDefaultNamespace(hasOverrides ? overrideNamespace : namespace); - return i18n; + element.requestUpdate(); } diff --git a/packages/common/src/i18n.js b/packages/common/src/i18n.js index 63ed95a6151a8f98047f5b00c9390f68a8901716..1db56149c8772428260cc630cbcd4559b37d2eba 100644 --- a/packages/common/src/i18n.js +++ b/packages/common/src/i18n.js @@ -1,4 +1,4 @@ -import {createInstance as _createInstance, setOverridesByFile} from '../i18next.js'; +import {createInstance as _createInstance, setOverridesByPromise} from '../i18next.js'; import de from './i18n/de/translation.json'; import en from './i18n/en/translation.json'; @@ -11,4 +11,4 @@ export function createInstanceGivenResources(en, de) { return _createInstance({en: en, de: de}, 'de', 'en'); } -export {setOverridesByFile}; +export {setOverridesByPromise}; diff --git a/packages/common/src/translation.js b/packages/common/src/translation.js index d0fd965caf5a42ac4346aca767039e92067aa72b..f459f2fcfc78a6cbbf0563eff297318af284f52a 100644 --- a/packages/common/src/translation.js +++ b/packages/common/src/translation.js @@ -1,7 +1,33 @@ import {css, html} from 'lit'; import {unsafeHTML} from 'lit/directives/unsafe-html.js'; import DBPLitElement from '../dbp-lit-element'; -import {createInstanceGivenResources, setOverridesByFile} from './i18n.js'; +import {createInstanceGivenResources, setOverridesByPromise} from './i18n.js'; + +// global variable as cache for translations +const translationCache = {}; + +// fetches overrides for given language +async function fetchOverridesByLanguage(overrides, lng) { + let result = await + fetch(overrides + lng +'/translation.json', { + headers: {'Content-Type': 'application/json'}, + }); + let json = await result.json(); + return json; +} + +// handles translation cache promises +async function cacheOverrides(overridesFile, lng) { + // use global var as cache + if (translationCache[lng] === undefined) { + // get translation.json for each lang + let response = fetchOverridesByLanguage(overridesFile, lng); + translationCache[lng] = response; + return response; + } else { + return translationCache[lng]; + } +} export class Translation extends DBPLitElement { constructor() { @@ -40,17 +66,15 @@ export class Translation extends DBPLitElement { const en = {}; de[this.key] = ""; en[this.key] = ""; - + // create i18n instance with given translations this._i18n = createInstanceGivenResources(en, de); - let local = this; - if (this.langDir) { - - // after init of overrides re-render page - setOverridesByFile(this._i18n, this, this.langDir, this.key).then(function(response) { - local.requestUpdate(); - }); + if (this.langDir) { + for(let lng of this._i18n.languages) { + cacheOverrides(this.langDir, lng); + setOverridesByPromise(this._i18n, this, translationCache); + } } }