@computerrock/formation-i18n
Advanced tools
Comparing version 0.2.1 to 0.2.2
{ | ||
"name": "@computerrock/formation-i18n", | ||
"version": "0.2.1", | ||
"version": "0.2.2", | ||
"description": "Formation framework - i18n layer", | ||
@@ -25,2 +25,6 @@ "license": "MIT", | ||
}, | ||
"dependencies": { | ||
"content-type": "^1.0.4", | ||
"qs": "^6.10.1" | ||
}, | ||
"peerDependencies": { | ||
@@ -31,3 +35,3 @@ "prop-types": "^15.7.2", | ||
}, | ||
"gitHead": "aa3cdd397d946a3fb54fa524579c048a6d8d62e5" | ||
"gitHead": "18dfc9a18633a699ddca97bfdf19b9724a51a9c5" | ||
} |
@@ -11,3 +11,3 @@ import React, {useState, useEffect} from 'react'; | ||
useEffect(() => { | ||
service.onServiceUpdate((activeLocale, availableLocales) => { | ||
return service.onServiceUpdate((activeLocale, availableLocales) => { | ||
setActiveLocale(activeLocale); | ||
@@ -14,0 +14,0 @@ setAvailableLocales(availableLocales); |
@@ -0,1 +1,3 @@ | ||
import handleResponse from './handleResponse'; | ||
/** | ||
@@ -7,48 +9,91 @@ * I18nService | ||
const I18nService = function (serviceParameters = {}) { | ||
const {LOCALE = 'en-US', LOCALE_TRANSLATIONS = {}} = serviceParameters; | ||
const localeTranslations = LOCALE_TRANSLATIONS; | ||
const { | ||
LOCALE = 'en-US', | ||
DEFAULT_LOCALE_TRANSLATIONS = {}, | ||
LOCALE_RESOURCES = [], | ||
} = serviceParameters; | ||
const defaultLocaleTranslations = DEFAULT_LOCALE_TRANSLATIONS; | ||
const localeResources = typeof LOCALE_RESOURCES !== 'undefined' && Array.isArray(LOCALE_RESOURCES) | ||
? LOCALE_RESOURCES : []; | ||
const onServiceUpdateCallbacks = []; | ||
let activeLocale = LOCALE; | ||
let activeLocaleTranslations = {}; | ||
let activeLocaleSet = {}; | ||
let availableLocales = []; | ||
// parses translation keys | ||
// TODO support async loading of localeTranslations from SERVICE_URL & merge with default keys | ||
const translationKeysPromise = Promise.resolve(localeTranslations).then(localeTranslations => { | ||
const translationKeys = Object.keys(localeTranslations).reduce((translationKeys, localeKey) => { | ||
const localeTranslationsItem = localeTranslations[localeKey]; | ||
if (typeof localeTranslationsItem.locale !== 'undefined') { | ||
translationKeys[localeTranslationsItem.locale] = localeTranslationsItem; | ||
} | ||
return translationKeys; | ||
}, { | ||
// initial locale translations | ||
'en-US': { | ||
'locale': 'en-US', | ||
'locale.label': 'English', | ||
}, | ||
}); | ||
// parse translation sets (keys & translations) | ||
const allLocaleSetsPromise = Promise.all([ | ||
// load each remote resource translation set | ||
...localeResources.map(localeResource => { | ||
if (!localeResource['locale'] || !localeResource['url']) return Promise.resolve(false); | ||
activeLocaleTranslations = translationKeys[activeLocale]; | ||
availableLocales = Object.keys(translationKeys).map(key => ({ | ||
locale: key, | ||
label: translationKeys[key]['label'], | ||
language: translationKeys[key]['language'], | ||
})); | ||
return fetch(localeResource['url'], { | ||
method: 'GET', | ||
headers: { | ||
'Content-Type': 'application/json', | ||
'Accept': 'application/json', | ||
}, | ||
}) | ||
.then(handleResponse) | ||
.catch(() => false); | ||
}), | ||
]) | ||
.then(resourceLocaleTranslations => { | ||
// filter failed resource loads | ||
resourceLocaleTranslations = resourceLocaleTranslations.filter(Boolean); | ||
onServiceUpdateCallbacks.forEach(callback => { | ||
if (typeof callback === 'function') { | ||
callback(activeLocale, availableLocales); | ||
} | ||
// map default locale sets | ||
return Object.keys(defaultLocaleTranslations).reduce((allLocaleSets, localeKey) => { | ||
const localeSet = defaultLocaleTranslations[localeKey]; | ||
if (typeof localeSet['locale'] !== 'undefined') { | ||
// check if resource locale set provided | ||
const resourceLocaleSet = resourceLocaleTranslations.find(resourceLocaleSet => { | ||
return resourceLocaleSet['locale'] === localeSet['locale']; | ||
}); | ||
if (resourceLocaleSet) { | ||
// map resource locale translationKeys to default locale set key | ||
// only keys that exist in default set are over-written | ||
Object.keys(resourceLocaleSet).forEach(translationKey => { | ||
if (typeof localeSet[translationKey] !== 'undefined' | ||
&& typeof resourceLocaleSet[translationKey] === 'string') { | ||
localeSet[translationKey] = resourceLocaleSet[translationKey]; | ||
} | ||
}); | ||
} | ||
allLocaleSets[localeSet['locale']] = localeSet; | ||
} | ||
return allLocaleSets; | ||
}, { | ||
// initial locale translations | ||
'en-US': { | ||
'locale': 'en-US', | ||
'locale.label': 'English', | ||
}, | ||
}); | ||
}) | ||
.then(allLocaleSets => { | ||
activeLocaleSet = allLocaleSets[activeLocale]; | ||
availableLocales = Object.keys(allLocaleSets).map(key => ({ | ||
locale: key, | ||
label: allLocaleSets[key]['label'], | ||
language: allLocaleSets[key]['language'], | ||
})); | ||
onServiceUpdateCallbacks.forEach(callback => { | ||
if (typeof callback === 'function') { | ||
callback(activeLocale, availableLocales); | ||
} | ||
}); | ||
return allLocaleSets; | ||
}); | ||
return translationKeys; | ||
}); | ||
const setActiveLocale = async locale => { | ||
const translationKeys = await translationKeysPromise; | ||
const allLocaleSets = await allLocaleSetsPromise; | ||
if (typeof translationKeys[locale] !== 'undefined') { | ||
if (typeof allLocaleSets[locale] !== 'undefined') { | ||
activeLocale = locale; | ||
activeLocaleTranslations = translationKeys[locale]; | ||
activeLocaleSet = allLocaleSets[locale]; | ||
@@ -64,5 +109,5 @@ onServiceUpdateCallbacks.forEach(callback => { | ||
const translate = (key = 'key', params = {}) => { | ||
if (typeof activeLocaleTranslations[key] === 'undefined') return key; | ||
if (typeof activeLocaleSet[key] === 'undefined') return key; | ||
let translation = activeLocaleTranslations[key]; | ||
let translation = activeLocaleSet[key]; | ||
Object.keys(params).forEach(key => { | ||
@@ -84,3 +129,3 @@ translation = translation.replace(new RegExp(`{${key}}`, 'g'), params[key]); | ||
getAvailableLocales: async () => { | ||
await translationKeysPromise; | ||
await allLocaleSetsPromise; | ||
return availableLocales; | ||
@@ -92,3 +137,7 @@ }, | ||
onServiceUpdate: callback => { | ||
onServiceUpdateCallbacks.push(callback); | ||
const callbacksLength = onServiceUpdateCallbacks.push(callback); | ||
return () => { | ||
onServiceUpdateCallbacks.splice(callbacksLength - 1, 1); | ||
}; | ||
}, | ||
@@ -95,0 +144,0 @@ }; |
Network access
Supply chain riskThis module accesses the network.
Found 1 instance in 1 package
New author
Supply chain riskA new npm collaborator published a version of the package for the first time. New collaborators are usually benign additions to a project, but do indicate a change to the security surface area of a package.
Found 1 instance in 1 package
12504
11
287
5
+ Addedcontent-type@^1.0.4
+ Addedqs@^6.10.1
+ Addedcall-bind-apply-helpers@1.0.2(transitive)
+ Addedcall-bound@1.0.3(transitive)
+ Addedcontent-type@1.0.5(transitive)
+ Addeddunder-proto@1.0.1(transitive)
+ Addedes-define-property@1.0.1(transitive)
+ Addedes-errors@1.3.0(transitive)
+ Addedes-object-atoms@1.1.1(transitive)
+ Addedfunction-bind@1.1.2(transitive)
+ Addedget-intrinsic@1.3.0(transitive)
+ Addedget-proto@1.0.1(transitive)
+ Addedgopd@1.2.0(transitive)
+ Addedhas-symbols@1.1.0(transitive)
+ Addedhasown@2.0.2(transitive)
+ Addedmath-intrinsics@1.1.0(transitive)
+ Addedobject-inspect@1.13.4(transitive)
+ Addedqs@6.14.0(transitive)
+ Addedside-channel@1.1.0(transitive)
+ Addedside-channel-list@1.0.0(transitive)
+ Addedside-channel-map@1.0.1(transitive)
+ Addedside-channel-weakmap@1.0.2(transitive)