UNPKG

@ibm-adw/skill-toolkit

Version:

Developing your own skills with IBM Automation Digital Worker Skill Toolkit

155 lines (133 loc) 6.26 kB
/* Licensed Materials - Property of IBM 5737-I23 Copyright IBM Corp. 2019, 2020. All Rights Reserved. U.S. Government Users Restricted Rights: Use, duplication or disclosure restricted by GSA ADP Schedule Contract with IBM Corp. */ import React, { useContext, useEffect, useState } from 'react'; import intl from 'react-intl-universal'; import { useHistory, useLocation } from 'react-router-dom'; import acceptLanguage from 'accept-language'; import bcp47 from 'bcp47'; // Supported locales data const SUPPORTED_LOCALES = process.env.REACT_APP_SUPPORTED_LOCALES.split(',').map(item => item.trim()); const DEFAULT_LOCALE = process.env.REACT_APP_DEFAULT_LOCALE; const LocaleContext = React.createContext({ enforcedLocale: false, currentLocale: '', fallbackLocale: '', initialized: false, }); const useLocale = (nlsModules) => { const localeContext = useContext(LocaleContext); const [ nlsLoaded, setNlsLoaded ] = useState(false); useEffect(() => { if (localeContext.initialized) { const currentLocale = intl.options.currentLocale; const fallbackLocale = intl.options.fallbackLocale; Promise.all(nlsModules()).then(nls => { intl.load({ [currentLocale]: nls[0].default, [fallbackLocale]: nls[1].default }); setNlsLoaded(true); }).catch((e) => { // TODO We need to decide what we want to do when a specific language file is not found // Could not load nls modules }); } }, [ localeContext, nlsModules ]); return nlsLoaded; }; const LocaleProvider = ({ supportedLocalesArray = SUPPORTED_LOCALES, defaultLocale = DEFAULT_LOCALE, children }) => { const history = useHistory(); const searchLocation = new URLSearchParams(useLocation().search); const queryParamsLocale = searchLocation.get('locale'); // Get valid supported locale for queryParamsLocale // Define supported languages. The first language is default language. acceptLanguage.languages([ defaultLocale ].concat(supportedLocalesArray)); // Get matching language. If no match, default language will be returned. const matchingLocale = acceptLanguage.get(queryParamsLocale); // Setting fallback locale const tmpParsedLocale = bcp47.parse(matchingLocale); const fallbackLocale = (tmpParsedLocale.langtag.region ? tmpParsedLocale.langtag.language.language : defaultLocale); // if needed, update URL with valid locale if (queryParamsLocale && matchingLocale !== queryParamsLocale) { searchLocation.set('locale', matchingLocale); history.replace({ search: searchLocation.toString() }); } const [ state, setState ] = useState({ enforcedLocale: !!queryParamsLocale, currentLocale: matchingLocale, fallbackLocale: fallbackLocale, initialized: false }); useEffect(() => { async function loadLocales() { const browserLocale = intl.determineLocale(); let cuLocale = state.currentLocale; let fbLocale = state.fallbackLocale; if (browserLocale && !queryParamsLocale) { // Get matching language. If no match, default language will be returned. const matchingBrowserLocale = acceptLanguage.get(browserLocale); // Setting current locale cuLocale = matchingBrowserLocale; // Setting fallback locale const tmpParsedLocale = bcp47.parse(matchingBrowserLocale); fbLocale = (tmpParsedLocale.langtag.region ? tmpParsedLocale.langtag.language.language : defaultLocale); } // TODO We need to decide what we want to do when a specific language file is not found const cuLocaleData = await import(/* webpackChunkName: "nls" */ `./nls/${cuLocale}.json`).then(module => module.default).catch(() => { return {}; }); const fallbackLocaleData = await import(/* webpackChunkName: "nls" */ `./nls/${fbLocale}.json`).then(module => module.default).catch(() => { return {}; }); intl.init({ currentLocale: cuLocale, locales: { [cuLocale]: cuLocaleData, [fbLocale]: fallbackLocaleData }, commonLocaleDataUrls: { en: '/locales/locale-data/1.0.0/en.js', zh: '/locales/locale-data/1.0.0/zh.js', fr: '/locales/locale-data/1.0.0/fr.js', fa: '/locales/locale-data/1.0.0/fa.js', ja: '/locales/locale-data/1.0.0/ja.js', de: '/locales/locale-data/1.0.0/de.js', es: '/locales/locale-data/1.0.0/es.js', ko: '/locales/locale-data/1.0.0/ko.js', pt: '/locales/locale-data/1.0.0/pt.js', it: '/locales/locale-data/1.0.0/it.js', ru: '/locales/locale-data/1.0.0/ru.js', pl: '/locales/locale-data/1.0.0/pl.js', nl: '/locales/locale-data/1.0.0/nl.js', sv: '/locales/locale-data/1.0.0/sv.js', tr: '/locales/locale-data/1.0.0/tr.js' }, fallbackLocale: fbLocale }); // Update state setState({ enforcedLocale: state.enforcedLocale, currentLocale: cuLocale, fallbackLocale: fbLocale, initialized: true }); } if (!state.initialized) { loadLocales(); } }, [ queryParamsLocale, matchingLocale, state, defaultLocale ]); // Only re-run the effect if localesLoaded changes return ( <LocaleContext.Provider value={{ enforcedLocale: state.enforcedLocale, currentLocale: state.currentLocale, fallbackLocale: state.fallbackLocale, initialized: state.initialized, }}> {children} </LocaleContext.Provider> ); }; export { LocaleContext, LocaleProvider, useLocale };