willba-component-library 0.3.26 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +75 -113
- package/lib/components/FilterBar/FilterBar.d.ts +1 -1
- package/lib/components/FilterCalendar/FilterCalendar.d.ts +1 -1
- package/lib/core/i18n/I18nProvider.d.ts +6 -0
- package/lib/core/i18n/index.d.ts +1 -0
- package/lib/embed.d.ts +18 -0
- package/lib/embed.esm.js +74 -0
- package/lib/embed.esm.js.map +1 -0
- package/lib/embed.umd.js +74 -0
- package/lib/embed.umd.js.map +1 -0
- package/lib/i18n.d.ts +2 -2
- package/lib/index.d.ts +2 -2
- package/lib/index.esm.js +1112 -931
- package/lib/index.esm.js.map +1 -1
- package/lib/index.js +1111 -930
- package/lib/index.js.map +1 -1
- package/package.json +9 -1
- package/.nvmrc +0 -1
- package/.storybook/main.ts +0 -17
- package/.storybook/preview.ts +0 -15
- package/lib/components/FilterBar/components/buttons/index.d.ts +0 -4
- package/lib/components/FilterBar/components/buttons/select-button/SelectButton.d.ts +0 -13
- package/lib/components/FilterBar/components/buttons/tab-button/TabButton.d.ts +0 -10
- package/lib/components/FilterBar/components/cards/image-card/ImageCard.d.ts +0 -11
- package/lib/components/FilterBar/components/cards/index.d.ts +0 -1
- package/lib/components/FilterBar/components/categories/Categories.d.ts +0 -8
- package/lib/components/FilterBar/components/common/FilterSectionHeader.d.ts +0 -8
- package/lib/components/FilterBar/components/dates/Dates.d.ts +0 -17
- package/lib/components/FilterBar/components/dates/index.d.ts +0 -1
- package/lib/components/FilterBar/components/guests/GuestCount/GuestCount.d.ts +0 -4
- package/lib/components/FilterBar/components/guests/Guests.d.ts +0 -12
- package/lib/components/FilterBar/components/locations/Locations.d.ts +0 -14
- package/lib/components/FilterBar/hooks/useFilterBar.d.ts +0 -32
- package/lib/components/FilterBar/hooks/useFilterUi.d.ts +0 -8
- package/lib/components/FilterBar/utils/calculateDropdownPosition.d.ts +0 -12
- package/lib/components/FilterBar/utils/getLocalizedContent.d.ts +0 -8
- package/lib/core/components/buttons/close-button/CloseButton.d.ts +0 -7
- package/lib/core/components/buttons/submit-button/SubmitButton.d.ts +0 -14
- package/lib/index.umd.js +0 -12489
- package/lib/index.umd.js.map +0 -1
- package/prettier.config.js +0 -6
- package/rollup.config.mjs +0 -63
- package/src/assets/IconsSvg.tsx +0 -69
- package/src/components/Button/Button.stories.tsx +0 -34
- package/src/components/Button/Button.tsx +0 -56
- package/src/components/Button/button.css +0 -30
- package/src/components/Button/index.ts +0 -1
- package/src/components/FilterBar/FilterBar.css +0 -35
- package/src/components/FilterBar/FilterBar.stories.tsx +0 -116
- package/src/components/FilterBar/FilterBar.tsx +0 -64
- package/src/components/FilterBar/FilterBarTypes.ts +0 -71
- package/src/components/FilterBar/components/Divider/Divider.css +0 -14
- package/src/components/FilterBar/components/Divider/Divider.tsx +0 -7
- package/src/components/FilterBar/components/FilterControls/FilterControls.css +0 -22
- package/src/components/FilterBar/components/FilterControls/FilterControls.tsx +0 -139
- package/src/components/FilterBar/components/FilterPanels/Categories/Categories.css +0 -21
- package/src/components/FilterBar/components/FilterPanels/Categories/Categories.tsx +0 -49
- package/src/components/FilterBar/components/FilterPanels/Dates/Dates.css +0 -9
- package/src/components/FilterBar/components/FilterPanels/Dates/Dates.tsx +0 -60
- package/src/components/FilterBar/components/FilterPanels/FilterPanels.css +0 -22
- package/src/components/FilterBar/components/FilterPanels/FilterPanels.tsx +0 -111
- package/src/components/FilterBar/components/FilterPanels/Guests/GuestCount/GuestCount.css +0 -58
- package/src/components/FilterBar/components/FilterPanels/Guests/GuestCount/GuestCount.tsx +0 -85
- package/src/components/FilterBar/components/FilterPanels/Guests/Guests.css +0 -24
- package/src/components/FilterBar/components/FilterPanels/Guests/Guests.tsx +0 -59
- package/src/components/FilterBar/components/FilterPanels/Locations/Locations.css +0 -16
- package/src/components/FilterBar/components/FilterPanels/Locations/Locations.tsx +0 -94
- package/src/components/FilterBar/components/FilterPanels/SectionHeader/SectionHeader.css +0 -34
- package/src/components/FilterBar/components/FilterPanels/SectionHeader/SectionHeader.tsx +0 -17
- package/src/components/FilterBar/components/FilterTabs/FilterTabs.css +0 -10
- package/src/components/FilterBar/components/FilterTabs/FilterTabs.tsx +0 -50
- package/src/components/FilterBar/components/ImageCard/ImageCard.css +0 -30
- package/src/components/FilterBar/components/ImageCard/ImageCard.tsx +0 -45
- package/src/components/FilterBar/components/SelectButton/SelectButton.css +0 -76
- package/src/components/FilterBar/components/SelectButton/SelectButton.tsx +0 -54
- package/src/components/FilterBar/components/TabButton/TabButton.css +0 -36
- package/src/components/FilterBar/components/TabButton/TabButton.tsx +0 -23
- package/src/components/FilterBar/components/index.ts +0 -6
- package/src/components/FilterBar/hooks/index.ts +0 -5
- package/src/components/FilterBar/hooks/useFilterActions.tsx +0 -126
- package/src/components/FilterBar/hooks/useFilterRefs.tsx +0 -21
- package/src/components/FilterBar/hooks/useFilterState.tsx +0 -86
- package/src/components/FilterBar/hooks/usePanelPosition.tsx +0 -52
- package/src/components/FilterBar/hooks/useScrollInToView.tsx +0 -29
- package/src/components/FilterBar/index.ts +0 -3
- package/src/components/FilterBar/providers/FilterBarProvider.tsx +0 -172
- package/src/components/FilterBar/providers/index.ts +0 -1
- package/src/components/FilterBar/utils/ageCategoriesRules.ts +0 -27
- package/src/components/FilterBar/utils/index.tsx +0 -3
- package/src/components/FilterBar/utils/parseGuests.tsx +0 -65
- package/src/components/FilterBar/utils/parseLocations.ts +0 -28
- package/src/components/FilterCalendar/FilterCalendar.css +0 -109
- package/src/components/FilterCalendar/FilterCalendar.stories.tsx +0 -554
- package/src/components/FilterCalendar/FilterCalendar.tsx +0 -115
- package/src/components/FilterCalendar/FilterCalendarTypes.ts +0 -11
- package/src/components/FilterCalendar/components/Footer.tsx +0 -96
- package/src/components/FilterCalendar/hooks/useFilterCalendar.ts +0 -163
- package/src/components/FilterCalendar/index.ts +0 -3
- package/src/core/components/buttons/CloseButton/CloseButton.css +0 -33
- package/src/core/components/buttons/CloseButton/CloseButton.tsx +0 -16
- package/src/core/components/buttons/SubmitButton/SubmitButton.css +0 -54
- package/src/core/components/buttons/SubmitButton/SubmitButton.tsx +0 -42
- package/src/core/components/calendar/Calendar.css +0 -280
- package/src/core/components/calendar/Calendar.tsx +0 -253
- package/src/core/components/calendar/CalendarTypes.ts +0 -48
- package/src/core/components/calendar/hooks/index.ts +0 -3
- package/src/core/components/calendar/hooks/useCalendarLoadingSpinner.tsx +0 -19
- package/src/core/components/calendar/hooks/useCalendarTooltips.tsx +0 -125
- package/src/core/components/calendar/hooks/useUpdateDisabledDates.tsx +0 -105
- package/src/core/components/calendar/utils/calendarSelectionRules.tsx +0 -180
- package/src/core/components/calendar/utils/checkForContinuousSelection.tsx +0 -86
- package/src/core/components/calendar/utils/disabledDatesByPage.tsx +0 -31
- package/src/core/components/calendar/utils/handleCalendarModifiers.tsx +0 -118
- package/src/core/components/calendar/utils/handleRangeContextDisabledDates.tsx +0 -75
- package/src/core/components/calendar/utils/index.ts +0 -8
- package/src/core/components/calendar/utils/nightsCount.tsx +0 -19
- package/src/core/components/calendar/utils/parseDate.tsx +0 -17
- package/src/core/components/calendar/utils/parseDates.tsx +0 -12
- package/src/core/components/index.ts +0 -7
- package/src/core/hooks/index.ts +0 -4
- package/src/core/hooks/useAutoFocus.tsx +0 -27
- package/src/core/hooks/useAwaitRender.tsx +0 -12
- package/src/core/hooks/useCloseFilterSection.tsx +0 -29
- package/src/core/hooks/useUpdateTranslations.tsx +0 -14
- package/src/i18n.ts +0 -27
- package/src/index.ts +0 -8
- package/src/locales/en/common.json +0 -18
- package/src/locales/en/filterBar.json +0 -33
- package/src/locales/fi/common.json +0 -19
- package/src/locales/fi/filterBar.json +0 -33
- package/src/themes/Default.css +0 -69
- package/src/themes/useTheme.tsx +0 -27
- package/stories/Button.stories.ts +0 -50
- package/stories/Button.tsx +0 -53
- package/stories/Configure.mdx +0 -364
- package/stories/Header.stories.ts +0 -27
- package/stories/Header.tsx +0 -70
- package/stories/Page.stories.ts +0 -29
- package/stories/Page.tsx +0 -91
- package/stories/assets/accessibility.png +0 -0
- package/stories/assets/accessibility.svg +0 -5
- package/stories/assets/addon-library.png +0 -0
- package/stories/assets/assets.png +0 -0
- package/stories/assets/context.png +0 -0
- package/stories/assets/discord.svg +0 -15
- package/stories/assets/docs.png +0 -0
- package/stories/assets/figma-plugin.png +0 -0
- package/stories/assets/github.svg +0 -3
- package/stories/assets/share.png +0 -0
- package/stories/assets/styling.png +0 -0
- package/stories/assets/testing.png +0 -0
- package/stories/assets/theming.png +0 -0
- package/stories/assets/tutorials.svg +0 -12
- package/stories/assets/youtube.svg +0 -4
- package/stories/button.css +0 -30
- package/stories/header.css +0 -32
- package/stories/page.css +0 -69
- package/tsconfig.json +0 -29
- /package/lib/components/FilterBar/components/{divider → Divider}/Divider.d.ts +0 -0
package/lib/index.js
CHANGED
|
@@ -242,6 +242,331 @@ var useAwaitRender = function () {
|
|
|
242
242
|
return null;
|
|
243
243
|
};
|
|
244
244
|
|
|
245
|
+
function warn() {
|
|
246
|
+
if (console && console.warn) {
|
|
247
|
+
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
248
|
+
args[_key] = arguments[_key];
|
|
249
|
+
}
|
|
250
|
+
if (typeof args[0] === 'string') args[0] = `react-i18next:: ${args[0]}`;
|
|
251
|
+
console.warn(...args);
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
const alreadyWarned = {};
|
|
255
|
+
function warnOnce() {
|
|
256
|
+
for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
|
|
257
|
+
args[_key2] = arguments[_key2];
|
|
258
|
+
}
|
|
259
|
+
if (typeof args[0] === 'string' && alreadyWarned[args[0]]) return;
|
|
260
|
+
if (typeof args[0] === 'string') alreadyWarned[args[0]] = new Date();
|
|
261
|
+
warn(...args);
|
|
262
|
+
}
|
|
263
|
+
const loadedClb = (i18n, cb) => () => {
|
|
264
|
+
if (i18n.isInitialized) {
|
|
265
|
+
cb();
|
|
266
|
+
} else {
|
|
267
|
+
const initialized = () => {
|
|
268
|
+
setTimeout(() => {
|
|
269
|
+
i18n.off('initialized', initialized);
|
|
270
|
+
}, 0);
|
|
271
|
+
cb();
|
|
272
|
+
};
|
|
273
|
+
i18n.on('initialized', initialized);
|
|
274
|
+
}
|
|
275
|
+
};
|
|
276
|
+
function loadNamespaces(i18n, ns, cb) {
|
|
277
|
+
i18n.loadNamespaces(ns, loadedClb(i18n, cb));
|
|
278
|
+
}
|
|
279
|
+
function loadLanguages(i18n, lng, ns, cb) {
|
|
280
|
+
if (typeof ns === 'string') ns = [ns];
|
|
281
|
+
ns.forEach(n => {
|
|
282
|
+
if (i18n.options.ns.indexOf(n) < 0) i18n.options.ns.push(n);
|
|
283
|
+
});
|
|
284
|
+
i18n.loadLanguages(lng, loadedClb(i18n, cb));
|
|
285
|
+
}
|
|
286
|
+
function oldI18nextHasLoadedNamespace(ns, i18n) {
|
|
287
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
288
|
+
const lng = i18n.languages[0];
|
|
289
|
+
const fallbackLng = i18n.options ? i18n.options.fallbackLng : false;
|
|
290
|
+
const lastLng = i18n.languages[i18n.languages.length - 1];
|
|
291
|
+
if (lng.toLowerCase() === 'cimode') return true;
|
|
292
|
+
const loadNotPending = (l, n) => {
|
|
293
|
+
const loadState = i18n.services.backendConnector.state[`${l}|${n}`];
|
|
294
|
+
return loadState === -1 || loadState === 2;
|
|
295
|
+
};
|
|
296
|
+
if (options.bindI18n && options.bindI18n.indexOf('languageChanging') > -1 && i18n.services.backendConnector.backend && i18n.isLanguageChangingTo && !loadNotPending(i18n.isLanguageChangingTo, ns)) return false;
|
|
297
|
+
if (i18n.hasResourceBundle(lng, ns)) return true;
|
|
298
|
+
if (!i18n.services.backendConnector.backend || i18n.options.resources && !i18n.options.partialBundledLanguages) return true;
|
|
299
|
+
if (loadNotPending(lng, ns) && (!fallbackLng || loadNotPending(lastLng, ns))) return true;
|
|
300
|
+
return false;
|
|
301
|
+
}
|
|
302
|
+
function hasLoadedNamespace(ns, i18n) {
|
|
303
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
304
|
+
if (!i18n.languages || !i18n.languages.length) {
|
|
305
|
+
warnOnce('i18n.languages were undefined or empty', i18n.languages);
|
|
306
|
+
return true;
|
|
307
|
+
}
|
|
308
|
+
const isNewerI18next = i18n.options.ignoreJSONStructure !== undefined;
|
|
309
|
+
if (!isNewerI18next) {
|
|
310
|
+
return oldI18nextHasLoadedNamespace(ns, i18n, options);
|
|
311
|
+
}
|
|
312
|
+
return i18n.hasLoadedNamespace(ns, {
|
|
313
|
+
lng: options.lng,
|
|
314
|
+
precheck: (i18nInstance, loadNotPending) => {
|
|
315
|
+
if (options.bindI18n && options.bindI18n.indexOf('languageChanging') > -1 && i18nInstance.services.backendConnector.backend && i18nInstance.isLanguageChangingTo && !loadNotPending(i18nInstance.isLanguageChangingTo, ns)) return false;
|
|
316
|
+
}
|
|
317
|
+
});
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
const matchHtmlEntity = /&(?:amp|#38|lt|#60|gt|#62|apos|#39|quot|#34|nbsp|#160|copy|#169|reg|#174|hellip|#8230|#x2F|#47);/g;
|
|
321
|
+
const htmlEntities = {
|
|
322
|
+
'&': '&',
|
|
323
|
+
'&': '&',
|
|
324
|
+
'<': '<',
|
|
325
|
+
'<': '<',
|
|
326
|
+
'>': '>',
|
|
327
|
+
'>': '>',
|
|
328
|
+
''': "'",
|
|
329
|
+
''': "'",
|
|
330
|
+
'"': '"',
|
|
331
|
+
'"': '"',
|
|
332
|
+
' ': ' ',
|
|
333
|
+
' ': ' ',
|
|
334
|
+
'©': '©',
|
|
335
|
+
'©': '©',
|
|
336
|
+
'®': '®',
|
|
337
|
+
'®': '®',
|
|
338
|
+
'…': '…',
|
|
339
|
+
'…': '…',
|
|
340
|
+
'/': '/',
|
|
341
|
+
'/': '/'
|
|
342
|
+
};
|
|
343
|
+
const unescapeHtmlEntity = m => htmlEntities[m];
|
|
344
|
+
const unescape = text => text.replace(matchHtmlEntity, unescapeHtmlEntity);
|
|
345
|
+
|
|
346
|
+
let defaultOptions$1 = {
|
|
347
|
+
bindI18n: 'languageChanged',
|
|
348
|
+
bindI18nStore: '',
|
|
349
|
+
transEmptyNodeValue: '',
|
|
350
|
+
transSupportBasicHtmlNodes: true,
|
|
351
|
+
transWrapTextNodes: '',
|
|
352
|
+
transKeepBasicHtmlNodesFor: ['br', 'strong', 'i', 'p'],
|
|
353
|
+
useSuspense: true,
|
|
354
|
+
unescape
|
|
355
|
+
};
|
|
356
|
+
function setDefaults() {
|
|
357
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
358
|
+
defaultOptions$1 = {
|
|
359
|
+
...defaultOptions$1,
|
|
360
|
+
...options
|
|
361
|
+
};
|
|
362
|
+
}
|
|
363
|
+
function getDefaults() {
|
|
364
|
+
return defaultOptions$1;
|
|
365
|
+
}
|
|
366
|
+
|
|
367
|
+
let i18nInstance;
|
|
368
|
+
function setI18n(instance) {
|
|
369
|
+
i18nInstance = instance;
|
|
370
|
+
}
|
|
371
|
+
function getI18n() {
|
|
372
|
+
return i18nInstance;
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
const initReactI18next = {
|
|
376
|
+
type: '3rdParty',
|
|
377
|
+
init(instance) {
|
|
378
|
+
setDefaults(instance.options.react);
|
|
379
|
+
setI18n(instance);
|
|
380
|
+
}
|
|
381
|
+
};
|
|
382
|
+
|
|
383
|
+
const I18nContext = React.createContext();
|
|
384
|
+
class ReportNamespaces {
|
|
385
|
+
constructor() {
|
|
386
|
+
this.usedNamespaces = {};
|
|
387
|
+
}
|
|
388
|
+
addUsedNamespaces(namespaces) {
|
|
389
|
+
namespaces.forEach(ns => {
|
|
390
|
+
if (!this.usedNamespaces[ns]) this.usedNamespaces[ns] = true;
|
|
391
|
+
});
|
|
392
|
+
}
|
|
393
|
+
getUsedNamespaces() {
|
|
394
|
+
return Object.keys(this.usedNamespaces);
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
const usePrevious = (value, ignore) => {
|
|
399
|
+
const ref = React.useRef();
|
|
400
|
+
React.useEffect(() => {
|
|
401
|
+
ref.current = ignore ? ref.current : value;
|
|
402
|
+
}, [value, ignore]);
|
|
403
|
+
return ref.current;
|
|
404
|
+
};
|
|
405
|
+
function useTranslation(ns) {
|
|
406
|
+
let props = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
407
|
+
const {
|
|
408
|
+
i18n: i18nFromProps
|
|
409
|
+
} = props;
|
|
410
|
+
const {
|
|
411
|
+
i18n: i18nFromContext,
|
|
412
|
+
defaultNS: defaultNSFromContext
|
|
413
|
+
} = React.useContext(I18nContext) || {};
|
|
414
|
+
const i18n = i18nFromProps || i18nFromContext || getI18n();
|
|
415
|
+
if (i18n && !i18n.reportNamespaces) i18n.reportNamespaces = new ReportNamespaces();
|
|
416
|
+
if (!i18n) {
|
|
417
|
+
warnOnce('You will need to pass in an i18next instance by using initReactI18next');
|
|
418
|
+
const notReadyT = (k, optsOrDefaultValue) => {
|
|
419
|
+
if (typeof optsOrDefaultValue === 'string') return optsOrDefaultValue;
|
|
420
|
+
if (optsOrDefaultValue && typeof optsOrDefaultValue === 'object' && typeof optsOrDefaultValue.defaultValue === 'string') return optsOrDefaultValue.defaultValue;
|
|
421
|
+
return Array.isArray(k) ? k[k.length - 1] : k;
|
|
422
|
+
};
|
|
423
|
+
const retNotReady = [notReadyT, {}, false];
|
|
424
|
+
retNotReady.t = notReadyT;
|
|
425
|
+
retNotReady.i18n = {};
|
|
426
|
+
retNotReady.ready = false;
|
|
427
|
+
return retNotReady;
|
|
428
|
+
}
|
|
429
|
+
if (i18n.options.react && i18n.options.react.wait !== undefined) warnOnce('It seems you are still using the old wait option, you may migrate to the new useSuspense behaviour.');
|
|
430
|
+
const i18nOptions = {
|
|
431
|
+
...getDefaults(),
|
|
432
|
+
...i18n.options.react,
|
|
433
|
+
...props
|
|
434
|
+
};
|
|
435
|
+
const {
|
|
436
|
+
useSuspense,
|
|
437
|
+
keyPrefix
|
|
438
|
+
} = i18nOptions;
|
|
439
|
+
let namespaces = ns || defaultNSFromContext || i18n.options && i18n.options.defaultNS;
|
|
440
|
+
namespaces = typeof namespaces === 'string' ? [namespaces] : namespaces || ['translation'];
|
|
441
|
+
if (i18n.reportNamespaces.addUsedNamespaces) i18n.reportNamespaces.addUsedNamespaces(namespaces);
|
|
442
|
+
const ready = (i18n.isInitialized || i18n.initializedStoreOnce) && namespaces.every(n => hasLoadedNamespace(n, i18n, i18nOptions));
|
|
443
|
+
function getT() {
|
|
444
|
+
return i18n.getFixedT(props.lng || null, i18nOptions.nsMode === 'fallback' ? namespaces : namespaces[0], keyPrefix);
|
|
445
|
+
}
|
|
446
|
+
const [t, setT] = React.useState(getT);
|
|
447
|
+
let joinedNS = namespaces.join();
|
|
448
|
+
if (props.lng) joinedNS = `${props.lng}${joinedNS}`;
|
|
449
|
+
const previousJoinedNS = usePrevious(joinedNS);
|
|
450
|
+
const isMounted = React.useRef(true);
|
|
451
|
+
React.useEffect(() => {
|
|
452
|
+
const {
|
|
453
|
+
bindI18n,
|
|
454
|
+
bindI18nStore
|
|
455
|
+
} = i18nOptions;
|
|
456
|
+
isMounted.current = true;
|
|
457
|
+
if (!ready && !useSuspense) {
|
|
458
|
+
if (props.lng) {
|
|
459
|
+
loadLanguages(i18n, props.lng, namespaces, () => {
|
|
460
|
+
if (isMounted.current) setT(getT);
|
|
461
|
+
});
|
|
462
|
+
} else {
|
|
463
|
+
loadNamespaces(i18n, namespaces, () => {
|
|
464
|
+
if (isMounted.current) setT(getT);
|
|
465
|
+
});
|
|
466
|
+
}
|
|
467
|
+
}
|
|
468
|
+
if (ready && previousJoinedNS && previousJoinedNS !== joinedNS && isMounted.current) {
|
|
469
|
+
setT(getT);
|
|
470
|
+
}
|
|
471
|
+
function boundReset() {
|
|
472
|
+
if (isMounted.current) setT(getT);
|
|
473
|
+
}
|
|
474
|
+
if (bindI18n && i18n) i18n.on(bindI18n, boundReset);
|
|
475
|
+
if (bindI18nStore && i18n) i18n.store.on(bindI18nStore, boundReset);
|
|
476
|
+
return () => {
|
|
477
|
+
isMounted.current = false;
|
|
478
|
+
if (bindI18n && i18n) bindI18n.split(' ').forEach(e => i18n.off(e, boundReset));
|
|
479
|
+
if (bindI18nStore && i18n) bindI18nStore.split(' ').forEach(e => i18n.store.off(e, boundReset));
|
|
480
|
+
};
|
|
481
|
+
}, [i18n, joinedNS]);
|
|
482
|
+
const isInitial = React.useRef(true);
|
|
483
|
+
React.useEffect(() => {
|
|
484
|
+
if (isMounted.current && !isInitial.current) {
|
|
485
|
+
setT(getT);
|
|
486
|
+
}
|
|
487
|
+
isInitial.current = false;
|
|
488
|
+
}, [i18n, keyPrefix]);
|
|
489
|
+
const ret = [t, i18n, ready];
|
|
490
|
+
ret.t = t;
|
|
491
|
+
ret.i18n = i18n;
|
|
492
|
+
ret.ready = ready;
|
|
493
|
+
if (ready) return ret;
|
|
494
|
+
if (!ready && !useSuspense) return ret;
|
|
495
|
+
throw new Promise(resolve => {
|
|
496
|
+
if (props.lng) {
|
|
497
|
+
loadLanguages(i18n, props.lng, namespaces, () => resolve());
|
|
498
|
+
} else {
|
|
499
|
+
loadNamespaces(i18n, namespaces, () => resolve());
|
|
500
|
+
}
|
|
501
|
+
});
|
|
502
|
+
}
|
|
503
|
+
|
|
504
|
+
function I18nextProvider(_ref) {
|
|
505
|
+
let {
|
|
506
|
+
i18n,
|
|
507
|
+
defaultNS,
|
|
508
|
+
children
|
|
509
|
+
} = _ref;
|
|
510
|
+
const value = React.useMemo(() => ({
|
|
511
|
+
i18n,
|
|
512
|
+
defaultNS
|
|
513
|
+
}), [i18n, defaultNS]);
|
|
514
|
+
return React.createElement(I18nContext.Provider, {
|
|
515
|
+
value
|
|
516
|
+
}, children);
|
|
517
|
+
}
|
|
518
|
+
|
|
519
|
+
var useUpdateTranslations = function (_a) {
|
|
520
|
+
var language = _a.language;
|
|
521
|
+
var i18n = useTranslation().i18n;
|
|
522
|
+
React.useEffect(function () {
|
|
523
|
+
if (language && i18n.language !== language) {
|
|
524
|
+
i18n.changeLanguage(language);
|
|
525
|
+
}
|
|
526
|
+
}, [language, i18n]);
|
|
527
|
+
};
|
|
528
|
+
|
|
529
|
+
// TODO - Refactor and rename this hook
|
|
530
|
+
var useCloseFilterSection = function (_a) {
|
|
531
|
+
var handleSelectedFilter = _a.handleSelectedFilter;
|
|
532
|
+
var filterSectionRef = React.useRef(null);
|
|
533
|
+
React.useEffect(function () {
|
|
534
|
+
var handleClickOutside = function (event) {
|
|
535
|
+
if (filterSectionRef.current &&
|
|
536
|
+
!filterSectionRef.current.contains(event.target)) {
|
|
537
|
+
handleSelectedFilter(false);
|
|
538
|
+
}
|
|
539
|
+
};
|
|
540
|
+
document.addEventListener('mousedown', handleClickOutside);
|
|
541
|
+
return function () {
|
|
542
|
+
document.removeEventListener('mousedown', handleClickOutside);
|
|
543
|
+
};
|
|
544
|
+
}, [filterSectionRef]);
|
|
545
|
+
return { filterSectionRef: filterSectionRef };
|
|
546
|
+
};
|
|
547
|
+
|
|
548
|
+
var useAutoFocus = function (autoFocus) {
|
|
549
|
+
var ref = React.useRef(null);
|
|
550
|
+
React.useEffect(function () {
|
|
551
|
+
if (!autoFocus || !ref.current)
|
|
552
|
+
return;
|
|
553
|
+
var attemptFocus = function (attempts) {
|
|
554
|
+
if (attempts === void 0) { attempts = 0; }
|
|
555
|
+
if (attempts > 20 || !ref.current)
|
|
556
|
+
return;
|
|
557
|
+
var focusable = ref.current.querySelector('button:not([disabled]), [tabindex]:not([tabindex="-1"])');
|
|
558
|
+
if (focusable) {
|
|
559
|
+
focusable.focus();
|
|
560
|
+
}
|
|
561
|
+
else {
|
|
562
|
+
requestAnimationFrame(function () { return attemptFocus(attempts + 1); });
|
|
563
|
+
}
|
|
564
|
+
};
|
|
565
|
+
requestAnimationFrame(function () { return attemptFocus(); });
|
|
566
|
+
}, [autoFocus]);
|
|
567
|
+
return ref;
|
|
568
|
+
};
|
|
569
|
+
|
|
245
570
|
const isString = obj => typeof obj === 'string';
|
|
246
571
|
const defer = () => {
|
|
247
572
|
let res;
|
|
@@ -302,7 +627,7 @@ const setPath = (object, path, newValue) => {
|
|
|
302
627
|
e = `${p[p.length - 1]}.${e}`;
|
|
303
628
|
p = p.slice(0, p.length - 1);
|
|
304
629
|
last = getLastOfPath(object, p, Object);
|
|
305
|
-
if (last
|
|
630
|
+
if (last && last.obj && typeof last.obj[`${last.k}.${e}`] !== 'undefined') {
|
|
306
631
|
last.obj = undefined;
|
|
307
632
|
}
|
|
308
633
|
}
|
|
@@ -322,7 +647,6 @@ const getPath = (object, path) => {
|
|
|
322
647
|
k
|
|
323
648
|
} = getLastOfPath(object, path);
|
|
324
649
|
if (!obj) return undefined;
|
|
325
|
-
if (!Object.prototype.hasOwnProperty.call(obj, k)) return undefined;
|
|
326
650
|
return obj[k];
|
|
327
651
|
};
|
|
328
652
|
const getPathWithDefaults = (data, defaultData, key) => {
|
|
@@ -400,12 +724,10 @@ const looksLikeObjectPath = (key, nsSeparator, keySeparator) => {
|
|
|
400
724
|
}
|
|
401
725
|
return matched;
|
|
402
726
|
};
|
|
403
|
-
const deepFind = (obj, path
|
|
727
|
+
const deepFind = function (obj, path) {
|
|
728
|
+
let keySeparator = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : '.';
|
|
404
729
|
if (!obj) return undefined;
|
|
405
|
-
if (obj[path])
|
|
406
|
-
if (!Object.prototype.hasOwnProperty.call(obj, path)) return undefined;
|
|
407
|
-
return obj[path];
|
|
408
|
-
}
|
|
730
|
+
if (obj[path]) return obj[path];
|
|
409
731
|
const tokens = path.split(keySeparator);
|
|
410
732
|
let current = obj;
|
|
411
733
|
for (let i = 0; i < tokens.length;) {
|
|
@@ -432,7 +754,7 @@ const deepFind = (obj, path, keySeparator = '.') => {
|
|
|
432
754
|
}
|
|
433
755
|
return current;
|
|
434
756
|
};
|
|
435
|
-
const getCleanedCode = code => code
|
|
757
|
+
const getCleanedCode = code => code && code.replace('_', '-');
|
|
436
758
|
|
|
437
759
|
const consoleLogger = {
|
|
438
760
|
type: 'logger',
|
|
@@ -446,29 +768,43 @@ const consoleLogger = {
|
|
|
446
768
|
this.output('error', args);
|
|
447
769
|
},
|
|
448
770
|
output(type, args) {
|
|
449
|
-
console
|
|
771
|
+
if (console && console[type]) console[type].apply(console, args);
|
|
450
772
|
}
|
|
451
773
|
};
|
|
452
774
|
class Logger {
|
|
453
|
-
constructor(concreteLogger
|
|
775
|
+
constructor(concreteLogger) {
|
|
776
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
454
777
|
this.init(concreteLogger, options);
|
|
455
778
|
}
|
|
456
|
-
init(concreteLogger
|
|
779
|
+
init(concreteLogger) {
|
|
780
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
457
781
|
this.prefix = options.prefix || 'i18next:';
|
|
458
782
|
this.logger = concreteLogger || consoleLogger;
|
|
459
783
|
this.options = options;
|
|
460
784
|
this.debug = options.debug;
|
|
461
785
|
}
|
|
462
|
-
log(
|
|
786
|
+
log() {
|
|
787
|
+
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
788
|
+
args[_key] = arguments[_key];
|
|
789
|
+
}
|
|
463
790
|
return this.forward(args, 'log', '', true);
|
|
464
791
|
}
|
|
465
|
-
warn(
|
|
792
|
+
warn() {
|
|
793
|
+
for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
|
|
794
|
+
args[_key2] = arguments[_key2];
|
|
795
|
+
}
|
|
466
796
|
return this.forward(args, 'warn', '', true);
|
|
467
797
|
}
|
|
468
|
-
error(
|
|
798
|
+
error() {
|
|
799
|
+
for (var _len3 = arguments.length, args = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
|
|
800
|
+
args[_key3] = arguments[_key3];
|
|
801
|
+
}
|
|
469
802
|
return this.forward(args, 'error', '');
|
|
470
803
|
}
|
|
471
|
-
deprecate(
|
|
804
|
+
deprecate() {
|
|
805
|
+
for (var _len4 = arguments.length, args = new Array(_len4), _key4 = 0; _key4 < _len4; _key4++) {
|
|
806
|
+
args[_key4] = arguments[_key4];
|
|
807
|
+
}
|
|
472
808
|
return this.forward(args, 'warn', 'WARNING DEPRECATED: ', true);
|
|
473
809
|
}
|
|
474
810
|
forward(args, lvl, prefix, debugOnly) {
|
|
@@ -512,10 +848,14 @@ class EventEmitter {
|
|
|
512
848
|
}
|
|
513
849
|
this.observers[event].delete(listener);
|
|
514
850
|
}
|
|
515
|
-
emit(event
|
|
851
|
+
emit(event) {
|
|
852
|
+
for (var _len = arguments.length, args = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
|
|
853
|
+
args[_key - 1] = arguments[_key];
|
|
854
|
+
}
|
|
516
855
|
if (this.observers[event]) {
|
|
517
856
|
const cloned = Array.from(this.observers[event].entries());
|
|
518
|
-
cloned.forEach(
|
|
857
|
+
cloned.forEach(_ref => {
|
|
858
|
+
let [observer, numTimesAdded] = _ref;
|
|
519
859
|
for (let i = 0; i < numTimesAdded; i++) {
|
|
520
860
|
observer(...args);
|
|
521
861
|
}
|
|
@@ -523,7 +863,8 @@ class EventEmitter {
|
|
|
523
863
|
}
|
|
524
864
|
if (this.observers['*']) {
|
|
525
865
|
const cloned = Array.from(this.observers['*'].entries());
|
|
526
|
-
cloned.forEach(
|
|
866
|
+
cloned.forEach(_ref2 => {
|
|
867
|
+
let [observer, numTimesAdded] = _ref2;
|
|
527
868
|
for (let i = 0; i < numTimesAdded; i++) {
|
|
528
869
|
observer.apply(observer, [event, ...args]);
|
|
529
870
|
}
|
|
@@ -533,10 +874,11 @@ class EventEmitter {
|
|
|
533
874
|
}
|
|
534
875
|
|
|
535
876
|
class ResourceStore extends EventEmitter {
|
|
536
|
-
constructor(data
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
877
|
+
constructor(data) {
|
|
878
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {
|
|
879
|
+
ns: ['translation'],
|
|
880
|
+
defaultNS: 'translation'
|
|
881
|
+
};
|
|
540
882
|
super();
|
|
541
883
|
this.data = data || {};
|
|
542
884
|
this.options = options;
|
|
@@ -558,7 +900,8 @@ class ResourceStore extends EventEmitter {
|
|
|
558
900
|
this.options.ns.splice(index, 1);
|
|
559
901
|
}
|
|
560
902
|
}
|
|
561
|
-
getResource(lng, ns, key
|
|
903
|
+
getResource(lng, ns, key) {
|
|
904
|
+
let options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {};
|
|
562
905
|
const keySeparator = options.keySeparator !== undefined ? options.keySeparator : this.options.keySeparator;
|
|
563
906
|
const ignoreJSONStructure = options.ignoreJSONStructure !== undefined ? options.ignoreJSONStructure : this.options.ignoreJSONStructure;
|
|
564
907
|
let path;
|
|
@@ -583,11 +926,12 @@ class ResourceStore extends EventEmitter {
|
|
|
583
926
|
key = path.slice(2).join('.');
|
|
584
927
|
}
|
|
585
928
|
if (result || !ignoreJSONStructure || !isString(key)) return result;
|
|
586
|
-
return deepFind(this.data
|
|
929
|
+
return deepFind(this.data && this.data[lng] && this.data[lng][ns], key, keySeparator);
|
|
587
930
|
}
|
|
588
|
-
addResource(lng, ns, key, value
|
|
589
|
-
|
|
590
|
-
|
|
931
|
+
addResource(lng, ns, key, value) {
|
|
932
|
+
let options = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : {
|
|
933
|
+
silent: false
|
|
934
|
+
};
|
|
591
935
|
const keySeparator = options.keySeparator !== undefined ? options.keySeparator : this.options.keySeparator;
|
|
592
936
|
let path = [lng, ns];
|
|
593
937
|
if (key) path = path.concat(keySeparator ? key.split(keySeparator) : key);
|
|
@@ -600,9 +944,10 @@ class ResourceStore extends EventEmitter {
|
|
|
600
944
|
setPath(this.data, path, value);
|
|
601
945
|
if (!options.silent) this.emit('added', lng, ns, key, value);
|
|
602
946
|
}
|
|
603
|
-
addResources(lng, ns, resources
|
|
604
|
-
|
|
605
|
-
|
|
947
|
+
addResources(lng, ns, resources) {
|
|
948
|
+
let options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {
|
|
949
|
+
silent: false
|
|
950
|
+
};
|
|
606
951
|
for (const m in resources) {
|
|
607
952
|
if (isString(resources[m]) || Array.isArray(resources[m])) this.addResource(lng, ns, m, resources[m], {
|
|
608
953
|
silent: true
|
|
@@ -610,10 +955,11 @@ class ResourceStore extends EventEmitter {
|
|
|
610
955
|
}
|
|
611
956
|
if (!options.silent) this.emit('added', lng, ns, resources);
|
|
612
957
|
}
|
|
613
|
-
addResourceBundle(lng, ns, resources, deep, overwrite
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
958
|
+
addResourceBundle(lng, ns, resources, deep, overwrite) {
|
|
959
|
+
let options = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : {
|
|
960
|
+
silent: false,
|
|
961
|
+
skipCopy: false
|
|
962
|
+
};
|
|
617
963
|
let path = [lng, ns];
|
|
618
964
|
if (lng.indexOf('.') > -1) {
|
|
619
965
|
path = lng.split('.');
|
|
@@ -647,6 +993,10 @@ class ResourceStore extends EventEmitter {
|
|
|
647
993
|
}
|
|
648
994
|
getResourceBundle(lng, ns) {
|
|
649
995
|
if (!ns) ns = this.options.defaultNS;
|
|
996
|
+
if (this.options.compatibilityAPI === 'v1') return {
|
|
997
|
+
...{},
|
|
998
|
+
...this.getResource(lng, ns)
|
|
999
|
+
};
|
|
650
1000
|
return this.getResource(lng, ns);
|
|
651
1001
|
}
|
|
652
1002
|
getDataByLanguage(lng) {
|
|
@@ -669,37 +1019,16 @@ var postProcessor = {
|
|
|
669
1019
|
},
|
|
670
1020
|
handle(processors, value, key, options, translator) {
|
|
671
1021
|
processors.forEach(processor => {
|
|
672
|
-
value = this.processors[processor]
|
|
1022
|
+
if (this.processors[processor]) value = this.processors[processor].process(value, key, options, translator);
|
|
673
1023
|
});
|
|
674
1024
|
return value;
|
|
675
1025
|
}
|
|
676
1026
|
};
|
|
677
1027
|
|
|
678
|
-
const PATH_KEY = Symbol('i18next/PATH_KEY');
|
|
679
|
-
function createProxy() {
|
|
680
|
-
const state = [];
|
|
681
|
-
const handler = Object.create(null);
|
|
682
|
-
let proxy;
|
|
683
|
-
handler.get = (target, key) => {
|
|
684
|
-
proxy?.revoke?.();
|
|
685
|
-
if (key === PATH_KEY) return state;
|
|
686
|
-
state.push(key);
|
|
687
|
-
proxy = Proxy.revocable(target, handler);
|
|
688
|
-
return proxy.proxy;
|
|
689
|
-
};
|
|
690
|
-
return Proxy.revocable(Object.create(null), handler).proxy;
|
|
691
|
-
}
|
|
692
|
-
function keysFromSelector(selector, opts) {
|
|
693
|
-
const {
|
|
694
|
-
[PATH_KEY]: path
|
|
695
|
-
} = selector(createProxy());
|
|
696
|
-
return path.join(opts?.keySeparator ?? '.');
|
|
697
|
-
}
|
|
698
|
-
|
|
699
1028
|
const checkedLoadedFor = {};
|
|
700
|
-
const shouldHandleAsObject = res => !isString(res) && typeof res !== 'boolean' && typeof res !== 'number';
|
|
701
1029
|
class Translator extends EventEmitter {
|
|
702
|
-
constructor(services
|
|
1030
|
+
constructor(services) {
|
|
1031
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
703
1032
|
super();
|
|
704
1033
|
copy(['resourceStore', 'languageUtils', 'pluralResolver', 'interpolator', 'backendConnector', 'i18nFormat', 'utils'], services, this);
|
|
705
1034
|
this.options = options;
|
|
@@ -711,28 +1040,23 @@ class Translator extends EventEmitter {
|
|
|
711
1040
|
changeLanguage(lng) {
|
|
712
1041
|
if (lng) this.language = lng;
|
|
713
1042
|
}
|
|
714
|
-
exists(key
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
const opt = {
|
|
718
|
-
...o
|
|
1043
|
+
exists(key) {
|
|
1044
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {
|
|
1045
|
+
interpolation: {}
|
|
719
1046
|
};
|
|
720
|
-
if (key
|
|
721
|
-
const resolved = this.resolve(key, opt);
|
|
722
|
-
if (resolved?.res === undefined) return false;
|
|
723
|
-
const isObject = shouldHandleAsObject(resolved.res);
|
|
724
|
-
if (opt.returnObjects === false && isObject) {
|
|
1047
|
+
if (key === undefined || key === null) {
|
|
725
1048
|
return false;
|
|
726
1049
|
}
|
|
727
|
-
|
|
1050
|
+
const resolved = this.resolve(key, options);
|
|
1051
|
+
return resolved && resolved.res !== undefined;
|
|
728
1052
|
}
|
|
729
|
-
extractFromKey(key,
|
|
730
|
-
let nsSeparator =
|
|
1053
|
+
extractFromKey(key, options) {
|
|
1054
|
+
let nsSeparator = options.nsSeparator !== undefined ? options.nsSeparator : this.options.nsSeparator;
|
|
731
1055
|
if (nsSeparator === undefined) nsSeparator = ':';
|
|
732
|
-
const keySeparator =
|
|
733
|
-
let namespaces =
|
|
1056
|
+
const keySeparator = options.keySeparator !== undefined ? options.keySeparator : this.options.keySeparator;
|
|
1057
|
+
let namespaces = options.ns || this.options.defaultNS || [];
|
|
734
1058
|
const wouldCheckForNsInKey = nsSeparator && key.indexOf(nsSeparator) > -1;
|
|
735
|
-
const seemsNaturalLanguage = !this.options.userDefinedKeySeparator && !
|
|
1059
|
+
const seemsNaturalLanguage = !this.options.userDefinedKeySeparator && !options.keySeparator && !this.options.userDefinedNsSeparator && !options.nsSeparator && !looksLikeObjectPath(key, nsSeparator, keySeparator);
|
|
736
1060
|
if (wouldCheckForNsInKey && !seemsNaturalLanguage) {
|
|
737
1061
|
const m = key.match(this.interpolator.nestingRegexp);
|
|
738
1062
|
if (m && m.length > 0) {
|
|
@@ -750,36 +1074,28 @@ class Translator extends EventEmitter {
|
|
|
750
1074
|
namespaces: isString(namespaces) ? [namespaces] : namespaces
|
|
751
1075
|
};
|
|
752
1076
|
}
|
|
753
|
-
translate(keys,
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
} : o;
|
|
757
|
-
if (typeof opt !== 'object' && this.options.overloadTranslationOptionHandler) {
|
|
758
|
-
opt = this.options.overloadTranslationOptionHandler(arguments);
|
|
1077
|
+
translate(keys, options, lastKey) {
|
|
1078
|
+
if (typeof options !== 'object' && this.options.overloadTranslationOptionHandler) {
|
|
1079
|
+
options = this.options.overloadTranslationOptionHandler(arguments);
|
|
759
1080
|
}
|
|
760
|
-
if (typeof
|
|
761
|
-
...
|
|
1081
|
+
if (typeof options === 'object') options = {
|
|
1082
|
+
...options
|
|
762
1083
|
};
|
|
763
|
-
if (!
|
|
764
|
-
if (keys
|
|
765
|
-
if (typeof keys === 'function') keys = keysFromSelector(keys, {
|
|
766
|
-
...this.options,
|
|
767
|
-
...opt
|
|
768
|
-
});
|
|
1084
|
+
if (!options) options = {};
|
|
1085
|
+
if (keys === undefined || keys === null) return '';
|
|
769
1086
|
if (!Array.isArray(keys)) keys = [String(keys)];
|
|
770
|
-
const returnDetails =
|
|
771
|
-
const keySeparator =
|
|
1087
|
+
const returnDetails = options.returnDetails !== undefined ? options.returnDetails : this.options.returnDetails;
|
|
1088
|
+
const keySeparator = options.keySeparator !== undefined ? options.keySeparator : this.options.keySeparator;
|
|
772
1089
|
const {
|
|
773
1090
|
key,
|
|
774
1091
|
namespaces
|
|
775
|
-
} = this.extractFromKey(keys[keys.length - 1],
|
|
1092
|
+
} = this.extractFromKey(keys[keys.length - 1], options);
|
|
776
1093
|
const namespace = namespaces[namespaces.length - 1];
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
const appendNamespaceToCIMode = opt.appendNamespaceToCIMode || this.options.appendNamespaceToCIMode;
|
|
781
|
-
if (lng?.toLowerCase() === 'cimode') {
|
|
1094
|
+
const lng = options.lng || this.language;
|
|
1095
|
+
const appendNamespaceToCIMode = options.appendNamespaceToCIMode || this.options.appendNamespaceToCIMode;
|
|
1096
|
+
if (lng && lng.toLowerCase() === 'cimode') {
|
|
782
1097
|
if (appendNamespaceToCIMode) {
|
|
1098
|
+
const nsSeparator = options.nsSeparator || this.options.nsSeparator;
|
|
783
1099
|
if (returnDetails) {
|
|
784
1100
|
return {
|
|
785
1101
|
res: `${namespace}${nsSeparator}${key}`,
|
|
@@ -787,7 +1103,7 @@ class Translator extends EventEmitter {
|
|
|
787
1103
|
exactUsedKey: key,
|
|
788
1104
|
usedLng: lng,
|
|
789
1105
|
usedNS: namespace,
|
|
790
|
-
usedParams: this.getUsedParamsDetails(
|
|
1106
|
+
usedParams: this.getUsedParamsDetails(options)
|
|
791
1107
|
};
|
|
792
1108
|
}
|
|
793
1109
|
return `${namespace}${nsSeparator}${key}`;
|
|
@@ -799,84 +1115,69 @@ class Translator extends EventEmitter {
|
|
|
799
1115
|
exactUsedKey: key,
|
|
800
1116
|
usedLng: lng,
|
|
801
1117
|
usedNS: namespace,
|
|
802
|
-
usedParams: this.getUsedParamsDetails(
|
|
1118
|
+
usedParams: this.getUsedParamsDetails(options)
|
|
803
1119
|
};
|
|
804
1120
|
}
|
|
805
1121
|
return key;
|
|
806
1122
|
}
|
|
807
|
-
const resolved = this.resolve(keys,
|
|
808
|
-
let res = resolved
|
|
809
|
-
const resUsedKey = resolved
|
|
810
|
-
const resExactUsedKey = resolved
|
|
1123
|
+
const resolved = this.resolve(keys, options);
|
|
1124
|
+
let res = resolved && resolved.res;
|
|
1125
|
+
const resUsedKey = resolved && resolved.usedKey || key;
|
|
1126
|
+
const resExactUsedKey = resolved && resolved.exactUsedKey || key;
|
|
1127
|
+
const resType = Object.prototype.toString.apply(res);
|
|
811
1128
|
const noObject = ['[object Number]', '[object Function]', '[object RegExp]'];
|
|
812
|
-
const joinArrays =
|
|
1129
|
+
const joinArrays = options.joinArrays !== undefined ? options.joinArrays : this.options.joinArrays;
|
|
813
1130
|
const handleAsObjectInI18nFormat = !this.i18nFormat || this.i18nFormat.handleAsObject;
|
|
814
|
-
const
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
const defaultValueSuffixOrdinalFallback = opt.ordinal && needsPluralHandling ? this.pluralResolver.getSuffix(lng, opt.count, {
|
|
818
|
-
ordinal: false
|
|
819
|
-
}) : '';
|
|
820
|
-
const needsZeroSuffixLookup = needsPluralHandling && !opt.ordinal && opt.count === 0;
|
|
821
|
-
const defaultValue = needsZeroSuffixLookup && opt[`defaultValue${this.options.pluralSeparator}zero`] || opt[`defaultValue${defaultValueSuffix}`] || opt[`defaultValue${defaultValueSuffixOrdinalFallback}`] || opt.defaultValue;
|
|
822
|
-
let resForObjHndl = res;
|
|
823
|
-
if (handleAsObjectInI18nFormat && !res && hasDefaultValue) {
|
|
824
|
-
resForObjHndl = defaultValue;
|
|
825
|
-
}
|
|
826
|
-
const handleAsObject = shouldHandleAsObject(resForObjHndl);
|
|
827
|
-
const resType = Object.prototype.toString.apply(resForObjHndl);
|
|
828
|
-
if (handleAsObjectInI18nFormat && resForObjHndl && handleAsObject && noObject.indexOf(resType) < 0 && !(isString(joinArrays) && Array.isArray(resForObjHndl))) {
|
|
829
|
-
if (!opt.returnObjects && !this.options.returnObjects) {
|
|
1131
|
+
const handleAsObject = !isString(res) && typeof res !== 'boolean' && typeof res !== 'number';
|
|
1132
|
+
if (handleAsObjectInI18nFormat && res && handleAsObject && noObject.indexOf(resType) < 0 && !(isString(joinArrays) && Array.isArray(res))) {
|
|
1133
|
+
if (!options.returnObjects && !this.options.returnObjects) {
|
|
830
1134
|
if (!this.options.returnedObjectHandler) {
|
|
831
1135
|
this.logger.warn('accessing an object - but returnObjects options is not enabled!');
|
|
832
1136
|
}
|
|
833
|
-
const r = this.options.returnedObjectHandler ? this.options.returnedObjectHandler(resUsedKey,
|
|
834
|
-
...
|
|
1137
|
+
const r = this.options.returnedObjectHandler ? this.options.returnedObjectHandler(resUsedKey, res, {
|
|
1138
|
+
...options,
|
|
835
1139
|
ns: namespaces
|
|
836
1140
|
}) : `key '${key} (${this.language})' returned an object instead of string.`;
|
|
837
1141
|
if (returnDetails) {
|
|
838
1142
|
resolved.res = r;
|
|
839
|
-
resolved.usedParams = this.getUsedParamsDetails(
|
|
1143
|
+
resolved.usedParams = this.getUsedParamsDetails(options);
|
|
840
1144
|
return resolved;
|
|
841
1145
|
}
|
|
842
1146
|
return r;
|
|
843
1147
|
}
|
|
844
1148
|
if (keySeparator) {
|
|
845
|
-
const resTypeIsArray = Array.isArray(
|
|
1149
|
+
const resTypeIsArray = Array.isArray(res);
|
|
846
1150
|
const copy = resTypeIsArray ? [] : {};
|
|
847
1151
|
const newKeyToUse = resTypeIsArray ? resExactUsedKey : resUsedKey;
|
|
848
|
-
for (const m in
|
|
849
|
-
if (Object.prototype.hasOwnProperty.call(
|
|
1152
|
+
for (const m in res) {
|
|
1153
|
+
if (Object.prototype.hasOwnProperty.call(res, m)) {
|
|
850
1154
|
const deepKey = `${newKeyToUse}${keySeparator}${m}`;
|
|
851
|
-
|
|
852
|
-
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
});
|
|
860
|
-
} else {
|
|
861
|
-
copy[m] = this.translate(deepKey, {
|
|
862
|
-
...opt,
|
|
863
|
-
...{
|
|
864
|
-
joinArrays: false,
|
|
865
|
-
ns: namespaces
|
|
866
|
-
}
|
|
867
|
-
});
|
|
868
|
-
}
|
|
869
|
-
if (copy[m] === deepKey) copy[m] = resForObjHndl[m];
|
|
1155
|
+
copy[m] = this.translate(deepKey, {
|
|
1156
|
+
...options,
|
|
1157
|
+
...{
|
|
1158
|
+
joinArrays: false,
|
|
1159
|
+
ns: namespaces
|
|
1160
|
+
}
|
|
1161
|
+
});
|
|
1162
|
+
if (copy[m] === deepKey) copy[m] = res[m];
|
|
870
1163
|
}
|
|
871
1164
|
}
|
|
872
1165
|
res = copy;
|
|
873
1166
|
}
|
|
874
1167
|
} else if (handleAsObjectInI18nFormat && isString(joinArrays) && Array.isArray(res)) {
|
|
875
1168
|
res = res.join(joinArrays);
|
|
876
|
-
if (res) res = this.extendTranslation(res, keys,
|
|
1169
|
+
if (res) res = this.extendTranslation(res, keys, options, lastKey);
|
|
877
1170
|
} else {
|
|
878
1171
|
let usedDefault = false;
|
|
879
1172
|
let usedKey = false;
|
|
1173
|
+
const needsPluralHandling = options.count !== undefined && !isString(options.count);
|
|
1174
|
+
const hasDefaultValue = Translator.hasDefaultValue(options);
|
|
1175
|
+
const defaultValueSuffix = needsPluralHandling ? this.pluralResolver.getSuffix(lng, options.count, options) : '';
|
|
1176
|
+
const defaultValueSuffixOrdinalFallback = options.ordinal && needsPluralHandling ? this.pluralResolver.getSuffix(lng, options.count, {
|
|
1177
|
+
ordinal: false
|
|
1178
|
+
}) : '';
|
|
1179
|
+
const needsZeroSuffixLookup = needsPluralHandling && !options.ordinal && options.count === 0 && this.pluralResolver.shouldUseIntlApi();
|
|
1180
|
+
const defaultValue = needsZeroSuffixLookup && options[`defaultValue${this.options.pluralSeparator}zero`] || options[`defaultValue${defaultValueSuffix}`] || options[`defaultValue${defaultValueSuffixOrdinalFallback}`] || options.defaultValue;
|
|
880
1181
|
if (!this.isValidLookup(res) && hasDefaultValue) {
|
|
881
1182
|
usedDefault = true;
|
|
882
1183
|
res = defaultValue;
|
|
@@ -885,47 +1186,47 @@ class Translator extends EventEmitter {
|
|
|
885
1186
|
usedKey = true;
|
|
886
1187
|
res = key;
|
|
887
1188
|
}
|
|
888
|
-
const missingKeyNoValueFallbackToKey =
|
|
1189
|
+
const missingKeyNoValueFallbackToKey = options.missingKeyNoValueFallbackToKey || this.options.missingKeyNoValueFallbackToKey;
|
|
889
1190
|
const resForMissing = missingKeyNoValueFallbackToKey && usedKey ? undefined : res;
|
|
890
1191
|
const updateMissing = hasDefaultValue && defaultValue !== res && this.options.updateMissing;
|
|
891
1192
|
if (usedKey || usedDefault || updateMissing) {
|
|
892
1193
|
this.logger.log(updateMissing ? 'updateKey' : 'missingKey', lng, namespace, key, updateMissing ? defaultValue : res);
|
|
893
1194
|
if (keySeparator) {
|
|
894
1195
|
const fk = this.resolve(key, {
|
|
895
|
-
...
|
|
1196
|
+
...options,
|
|
896
1197
|
keySeparator: false
|
|
897
1198
|
});
|
|
898
1199
|
if (fk && fk.res) this.logger.warn('Seems the loaded translations were in flat JSON format instead of nested. Either set keySeparator: false on init or make sure your translations are published in nested format.');
|
|
899
1200
|
}
|
|
900
1201
|
let lngs = [];
|
|
901
|
-
const fallbackLngs = this.languageUtils.getFallbackCodes(this.options.fallbackLng,
|
|
1202
|
+
const fallbackLngs = this.languageUtils.getFallbackCodes(this.options.fallbackLng, options.lng || this.language);
|
|
902
1203
|
if (this.options.saveMissingTo === 'fallback' && fallbackLngs && fallbackLngs[0]) {
|
|
903
1204
|
for (let i = 0; i < fallbackLngs.length; i++) {
|
|
904
1205
|
lngs.push(fallbackLngs[i]);
|
|
905
1206
|
}
|
|
906
1207
|
} else if (this.options.saveMissingTo === 'all') {
|
|
907
|
-
lngs = this.languageUtils.toResolveHierarchy(
|
|
1208
|
+
lngs = this.languageUtils.toResolveHierarchy(options.lng || this.language);
|
|
908
1209
|
} else {
|
|
909
|
-
lngs.push(
|
|
1210
|
+
lngs.push(options.lng || this.language);
|
|
910
1211
|
}
|
|
911
1212
|
const send = (l, k, specificDefaultValue) => {
|
|
912
1213
|
const defaultForMissing = hasDefaultValue && specificDefaultValue !== res ? specificDefaultValue : resForMissing;
|
|
913
1214
|
if (this.options.missingKeyHandler) {
|
|
914
|
-
this.options.missingKeyHandler(l, namespace, k, defaultForMissing, updateMissing,
|
|
915
|
-
} else if (this.backendConnector
|
|
916
|
-
this.backendConnector.saveMissing(l, namespace, k, defaultForMissing, updateMissing,
|
|
1215
|
+
this.options.missingKeyHandler(l, namespace, k, defaultForMissing, updateMissing, options);
|
|
1216
|
+
} else if (this.backendConnector && this.backendConnector.saveMissing) {
|
|
1217
|
+
this.backendConnector.saveMissing(l, namespace, k, defaultForMissing, updateMissing, options);
|
|
917
1218
|
}
|
|
918
1219
|
this.emit('missingKey', l, namespace, k, res);
|
|
919
1220
|
};
|
|
920
1221
|
if (this.options.saveMissing) {
|
|
921
1222
|
if (this.options.saveMissingPlurals && needsPluralHandling) {
|
|
922
1223
|
lngs.forEach(language => {
|
|
923
|
-
const suffixes = this.pluralResolver.getSuffixes(language,
|
|
924
|
-
if (needsZeroSuffixLookup &&
|
|
1224
|
+
const suffixes = this.pluralResolver.getSuffixes(language, options);
|
|
1225
|
+
if (needsZeroSuffixLookup && options[`defaultValue${this.options.pluralSeparator}zero`] && suffixes.indexOf(`${this.options.pluralSeparator}zero`) < 0) {
|
|
925
1226
|
suffixes.push(`${this.options.pluralSeparator}zero`);
|
|
926
1227
|
}
|
|
927
1228
|
suffixes.forEach(suffix => {
|
|
928
|
-
send([language], key + suffix,
|
|
1229
|
+
send([language], key + suffix, options[`defaultValue${suffix}`] || defaultValue);
|
|
929
1230
|
});
|
|
930
1231
|
});
|
|
931
1232
|
} else {
|
|
@@ -933,80 +1234,87 @@ class Translator extends EventEmitter {
|
|
|
933
1234
|
}
|
|
934
1235
|
}
|
|
935
1236
|
}
|
|
936
|
-
res = this.extendTranslation(res, keys,
|
|
937
|
-
if (usedKey && res === key && this.options.appendNamespaceToMissingKey) {
|
|
938
|
-
res = `${namespace}${nsSeparator}${key}`;
|
|
939
|
-
}
|
|
1237
|
+
res = this.extendTranslation(res, keys, options, resolved, lastKey);
|
|
1238
|
+
if (usedKey && res === key && this.options.appendNamespaceToMissingKey) res = `${namespace}:${key}`;
|
|
940
1239
|
if ((usedKey || usedDefault) && this.options.parseMissingKeyHandler) {
|
|
941
|
-
|
|
1240
|
+
if (this.options.compatibilityAPI !== 'v1') {
|
|
1241
|
+
res = this.options.parseMissingKeyHandler(this.options.appendNamespaceToMissingKey ? `${namespace}:${key}` : key, usedDefault ? res : undefined);
|
|
1242
|
+
} else {
|
|
1243
|
+
res = this.options.parseMissingKeyHandler(res);
|
|
1244
|
+
}
|
|
942
1245
|
}
|
|
943
1246
|
}
|
|
944
1247
|
if (returnDetails) {
|
|
945
1248
|
resolved.res = res;
|
|
946
|
-
resolved.usedParams = this.getUsedParamsDetails(
|
|
1249
|
+
resolved.usedParams = this.getUsedParamsDetails(options);
|
|
947
1250
|
return resolved;
|
|
948
1251
|
}
|
|
949
1252
|
return res;
|
|
950
1253
|
}
|
|
951
|
-
extendTranslation(res, key,
|
|
952
|
-
|
|
1254
|
+
extendTranslation(res, key, options, resolved, lastKey) {
|
|
1255
|
+
var _this = this;
|
|
1256
|
+
if (this.i18nFormat && this.i18nFormat.parse) {
|
|
953
1257
|
res = this.i18nFormat.parse(res, {
|
|
954
1258
|
...this.options.interpolation.defaultVariables,
|
|
955
|
-
...
|
|
956
|
-
},
|
|
1259
|
+
...options
|
|
1260
|
+
}, options.lng || this.language || resolved.usedLng, resolved.usedNS, resolved.usedKey, {
|
|
957
1261
|
resolved
|
|
958
1262
|
});
|
|
959
|
-
} else if (!
|
|
960
|
-
if (
|
|
961
|
-
...
|
|
1263
|
+
} else if (!options.skipInterpolation) {
|
|
1264
|
+
if (options.interpolation) this.interpolator.init({
|
|
1265
|
+
...options,
|
|
962
1266
|
...{
|
|
963
1267
|
interpolation: {
|
|
964
1268
|
...this.options.interpolation,
|
|
965
|
-
...
|
|
1269
|
+
...options.interpolation
|
|
966
1270
|
}
|
|
967
1271
|
}
|
|
968
1272
|
});
|
|
969
|
-
const skipOnVariables = isString(res) && (
|
|
1273
|
+
const skipOnVariables = isString(res) && (options && options.interpolation && options.interpolation.skipOnVariables !== undefined ? options.interpolation.skipOnVariables : this.options.interpolation.skipOnVariables);
|
|
970
1274
|
let nestBef;
|
|
971
1275
|
if (skipOnVariables) {
|
|
972
1276
|
const nb = res.match(this.interpolator.nestingRegexp);
|
|
973
1277
|
nestBef = nb && nb.length;
|
|
974
1278
|
}
|
|
975
|
-
let data =
|
|
1279
|
+
let data = options.replace && !isString(options.replace) ? options.replace : options;
|
|
976
1280
|
if (this.options.interpolation.defaultVariables) data = {
|
|
977
1281
|
...this.options.interpolation.defaultVariables,
|
|
978
1282
|
...data
|
|
979
1283
|
};
|
|
980
|
-
res = this.interpolator.interpolate(res, data,
|
|
1284
|
+
res = this.interpolator.interpolate(res, data, options.lng || this.language || resolved.usedLng, options);
|
|
981
1285
|
if (skipOnVariables) {
|
|
982
1286
|
const na = res.match(this.interpolator.nestingRegexp);
|
|
983
1287
|
const nestAft = na && na.length;
|
|
984
|
-
if (nestBef < nestAft)
|
|
1288
|
+
if (nestBef < nestAft) options.nest = false;
|
|
985
1289
|
}
|
|
986
|
-
if (!
|
|
987
|
-
if (
|
|
988
|
-
|
|
989
|
-
|
|
1290
|
+
if (!options.lng && this.options.compatibilityAPI !== 'v1' && resolved && resolved.res) options.lng = this.language || resolved.usedLng;
|
|
1291
|
+
if (options.nest !== false) res = this.interpolator.nest(res, function () {
|
|
1292
|
+
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
1293
|
+
args[_key] = arguments[_key];
|
|
1294
|
+
}
|
|
1295
|
+
if (lastKey && lastKey[0] === args[0] && !options.context) {
|
|
1296
|
+
_this.logger.warn(`It seems you are nesting recursively key: ${args[0]} in key: ${key[0]}`);
|
|
990
1297
|
return null;
|
|
991
1298
|
}
|
|
992
|
-
return
|
|
993
|
-
},
|
|
994
|
-
if (
|
|
1299
|
+
return _this.translate(...args, key);
|
|
1300
|
+
}, options);
|
|
1301
|
+
if (options.interpolation) this.interpolator.reset();
|
|
995
1302
|
}
|
|
996
|
-
const postProcess =
|
|
1303
|
+
const postProcess = options.postProcess || this.options.postProcess;
|
|
997
1304
|
const postProcessorNames = isString(postProcess) ? [postProcess] : postProcess;
|
|
998
|
-
if (res
|
|
1305
|
+
if (res !== undefined && res !== null && postProcessorNames && postProcessorNames.length && options.applyPostProcessor !== false) {
|
|
999
1306
|
res = postProcessor.handle(postProcessorNames, res, key, this.options && this.options.postProcessPassResolved ? {
|
|
1000
1307
|
i18nResolved: {
|
|
1001
1308
|
...resolved,
|
|
1002
|
-
usedParams: this.getUsedParamsDetails(
|
|
1309
|
+
usedParams: this.getUsedParamsDetails(options)
|
|
1003
1310
|
},
|
|
1004
|
-
...
|
|
1005
|
-
} :
|
|
1311
|
+
...options
|
|
1312
|
+
} : options, this);
|
|
1006
1313
|
}
|
|
1007
1314
|
return res;
|
|
1008
1315
|
}
|
|
1009
|
-
resolve(keys
|
|
1316
|
+
resolve(keys) {
|
|
1317
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
1010
1318
|
let found;
|
|
1011
1319
|
let usedKey;
|
|
1012
1320
|
let exactUsedKey;
|
|
@@ -1015,19 +1323,19 @@ class Translator extends EventEmitter {
|
|
|
1015
1323
|
if (isString(keys)) keys = [keys];
|
|
1016
1324
|
keys.forEach(k => {
|
|
1017
1325
|
if (this.isValidLookup(found)) return;
|
|
1018
|
-
const extracted = this.extractFromKey(k,
|
|
1326
|
+
const extracted = this.extractFromKey(k, options);
|
|
1019
1327
|
const key = extracted.key;
|
|
1020
1328
|
usedKey = key;
|
|
1021
1329
|
let namespaces = extracted.namespaces;
|
|
1022
1330
|
if (this.options.fallbackNS) namespaces = namespaces.concat(this.options.fallbackNS);
|
|
1023
|
-
const needsPluralHandling =
|
|
1024
|
-
const needsZeroSuffixLookup = needsPluralHandling && !
|
|
1025
|
-
const needsContextHandling =
|
|
1026
|
-
const codes =
|
|
1331
|
+
const needsPluralHandling = options.count !== undefined && !isString(options.count);
|
|
1332
|
+
const needsZeroSuffixLookup = needsPluralHandling && !options.ordinal && options.count === 0 && this.pluralResolver.shouldUseIntlApi();
|
|
1333
|
+
const needsContextHandling = options.context !== undefined && (isString(options.context) || typeof options.context === 'number') && options.context !== '';
|
|
1334
|
+
const codes = options.lngs ? options.lngs : this.languageUtils.toResolveHierarchy(options.lng || this.language, options.fallbackLng);
|
|
1027
1335
|
namespaces.forEach(ns => {
|
|
1028
1336
|
if (this.isValidLookup(found)) return;
|
|
1029
1337
|
usedNS = ns;
|
|
1030
|
-
if (!checkedLoadedFor[`${codes[0]}-${ns}`] && this.utils
|
|
1338
|
+
if (!checkedLoadedFor[`${codes[0]}-${ns}`] && this.utils && this.utils.hasLoadedNamespace && !this.utils.hasLoadedNamespace(usedNS)) {
|
|
1031
1339
|
checkedLoadedFor[`${codes[0]}-${ns}`] = true;
|
|
1032
1340
|
this.logger.warn(`key "${usedKey}" for languages "${codes.join(', ')}" won't get resolved as namespace "${usedNS}" was not yet loaded`, 'This means something IS WRONG in your setup. You access the t function before i18next.init / i18next.loadNamespace / i18next.changeLanguage was done. Wait for the callback or Promise to resolve before accessing it!!!');
|
|
1033
1341
|
}
|
|
@@ -1035,30 +1343,30 @@ class Translator extends EventEmitter {
|
|
|
1035
1343
|
if (this.isValidLookup(found)) return;
|
|
1036
1344
|
usedLng = code;
|
|
1037
1345
|
const finalKeys = [key];
|
|
1038
|
-
if (this.i18nFormat
|
|
1039
|
-
this.i18nFormat.addLookupKeys(finalKeys, key, code, ns,
|
|
1346
|
+
if (this.i18nFormat && this.i18nFormat.addLookupKeys) {
|
|
1347
|
+
this.i18nFormat.addLookupKeys(finalKeys, key, code, ns, options);
|
|
1040
1348
|
} else {
|
|
1041
1349
|
let pluralSuffix;
|
|
1042
|
-
if (needsPluralHandling) pluralSuffix = this.pluralResolver.getSuffix(code,
|
|
1350
|
+
if (needsPluralHandling) pluralSuffix = this.pluralResolver.getSuffix(code, options.count, options);
|
|
1043
1351
|
const zeroSuffix = `${this.options.pluralSeparator}zero`;
|
|
1044
1352
|
const ordinalPrefix = `${this.options.pluralSeparator}ordinal${this.options.pluralSeparator}`;
|
|
1045
1353
|
if (needsPluralHandling) {
|
|
1046
|
-
|
|
1354
|
+
finalKeys.push(key + pluralSuffix);
|
|
1355
|
+
if (options.ordinal && pluralSuffix.indexOf(ordinalPrefix) === 0) {
|
|
1047
1356
|
finalKeys.push(key + pluralSuffix.replace(ordinalPrefix, this.options.pluralSeparator));
|
|
1048
1357
|
}
|
|
1049
|
-
finalKeys.push(key + pluralSuffix);
|
|
1050
1358
|
if (needsZeroSuffixLookup) {
|
|
1051
1359
|
finalKeys.push(key + zeroSuffix);
|
|
1052
1360
|
}
|
|
1053
1361
|
}
|
|
1054
1362
|
if (needsContextHandling) {
|
|
1055
|
-
const contextKey = `${key}${this.options.contextSeparator
|
|
1363
|
+
const contextKey = `${key}${this.options.contextSeparator}${options.context}`;
|
|
1056
1364
|
finalKeys.push(contextKey);
|
|
1057
1365
|
if (needsPluralHandling) {
|
|
1058
|
-
|
|
1366
|
+
finalKeys.push(contextKey + pluralSuffix);
|
|
1367
|
+
if (options.ordinal && pluralSuffix.indexOf(ordinalPrefix) === 0) {
|
|
1059
1368
|
finalKeys.push(contextKey + pluralSuffix.replace(ordinalPrefix, this.options.pluralSeparator));
|
|
1060
1369
|
}
|
|
1061
|
-
finalKeys.push(contextKey + pluralSuffix);
|
|
1062
1370
|
if (needsZeroSuffixLookup) {
|
|
1063
1371
|
finalKeys.push(contextKey + zeroSuffix);
|
|
1064
1372
|
}
|
|
@@ -1069,7 +1377,7 @@ class Translator extends EventEmitter {
|
|
|
1069
1377
|
while (possibleKey = finalKeys.pop()) {
|
|
1070
1378
|
if (!this.isValidLookup(found)) {
|
|
1071
1379
|
exactUsedKey = possibleKey;
|
|
1072
|
-
found = this.getResource(code, ns, possibleKey,
|
|
1380
|
+
found = this.getResource(code, ns, possibleKey, options);
|
|
1073
1381
|
}
|
|
1074
1382
|
}
|
|
1075
1383
|
});
|
|
@@ -1086,11 +1394,13 @@ class Translator extends EventEmitter {
|
|
|
1086
1394
|
isValidLookup(res) {
|
|
1087
1395
|
return res !== undefined && !(!this.options.returnNull && res === null) && !(!this.options.returnEmptyString && res === '');
|
|
1088
1396
|
}
|
|
1089
|
-
getResource(code, ns, key
|
|
1090
|
-
|
|
1397
|
+
getResource(code, ns, key) {
|
|
1398
|
+
let options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {};
|
|
1399
|
+
if (this.i18nFormat && this.i18nFormat.getResource) return this.i18nFormat.getResource(code, ns, key, options);
|
|
1091
1400
|
return this.resourceStore.getResource(code, ns, key, options);
|
|
1092
1401
|
}
|
|
1093
|
-
getUsedParamsDetails(
|
|
1402
|
+
getUsedParamsDetails() {
|
|
1403
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
1094
1404
|
const optionsKeys = ['defaultValue', 'ordinal', 'context', 'replace', 'lng', 'lngs', 'fallbackLng', 'ns', 'keySeparator', 'nsSeparator', 'returnObjects', 'returnDetails', 'joinArrays', 'postProcess', 'interpolation'];
|
|
1095
1405
|
const useOptionsReplaceForData = options.replace && !isString(options.replace);
|
|
1096
1406
|
let data = useOptionsReplaceForData ? options.replace : options;
|
|
@@ -1124,6 +1434,7 @@ class Translator extends EventEmitter {
|
|
|
1124
1434
|
}
|
|
1125
1435
|
}
|
|
1126
1436
|
|
|
1437
|
+
const capitalize = string => string.charAt(0).toUpperCase() + string.slice(1);
|
|
1127
1438
|
class LanguageUtil {
|
|
1128
1439
|
constructor(options) {
|
|
1129
1440
|
this.options = options;
|
|
@@ -1147,18 +1458,31 @@ class LanguageUtil {
|
|
|
1147
1458
|
}
|
|
1148
1459
|
formatLanguageCode(code) {
|
|
1149
1460
|
if (isString(code) && code.indexOf('-') > -1) {
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1461
|
+
if (typeof Intl !== 'undefined' && typeof Intl.getCanonicalLocales !== 'undefined') {
|
|
1462
|
+
try {
|
|
1463
|
+
let formattedCode = Intl.getCanonicalLocales(code)[0];
|
|
1464
|
+
if (formattedCode && this.options.lowerCaseLng) {
|
|
1465
|
+
formattedCode = formattedCode.toLowerCase();
|
|
1466
|
+
}
|
|
1467
|
+
if (formattedCode) return formattedCode;
|
|
1468
|
+
} catch (e) {}
|
|
1156
1469
|
}
|
|
1157
|
-
|
|
1470
|
+
const specialCases = ['hans', 'hant', 'latn', 'cyrl', 'cans', 'mong', 'arab'];
|
|
1471
|
+
let p = code.split('-');
|
|
1158
1472
|
if (this.options.lowerCaseLng) {
|
|
1159
|
-
|
|
1473
|
+
p = p.map(part => part.toLowerCase());
|
|
1474
|
+
} else if (p.length === 2) {
|
|
1475
|
+
p[0] = p[0].toLowerCase();
|
|
1476
|
+
p[1] = p[1].toUpperCase();
|
|
1477
|
+
if (specialCases.indexOf(p[1].toLowerCase()) > -1) p[1] = capitalize(p[1].toLowerCase());
|
|
1478
|
+
} else if (p.length === 3) {
|
|
1479
|
+
p[0] = p[0].toLowerCase();
|
|
1480
|
+
if (p[1].length === 2) p[1] = p[1].toUpperCase();
|
|
1481
|
+
if (p[0] !== 'sgn' && p[2].length === 2) p[2] = p[2].toUpperCase();
|
|
1482
|
+
if (specialCases.indexOf(p[1].toLowerCase()) > -1) p[1] = capitalize(p[1].toLowerCase());
|
|
1483
|
+
if (specialCases.indexOf(p[2].toLowerCase()) > -1) p[2] = capitalize(p[2].toLowerCase());
|
|
1160
1484
|
}
|
|
1161
|
-
return
|
|
1485
|
+
return p.join('-');
|
|
1162
1486
|
}
|
|
1163
1487
|
return this.options.cleanCode || this.options.lowerCaseLng ? code.toLowerCase() : code;
|
|
1164
1488
|
}
|
|
@@ -1179,8 +1503,6 @@ class LanguageUtil {
|
|
|
1179
1503
|
if (!found && this.options.supportedLngs) {
|
|
1180
1504
|
codes.forEach(code => {
|
|
1181
1505
|
if (found) return;
|
|
1182
|
-
const lngScOnly = this.getScriptPartFromCode(code);
|
|
1183
|
-
if (this.isSupportedCode(lngScOnly)) return found = lngScOnly;
|
|
1184
1506
|
const lngOnly = this.getLanguagePartFromCode(code);
|
|
1185
1507
|
if (this.isSupportedCode(lngOnly)) return found = lngOnly;
|
|
1186
1508
|
found = this.options.supportedLngs.find(supportedLng => {
|
|
@@ -1208,7 +1530,7 @@ class LanguageUtil {
|
|
|
1208
1530
|
return found || [];
|
|
1209
1531
|
}
|
|
1210
1532
|
toResolveHierarchy(code, fallbackCode) {
|
|
1211
|
-
const fallbackCodes = this.getFallbackCodes(
|
|
1533
|
+
const fallbackCodes = this.getFallbackCodes(fallbackCode || this.options.fallbackLng || [], code);
|
|
1212
1534
|
const codes = [];
|
|
1213
1535
|
const addCode = c => {
|
|
1214
1536
|
if (!c) return;
|
|
@@ -1232,6 +1554,125 @@ class LanguageUtil {
|
|
|
1232
1554
|
}
|
|
1233
1555
|
}
|
|
1234
1556
|
|
|
1557
|
+
let sets = [{
|
|
1558
|
+
lngs: ['ach', 'ak', 'am', 'arn', 'br', 'fil', 'gun', 'ln', 'mfe', 'mg', 'mi', 'oc', 'pt', 'pt-BR', 'tg', 'tl', 'ti', 'tr', 'uz', 'wa'],
|
|
1559
|
+
nr: [1, 2],
|
|
1560
|
+
fc: 1
|
|
1561
|
+
}, {
|
|
1562
|
+
lngs: ['af', 'an', 'ast', 'az', 'bg', 'bn', 'ca', 'da', 'de', 'dev', 'el', 'en', 'eo', 'es', 'et', 'eu', 'fi', 'fo', 'fur', 'fy', 'gl', 'gu', 'ha', 'hi', 'hu', 'hy', 'ia', 'it', 'kk', 'kn', 'ku', 'lb', 'mai', 'ml', 'mn', 'mr', 'nah', 'nap', 'nb', 'ne', 'nl', 'nn', 'no', 'nso', 'pa', 'pap', 'pms', 'ps', 'pt-PT', 'rm', 'sco', 'se', 'si', 'so', 'son', 'sq', 'sv', 'sw', 'ta', 'te', 'tk', 'ur', 'yo'],
|
|
1563
|
+
nr: [1, 2],
|
|
1564
|
+
fc: 2
|
|
1565
|
+
}, {
|
|
1566
|
+
lngs: ['ay', 'bo', 'cgg', 'fa', 'ht', 'id', 'ja', 'jbo', 'ka', 'km', 'ko', 'ky', 'lo', 'ms', 'sah', 'su', 'th', 'tt', 'ug', 'vi', 'wo', 'zh'],
|
|
1567
|
+
nr: [1],
|
|
1568
|
+
fc: 3
|
|
1569
|
+
}, {
|
|
1570
|
+
lngs: ['be', 'bs', 'cnr', 'dz', 'hr', 'ru', 'sr', 'uk'],
|
|
1571
|
+
nr: [1, 2, 5],
|
|
1572
|
+
fc: 4
|
|
1573
|
+
}, {
|
|
1574
|
+
lngs: ['ar'],
|
|
1575
|
+
nr: [0, 1, 2, 3, 11, 100],
|
|
1576
|
+
fc: 5
|
|
1577
|
+
}, {
|
|
1578
|
+
lngs: ['cs', 'sk'],
|
|
1579
|
+
nr: [1, 2, 5],
|
|
1580
|
+
fc: 6
|
|
1581
|
+
}, {
|
|
1582
|
+
lngs: ['csb', 'pl'],
|
|
1583
|
+
nr: [1, 2, 5],
|
|
1584
|
+
fc: 7
|
|
1585
|
+
}, {
|
|
1586
|
+
lngs: ['cy'],
|
|
1587
|
+
nr: [1, 2, 3, 8],
|
|
1588
|
+
fc: 8
|
|
1589
|
+
}, {
|
|
1590
|
+
lngs: ['fr'],
|
|
1591
|
+
nr: [1, 2],
|
|
1592
|
+
fc: 9
|
|
1593
|
+
}, {
|
|
1594
|
+
lngs: ['ga'],
|
|
1595
|
+
nr: [1, 2, 3, 7, 11],
|
|
1596
|
+
fc: 10
|
|
1597
|
+
}, {
|
|
1598
|
+
lngs: ['gd'],
|
|
1599
|
+
nr: [1, 2, 3, 20],
|
|
1600
|
+
fc: 11
|
|
1601
|
+
}, {
|
|
1602
|
+
lngs: ['is'],
|
|
1603
|
+
nr: [1, 2],
|
|
1604
|
+
fc: 12
|
|
1605
|
+
}, {
|
|
1606
|
+
lngs: ['jv'],
|
|
1607
|
+
nr: [0, 1],
|
|
1608
|
+
fc: 13
|
|
1609
|
+
}, {
|
|
1610
|
+
lngs: ['kw'],
|
|
1611
|
+
nr: [1, 2, 3, 4],
|
|
1612
|
+
fc: 14
|
|
1613
|
+
}, {
|
|
1614
|
+
lngs: ['lt'],
|
|
1615
|
+
nr: [1, 2, 10],
|
|
1616
|
+
fc: 15
|
|
1617
|
+
}, {
|
|
1618
|
+
lngs: ['lv'],
|
|
1619
|
+
nr: [1, 2, 0],
|
|
1620
|
+
fc: 16
|
|
1621
|
+
}, {
|
|
1622
|
+
lngs: ['mk'],
|
|
1623
|
+
nr: [1, 2],
|
|
1624
|
+
fc: 17
|
|
1625
|
+
}, {
|
|
1626
|
+
lngs: ['mnk'],
|
|
1627
|
+
nr: [0, 1, 2],
|
|
1628
|
+
fc: 18
|
|
1629
|
+
}, {
|
|
1630
|
+
lngs: ['mt'],
|
|
1631
|
+
nr: [1, 2, 11, 20],
|
|
1632
|
+
fc: 19
|
|
1633
|
+
}, {
|
|
1634
|
+
lngs: ['or'],
|
|
1635
|
+
nr: [2, 1],
|
|
1636
|
+
fc: 2
|
|
1637
|
+
}, {
|
|
1638
|
+
lngs: ['ro'],
|
|
1639
|
+
nr: [1, 2, 20],
|
|
1640
|
+
fc: 20
|
|
1641
|
+
}, {
|
|
1642
|
+
lngs: ['sl'],
|
|
1643
|
+
nr: [5, 1, 2, 3],
|
|
1644
|
+
fc: 21
|
|
1645
|
+
}, {
|
|
1646
|
+
lngs: ['he', 'iw'],
|
|
1647
|
+
nr: [1, 2, 20, 21],
|
|
1648
|
+
fc: 22
|
|
1649
|
+
}];
|
|
1650
|
+
let _rulesPluralsTypes = {
|
|
1651
|
+
1: n => Number(n > 1),
|
|
1652
|
+
2: n => Number(n != 1),
|
|
1653
|
+
3: n => 0,
|
|
1654
|
+
4: n => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n % 10 >= 2 && n % 10 <= 4 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
|
|
1655
|
+
5: n => Number(n == 0 ? 0 : n == 1 ? 1 : n == 2 ? 2 : n % 100 >= 3 && n % 100 <= 10 ? 3 : n % 100 >= 11 ? 4 : 5),
|
|
1656
|
+
6: n => Number(n == 1 ? 0 : n >= 2 && n <= 4 ? 1 : 2),
|
|
1657
|
+
7: n => Number(n == 1 ? 0 : n % 10 >= 2 && n % 10 <= 4 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
|
|
1658
|
+
8: n => Number(n == 1 ? 0 : n == 2 ? 1 : n != 8 && n != 11 ? 2 : 3),
|
|
1659
|
+
9: n => Number(n >= 2),
|
|
1660
|
+
10: n => Number(n == 1 ? 0 : n == 2 ? 1 : n < 7 ? 2 : n < 11 ? 3 : 4),
|
|
1661
|
+
11: n => Number(n == 1 || n == 11 ? 0 : n == 2 || n == 12 ? 1 : n > 2 && n < 20 ? 2 : 3),
|
|
1662
|
+
12: n => Number(n % 10 != 1 || n % 100 == 11),
|
|
1663
|
+
13: n => Number(n !== 0),
|
|
1664
|
+
14: n => Number(n == 1 ? 0 : n == 2 ? 1 : n == 3 ? 2 : 3),
|
|
1665
|
+
15: n => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n % 10 >= 2 && (n % 100 < 10 || n % 100 >= 20) ? 1 : 2),
|
|
1666
|
+
16: n => Number(n % 10 == 1 && n % 100 != 11 ? 0 : n !== 0 ? 1 : 2),
|
|
1667
|
+
17: n => Number(n == 1 || n % 10 == 1 && n % 100 != 11 ? 0 : 1),
|
|
1668
|
+
18: n => Number(n == 0 ? 0 : n == 1 ? 1 : 2),
|
|
1669
|
+
19: n => Number(n == 1 ? 0 : n == 0 || n % 100 > 1 && n % 100 < 11 ? 1 : n % 100 > 10 && n % 100 < 20 ? 2 : 3),
|
|
1670
|
+
20: n => Number(n == 1 ? 0 : n == 0 || n % 100 > 0 && n % 100 < 20 ? 1 : 2),
|
|
1671
|
+
21: n => Number(n % 100 == 1 ? 1 : n % 100 == 2 ? 2 : n % 100 == 3 || n % 100 == 4 ? 3 : 0),
|
|
1672
|
+
22: n => Number(n == 1 ? 0 : n == 2 ? 1 : (n < 0 || n > 10) && n % 10 == 0 ? 2 : 3)
|
|
1673
|
+
};
|
|
1674
|
+
const nonIntlVersions = ['v1', 'v2', 'v3'];
|
|
1675
|
+
const intlVersions = ['v4'];
|
|
1235
1676
|
const suffixesOrder = {
|
|
1236
1677
|
zero: 0,
|
|
1237
1678
|
one: 1,
|
|
@@ -1240,74 +1681,129 @@ const suffixesOrder = {
|
|
|
1240
1681
|
many: 4,
|
|
1241
1682
|
other: 5
|
|
1242
1683
|
};
|
|
1243
|
-
const
|
|
1244
|
-
|
|
1245
|
-
|
|
1246
|
-
|
|
1247
|
-
|
|
1684
|
+
const createRules = () => {
|
|
1685
|
+
const rules = {};
|
|
1686
|
+
sets.forEach(set => {
|
|
1687
|
+
set.lngs.forEach(l => {
|
|
1688
|
+
rules[l] = {
|
|
1689
|
+
numbers: set.nr,
|
|
1690
|
+
plurals: _rulesPluralsTypes[set.fc]
|
|
1691
|
+
};
|
|
1692
|
+
});
|
|
1693
|
+
});
|
|
1694
|
+
return rules;
|
|
1248
1695
|
};
|
|
1249
1696
|
class PluralResolver {
|
|
1250
|
-
constructor(languageUtils
|
|
1697
|
+
constructor(languageUtils) {
|
|
1698
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
1251
1699
|
this.languageUtils = languageUtils;
|
|
1252
1700
|
this.options = options;
|
|
1253
1701
|
this.logger = baseLogger.create('pluralResolver');
|
|
1702
|
+
if ((!this.options.compatibilityJSON || intlVersions.includes(this.options.compatibilityJSON)) && (typeof Intl === 'undefined' || !Intl.PluralRules)) {
|
|
1703
|
+
this.options.compatibilityJSON = 'v3';
|
|
1704
|
+
this.logger.error('Your environment seems not to be Intl API compatible, use an Intl.PluralRules polyfill. Will fallback to the compatibilityJSON v3 format handling.');
|
|
1705
|
+
}
|
|
1706
|
+
this.rules = createRules();
|
|
1254
1707
|
this.pluralRulesCache = {};
|
|
1255
1708
|
}
|
|
1709
|
+
addRule(lng, obj) {
|
|
1710
|
+
this.rules[lng] = obj;
|
|
1711
|
+
}
|
|
1256
1712
|
clearCache() {
|
|
1257
1713
|
this.pluralRulesCache = {};
|
|
1258
1714
|
}
|
|
1259
|
-
getRule(code
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
if (cacheKey in this.pluralRulesCache) {
|
|
1267
|
-
return this.pluralRulesCache[cacheKey];
|
|
1268
|
-
}
|
|
1269
|
-
let rule;
|
|
1270
|
-
try {
|
|
1271
|
-
rule = new Intl.PluralRules(cleanedCode, {
|
|
1715
|
+
getRule(code) {
|
|
1716
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
1717
|
+
if (this.shouldUseIntlApi()) {
|
|
1718
|
+
const cleanedCode = getCleanedCode(code === 'dev' ? 'en' : code);
|
|
1719
|
+
const type = options.ordinal ? 'ordinal' : 'cardinal';
|
|
1720
|
+
const cacheKey = JSON.stringify({
|
|
1721
|
+
cleanedCode,
|
|
1272
1722
|
type
|
|
1273
1723
|
});
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1724
|
+
if (cacheKey in this.pluralRulesCache) {
|
|
1725
|
+
return this.pluralRulesCache[cacheKey];
|
|
1726
|
+
}
|
|
1727
|
+
let rule;
|
|
1728
|
+
try {
|
|
1729
|
+
rule = new Intl.PluralRules(cleanedCode, {
|
|
1730
|
+
type
|
|
1731
|
+
});
|
|
1732
|
+
} catch (err) {
|
|
1733
|
+
if (!code.match(/-|_/)) return;
|
|
1734
|
+
const lngPart = this.languageUtils.getLanguagePartFromCode(code);
|
|
1735
|
+
rule = this.getRule(lngPart, options);
|
|
1278
1736
|
}
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
rule = this.getRule(lngPart, options);
|
|
1737
|
+
this.pluralRulesCache[cacheKey] = rule;
|
|
1738
|
+
return rule;
|
|
1282
1739
|
}
|
|
1283
|
-
this.
|
|
1284
|
-
return rule;
|
|
1740
|
+
return this.rules[code] || this.rules[this.languageUtils.getLanguagePartFromCode(code)];
|
|
1285
1741
|
}
|
|
1286
|
-
needsPlural(code
|
|
1287
|
-
let
|
|
1288
|
-
|
|
1289
|
-
|
|
1742
|
+
needsPlural(code) {
|
|
1743
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
1744
|
+
const rule = this.getRule(code, options);
|
|
1745
|
+
if (this.shouldUseIntlApi()) {
|
|
1746
|
+
return rule && rule.resolvedOptions().pluralCategories.length > 1;
|
|
1747
|
+
}
|
|
1748
|
+
return rule && rule.numbers.length > 1;
|
|
1290
1749
|
}
|
|
1291
|
-
getPluralFormsOfKey(code, key
|
|
1750
|
+
getPluralFormsOfKey(code, key) {
|
|
1751
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
1292
1752
|
return this.getSuffixes(code, options).map(suffix => `${key}${suffix}`);
|
|
1293
1753
|
}
|
|
1294
|
-
getSuffixes(code
|
|
1295
|
-
let
|
|
1296
|
-
|
|
1297
|
-
if (!rule)
|
|
1298
|
-
|
|
1754
|
+
getSuffixes(code) {
|
|
1755
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
1756
|
+
const rule = this.getRule(code, options);
|
|
1757
|
+
if (!rule) {
|
|
1758
|
+
return [];
|
|
1759
|
+
}
|
|
1760
|
+
if (this.shouldUseIntlApi()) {
|
|
1761
|
+
return rule.resolvedOptions().pluralCategories.sort((pluralCategory1, pluralCategory2) => suffixesOrder[pluralCategory1] - suffixesOrder[pluralCategory2]).map(pluralCategory => `${this.options.prepend}${options.ordinal ? `ordinal${this.options.prepend}` : ''}${pluralCategory}`);
|
|
1762
|
+
}
|
|
1763
|
+
return rule.numbers.map(number => this.getSuffix(code, number, options));
|
|
1299
1764
|
}
|
|
1300
|
-
getSuffix(code, count
|
|
1765
|
+
getSuffix(code, count) {
|
|
1766
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
1301
1767
|
const rule = this.getRule(code, options);
|
|
1302
1768
|
if (rule) {
|
|
1303
|
-
|
|
1769
|
+
if (this.shouldUseIntlApi()) {
|
|
1770
|
+
return `${this.options.prepend}${options.ordinal ? `ordinal${this.options.prepend}` : ''}${rule.select(count)}`;
|
|
1771
|
+
}
|
|
1772
|
+
return this.getSuffixRetroCompatible(rule, count);
|
|
1304
1773
|
}
|
|
1305
1774
|
this.logger.warn(`no plural rule found for: ${code}`);
|
|
1306
|
-
return
|
|
1775
|
+
return '';
|
|
1776
|
+
}
|
|
1777
|
+
getSuffixRetroCompatible(rule, count) {
|
|
1778
|
+
const idx = rule.noAbs ? rule.plurals(count) : rule.plurals(Math.abs(count));
|
|
1779
|
+
let suffix = rule.numbers[idx];
|
|
1780
|
+
if (this.options.simplifyPluralSuffix && rule.numbers.length === 2 && rule.numbers[0] === 1) {
|
|
1781
|
+
if (suffix === 2) {
|
|
1782
|
+
suffix = 'plural';
|
|
1783
|
+
} else if (suffix === 1) {
|
|
1784
|
+
suffix = '';
|
|
1785
|
+
}
|
|
1786
|
+
}
|
|
1787
|
+
const returnSuffix = () => this.options.prepend && suffix.toString() ? this.options.prepend + suffix.toString() : suffix.toString();
|
|
1788
|
+
if (this.options.compatibilityJSON === 'v1') {
|
|
1789
|
+
if (suffix === 1) return '';
|
|
1790
|
+
if (typeof suffix === 'number') return `_plural_${suffix.toString()}`;
|
|
1791
|
+
return returnSuffix();
|
|
1792
|
+
} else if (this.options.compatibilityJSON === 'v2') {
|
|
1793
|
+
return returnSuffix();
|
|
1794
|
+
} else if (this.options.simplifyPluralSuffix && rule.numbers.length === 2 && rule.numbers[0] === 1) {
|
|
1795
|
+
return returnSuffix();
|
|
1796
|
+
}
|
|
1797
|
+
return this.options.prepend && idx.toString() ? this.options.prepend + idx.toString() : idx.toString();
|
|
1798
|
+
}
|
|
1799
|
+
shouldUseIntlApi() {
|
|
1800
|
+
return !nonIntlVersions.includes(this.options.compatibilityJSON);
|
|
1307
1801
|
}
|
|
1308
1802
|
}
|
|
1309
1803
|
|
|
1310
|
-
const deepFindWithDefaults = (data, defaultData, key
|
|
1804
|
+
const deepFindWithDefaults = function (data, defaultData, key) {
|
|
1805
|
+
let keySeparator = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : '.';
|
|
1806
|
+
let ignoreJSONStructure = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : true;
|
|
1311
1807
|
let path = getPathWithDefaults(data, defaultData, key);
|
|
1312
1808
|
if (!path && ignoreJSONStructure && isString(key)) {
|
|
1313
1809
|
path = deepFind(data, key, keySeparator);
|
|
@@ -1317,13 +1813,15 @@ const deepFindWithDefaults = (data, defaultData, key, keySeparator = '.', ignore
|
|
|
1317
1813
|
};
|
|
1318
1814
|
const regexSafe = val => val.replace(/\$/g, '$$$$');
|
|
1319
1815
|
class Interpolator {
|
|
1320
|
-
constructor(
|
|
1816
|
+
constructor() {
|
|
1817
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
1321
1818
|
this.logger = baseLogger.create('interpolator');
|
|
1322
1819
|
this.options = options;
|
|
1323
|
-
this.format = options
|
|
1820
|
+
this.format = options.interpolation && options.interpolation.format || (value => value);
|
|
1324
1821
|
this.init(options);
|
|
1325
1822
|
}
|
|
1326
|
-
init(
|
|
1823
|
+
init() {
|
|
1824
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
1327
1825
|
if (!options.interpolation) options.interpolation = {
|
|
1328
1826
|
escapeValue: true
|
|
1329
1827
|
};
|
|
@@ -1366,7 +1864,7 @@ class Interpolator {
|
|
|
1366
1864
|
}
|
|
1367
1865
|
resetRegExp() {
|
|
1368
1866
|
const getOrResetRegExp = (existingRegExp, pattern) => {
|
|
1369
|
-
if (existingRegExp
|
|
1867
|
+
if (existingRegExp && existingRegExp.source === pattern) {
|
|
1370
1868
|
existingRegExp.lastIndex = 0;
|
|
1371
1869
|
return existingRegExp;
|
|
1372
1870
|
}
|
|
@@ -1374,7 +1872,7 @@ class Interpolator {
|
|
|
1374
1872
|
};
|
|
1375
1873
|
this.regexp = getOrResetRegExp(this.regexp, `${this.prefix}(.+?)${this.suffix}`);
|
|
1376
1874
|
this.regexpUnescape = getOrResetRegExp(this.regexpUnescape, `${this.prefix}${this.unescapePrefix}(.+?)${this.unescapeSuffix}${this.suffix}`);
|
|
1377
|
-
this.nestingRegexp = getOrResetRegExp(this.nestingRegexp, `${this.nestingPrefix}(
|
|
1875
|
+
this.nestingRegexp = getOrResetRegExp(this.nestingRegexp, `${this.nestingPrefix}(.+?)${this.nestingSuffix}`);
|
|
1378
1876
|
}
|
|
1379
1877
|
interpolate(str, data, lng, options) {
|
|
1380
1878
|
let match;
|
|
@@ -1400,8 +1898,8 @@ class Interpolator {
|
|
|
1400
1898
|
});
|
|
1401
1899
|
};
|
|
1402
1900
|
this.resetRegExp();
|
|
1403
|
-
const missingInterpolationHandler = options
|
|
1404
|
-
const skipOnVariables = options
|
|
1901
|
+
const missingInterpolationHandler = options && options.missingInterpolationHandler || this.options.missingInterpolationHandler;
|
|
1902
|
+
const skipOnVariables = options && options.interpolation && options.interpolation.skipOnVariables !== undefined ? options.interpolation.skipOnVariables : this.options.interpolation.skipOnVariables;
|
|
1405
1903
|
const todos = [{
|
|
1406
1904
|
regex: this.regexpUnescape,
|
|
1407
1905
|
safeValue: val => regexSafe(val)
|
|
@@ -1446,20 +1944,21 @@ class Interpolator {
|
|
|
1446
1944
|
});
|
|
1447
1945
|
return str;
|
|
1448
1946
|
}
|
|
1449
|
-
nest(str, fc
|
|
1947
|
+
nest(str, fc) {
|
|
1948
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
1450
1949
|
let match;
|
|
1451
1950
|
let value;
|
|
1452
1951
|
let clonedOptions;
|
|
1453
1952
|
const handleHasOptions = (key, inheritedOptions) => {
|
|
1454
1953
|
const sep = this.nestingOptionsSeparator;
|
|
1455
1954
|
if (key.indexOf(sep) < 0) return key;
|
|
1456
|
-
const c = key.split(new RegExp(`${
|
|
1955
|
+
const c = key.split(new RegExp(`${sep}[ ]*{`));
|
|
1457
1956
|
let optionsString = `{${c[1]}`;
|
|
1458
1957
|
key = c[0];
|
|
1459
1958
|
optionsString = this.interpolate(optionsString, clonedOptions);
|
|
1460
1959
|
const matchedSingleQuotes = optionsString.match(/'/g);
|
|
1461
1960
|
const matchedDoubleQuotes = optionsString.match(/"/g);
|
|
1462
|
-
if (
|
|
1961
|
+
if (matchedSingleQuotes && matchedSingleQuotes.length % 2 === 0 && !matchedDoubleQuotes || matchedDoubleQuotes.length % 2 !== 0) {
|
|
1463
1962
|
optionsString = optionsString.replace(/'/g, '"');
|
|
1464
1963
|
}
|
|
1465
1964
|
try {
|
|
@@ -1483,10 +1982,12 @@ class Interpolator {
|
|
|
1483
1982
|
clonedOptions = clonedOptions.replace && !isString(clonedOptions.replace) ? clonedOptions.replace : clonedOptions;
|
|
1484
1983
|
clonedOptions.applyPostProcessor = false;
|
|
1485
1984
|
delete clonedOptions.defaultValue;
|
|
1486
|
-
|
|
1487
|
-
if (
|
|
1488
|
-
|
|
1489
|
-
match[1] =
|
|
1985
|
+
let doReduce = false;
|
|
1986
|
+
if (match[0].indexOf(this.formatSeparator) !== -1 && !/{.*}/.test(match[1])) {
|
|
1987
|
+
const r = match[1].split(this.formatSeparator).map(elem => elem.trim());
|
|
1988
|
+
match[1] = r.shift();
|
|
1989
|
+
formatters = r;
|
|
1990
|
+
doReduce = true;
|
|
1490
1991
|
}
|
|
1491
1992
|
value = fc(handleHasOptions.call(this, match[1].trim(), clonedOptions), clonedOptions);
|
|
1492
1993
|
if (value && match[0] === str && !isString(value)) return value;
|
|
@@ -1495,7 +1996,7 @@ class Interpolator {
|
|
|
1495
1996
|
this.logger.warn(`missed to resolve ${match[1]} for nesting ${str}`);
|
|
1496
1997
|
value = '';
|
|
1497
1998
|
}
|
|
1498
|
-
if (
|
|
1999
|
+
if (doReduce) {
|
|
1499
2000
|
value = formatters.reduce((v, f) => this.format(v, f, options.lng, {
|
|
1500
2001
|
...options,
|
|
1501
2002
|
interpolationkey: match[1].trim()
|
|
@@ -1541,68 +2042,68 @@ const parseFormatStr = formatStr => {
|
|
|
1541
2042
|
};
|
|
1542
2043
|
const createCachedFormatter = fn => {
|
|
1543
2044
|
const cache = {};
|
|
1544
|
-
return (
|
|
1545
|
-
let optForCache =
|
|
1546
|
-
if (
|
|
2045
|
+
return (val, lng, options) => {
|
|
2046
|
+
let optForCache = options;
|
|
2047
|
+
if (options && options.interpolationkey && options.formatParams && options.formatParams[options.interpolationkey] && options[options.interpolationkey]) {
|
|
1547
2048
|
optForCache = {
|
|
1548
2049
|
...optForCache,
|
|
1549
|
-
[
|
|
2050
|
+
[options.interpolationkey]: undefined
|
|
1550
2051
|
};
|
|
1551
2052
|
}
|
|
1552
|
-
const key =
|
|
1553
|
-
let
|
|
1554
|
-
if (!
|
|
1555
|
-
|
|
1556
|
-
cache[key] =
|
|
2053
|
+
const key = lng + JSON.stringify(optForCache);
|
|
2054
|
+
let formatter = cache[key];
|
|
2055
|
+
if (!formatter) {
|
|
2056
|
+
formatter = fn(getCleanedCode(lng), options);
|
|
2057
|
+
cache[key] = formatter;
|
|
1557
2058
|
}
|
|
1558
|
-
return
|
|
2059
|
+
return formatter(val);
|
|
1559
2060
|
};
|
|
1560
2061
|
};
|
|
1561
|
-
const createNonCachedFormatter = fn => (v, l, o) => fn(getCleanedCode(l), o)(v);
|
|
1562
2062
|
class Formatter {
|
|
1563
|
-
constructor(
|
|
2063
|
+
constructor() {
|
|
2064
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
1564
2065
|
this.logger = baseLogger.create('formatter');
|
|
1565
2066
|
this.options = options;
|
|
1566
|
-
this.init(options);
|
|
1567
|
-
}
|
|
1568
|
-
init(services, options = {
|
|
1569
|
-
interpolation: {}
|
|
1570
|
-
}) {
|
|
1571
|
-
this.formatSeparator = options.interpolation.formatSeparator || ',';
|
|
1572
|
-
const cf = options.cacheInBuiltFormats ? createCachedFormatter : createNonCachedFormatter;
|
|
1573
2067
|
this.formats = {
|
|
1574
|
-
number:
|
|
2068
|
+
number: createCachedFormatter((lng, opt) => {
|
|
1575
2069
|
const formatter = new Intl.NumberFormat(lng, {
|
|
1576
2070
|
...opt
|
|
1577
2071
|
});
|
|
1578
2072
|
return val => formatter.format(val);
|
|
1579
2073
|
}),
|
|
1580
|
-
currency:
|
|
2074
|
+
currency: createCachedFormatter((lng, opt) => {
|
|
1581
2075
|
const formatter = new Intl.NumberFormat(lng, {
|
|
1582
2076
|
...opt,
|
|
1583
2077
|
style: 'currency'
|
|
1584
2078
|
});
|
|
1585
2079
|
return val => formatter.format(val);
|
|
1586
2080
|
}),
|
|
1587
|
-
datetime:
|
|
2081
|
+
datetime: createCachedFormatter((lng, opt) => {
|
|
1588
2082
|
const formatter = new Intl.DateTimeFormat(lng, {
|
|
1589
2083
|
...opt
|
|
1590
2084
|
});
|
|
1591
2085
|
return val => formatter.format(val);
|
|
1592
2086
|
}),
|
|
1593
|
-
relativetime:
|
|
2087
|
+
relativetime: createCachedFormatter((lng, opt) => {
|
|
1594
2088
|
const formatter = new Intl.RelativeTimeFormat(lng, {
|
|
1595
2089
|
...opt
|
|
1596
2090
|
});
|
|
1597
2091
|
return val => formatter.format(val, opt.range || 'day');
|
|
1598
2092
|
}),
|
|
1599
|
-
list:
|
|
2093
|
+
list: createCachedFormatter((lng, opt) => {
|
|
1600
2094
|
const formatter = new Intl.ListFormat(lng, {
|
|
1601
2095
|
...opt
|
|
1602
2096
|
});
|
|
1603
2097
|
return val => formatter.format(val);
|
|
1604
2098
|
})
|
|
1605
2099
|
};
|
|
2100
|
+
this.init(options);
|
|
2101
|
+
}
|
|
2102
|
+
init(services) {
|
|
2103
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {
|
|
2104
|
+
interpolation: {}
|
|
2105
|
+
};
|
|
2106
|
+
this.formatSeparator = options.interpolation.formatSeparator || ',';
|
|
1606
2107
|
}
|
|
1607
2108
|
add(name, fc) {
|
|
1608
2109
|
this.formats[name.toLowerCase().trim()] = fc;
|
|
@@ -1610,7 +2111,8 @@ class Formatter {
|
|
|
1610
2111
|
addCached(name, fc) {
|
|
1611
2112
|
this.formats[name.toLowerCase().trim()] = createCachedFormatter(fc);
|
|
1612
2113
|
}
|
|
1613
|
-
format(value, format, lng
|
|
2114
|
+
format(value, format, lng) {
|
|
2115
|
+
let options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {};
|
|
1614
2116
|
const formats = format.split(this.formatSeparator);
|
|
1615
2117
|
if (formats.length > 1 && formats[0].indexOf('(') > 1 && formats[0].indexOf(')') < 0 && formats.find(f => f.indexOf(')') > -1)) {
|
|
1616
2118
|
const lastIndex = formats.findIndex(f => f.indexOf(')') > -1);
|
|
@@ -1624,7 +2126,7 @@ class Formatter {
|
|
|
1624
2126
|
if (this.formats[formatName]) {
|
|
1625
2127
|
let formatted = mem;
|
|
1626
2128
|
try {
|
|
1627
|
-
const valOptions = options
|
|
2129
|
+
const valOptions = options && options.formatParams && options.formatParams[options.interpolationkey] || {};
|
|
1628
2130
|
const l = valOptions.locale || valOptions.lng || options.locale || options.lng || lng;
|
|
1629
2131
|
formatted = this.formats[formatName](mem, l, {
|
|
1630
2132
|
...formatOptions,
|
|
@@ -1651,7 +2153,8 @@ const removePending = (q, name) => {
|
|
|
1651
2153
|
}
|
|
1652
2154
|
};
|
|
1653
2155
|
class Connector extends EventEmitter {
|
|
1654
|
-
constructor(backend, store, services
|
|
2156
|
+
constructor(backend, store, services) {
|
|
2157
|
+
let options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {};
|
|
1655
2158
|
super();
|
|
1656
2159
|
this.backend = backend;
|
|
1657
2160
|
this.store = store;
|
|
@@ -1666,7 +2169,9 @@ class Connector extends EventEmitter {
|
|
|
1666
2169
|
this.retryTimeout = options.retryTimeout >= 1 ? options.retryTimeout : 350;
|
|
1667
2170
|
this.state = {};
|
|
1668
2171
|
this.queue = [];
|
|
1669
|
-
this.backend
|
|
2172
|
+
if (this.backend && this.backend.init) {
|
|
2173
|
+
this.backend.init(services, options.backend, options);
|
|
2174
|
+
}
|
|
1670
2175
|
}
|
|
1671
2176
|
queueLoad(languages, namespaces, options, callback) {
|
|
1672
2177
|
const toLoad = {};
|
|
@@ -1745,7 +2250,10 @@ class Connector extends EventEmitter {
|
|
|
1745
2250
|
this.emit('loaded', loaded);
|
|
1746
2251
|
this.queue = this.queue.filter(q => !q.done);
|
|
1747
2252
|
}
|
|
1748
|
-
read(lng, ns, fcName
|
|
2253
|
+
read(lng, ns, fcName) {
|
|
2254
|
+
let tried = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 0;
|
|
2255
|
+
let wait = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : this.retryTimeout;
|
|
2256
|
+
let callback = arguments.length > 5 ? arguments[5] : undefined;
|
|
1749
2257
|
if (!lng.length) return callback(null, {});
|
|
1750
2258
|
if (this.readingCalls >= this.maxParallelReads) {
|
|
1751
2259
|
this.waitingReads.push({
|
|
@@ -1789,7 +2297,9 @@ class Connector extends EventEmitter {
|
|
|
1789
2297
|
}
|
|
1790
2298
|
return fc(lng, ns, resolver);
|
|
1791
2299
|
}
|
|
1792
|
-
prepareLoading(languages, namespaces
|
|
2300
|
+
prepareLoading(languages, namespaces) {
|
|
2301
|
+
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
2302
|
+
let callback = arguments.length > 3 ? arguments[3] : undefined;
|
|
1793
2303
|
if (!this.backend) {
|
|
1794
2304
|
this.logger.warn('No backend was added via i18next.use. Will not load resources.');
|
|
1795
2305
|
return callback && callback();
|
|
@@ -1813,7 +2323,8 @@ class Connector extends EventEmitter {
|
|
|
1813
2323
|
reload: true
|
|
1814
2324
|
}, callback);
|
|
1815
2325
|
}
|
|
1816
|
-
loadOne(name
|
|
2326
|
+
loadOne(name) {
|
|
2327
|
+
let prefix = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : '';
|
|
1817
2328
|
const s = name.split('|');
|
|
1818
2329
|
const lng = s[0];
|
|
1819
2330
|
const ns = s[1];
|
|
@@ -1823,13 +2334,15 @@ class Connector extends EventEmitter {
|
|
|
1823
2334
|
this.loaded(name, err, data);
|
|
1824
2335
|
});
|
|
1825
2336
|
}
|
|
1826
|
-
saveMissing(languages, namespace, key, fallbackValue, isUpdate
|
|
1827
|
-
|
|
2337
|
+
saveMissing(languages, namespace, key, fallbackValue, isUpdate) {
|
|
2338
|
+
let options = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : {};
|
|
2339
|
+
let clb = arguments.length > 6 && arguments[6] !== undefined ? arguments[6] : () => {};
|
|
2340
|
+
if (this.services.utils && this.services.utils.hasLoadedNamespace && !this.services.utils.hasLoadedNamespace(namespace)) {
|
|
1828
2341
|
this.logger.warn(`did not save key "${key}" as the namespace "${namespace}" was not yet loaded`, 'This means something IS WRONG in your setup. You access the t function before i18next.init / i18next.loadNamespace / i18next.changeLanguage was done. Wait for the callback or Promise to resolve before accessing it!!!');
|
|
1829
2342
|
return;
|
|
1830
2343
|
}
|
|
1831
2344
|
if (key === undefined || key === null || key === '') return;
|
|
1832
|
-
if (this.backend
|
|
2345
|
+
if (this.backend && this.backend.create) {
|
|
1833
2346
|
const opts = {
|
|
1834
2347
|
...options,
|
|
1835
2348
|
isUpdate
|
|
@@ -1862,7 +2375,7 @@ class Connector extends EventEmitter {
|
|
|
1862
2375
|
|
|
1863
2376
|
const get = () => ({
|
|
1864
2377
|
debug: false,
|
|
1865
|
-
|
|
2378
|
+
initImmediate: true,
|
|
1866
2379
|
ns: ['translation'],
|
|
1867
2380
|
defaultNS: ['translation'],
|
|
1868
2381
|
fallbackLng: ['dev'],
|
|
@@ -1918,17 +2431,15 @@ const get = () => ({
|
|
|
1918
2431
|
nestingOptionsSeparator: ',',
|
|
1919
2432
|
maxReplaces: 1000,
|
|
1920
2433
|
skipOnVariables: true
|
|
1921
|
-
}
|
|
1922
|
-
cacheInBuiltFormats: true
|
|
2434
|
+
}
|
|
1923
2435
|
});
|
|
1924
2436
|
const transformOptions = options => {
|
|
1925
2437
|
if (isString(options.ns)) options.ns = [options.ns];
|
|
1926
2438
|
if (isString(options.fallbackLng)) options.fallbackLng = [options.fallbackLng];
|
|
1927
2439
|
if (isString(options.fallbackNS)) options.fallbackNS = [options.fallbackNS];
|
|
1928
|
-
if (options.supportedLngs
|
|
2440
|
+
if (options.supportedLngs && options.supportedLngs.indexOf('cimode') < 0) {
|
|
1929
2441
|
options.supportedLngs = options.supportedLngs.concat(['cimode']);
|
|
1930
2442
|
}
|
|
1931
|
-
if (typeof options.initImmediate === 'boolean') options.initAsync = options.initImmediate;
|
|
1932
2443
|
return options;
|
|
1933
2444
|
};
|
|
1934
2445
|
|
|
@@ -1941,17 +2452,10 @@ const bindMemberFunctions = inst => {
|
|
|
1941
2452
|
}
|
|
1942
2453
|
});
|
|
1943
2454
|
};
|
|
1944
|
-
let supportNoticeShown = false;
|
|
1945
|
-
const usesLocize = inst => {
|
|
1946
|
-
if (inst?.modules?.backend?.name?.indexOf('Locize') > 0) return true;
|
|
1947
|
-
if (inst?.modules?.backend?.constructor?.name?.indexOf('Locize') > 0) return true;
|
|
1948
|
-
if (inst?.options?.backend?.backends) {
|
|
1949
|
-
if (inst.options.backend.backends.some(b => b?.name?.indexOf('Locize') > 0 || b?.constructor?.name?.indexOf('Locize') > 0)) return true;
|
|
1950
|
-
}
|
|
1951
|
-
return false;
|
|
1952
|
-
};
|
|
1953
2455
|
class I18n extends EventEmitter {
|
|
1954
|
-
constructor(
|
|
2456
|
+
constructor() {
|
|
2457
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
2458
|
+
let callback = arguments.length > 1 ? arguments[1] : undefined;
|
|
1955
2459
|
super();
|
|
1956
2460
|
this.options = transformOptions(options);
|
|
1957
2461
|
this.services = {};
|
|
@@ -1961,7 +2465,7 @@ class I18n extends EventEmitter {
|
|
|
1961
2465
|
};
|
|
1962
2466
|
bindMemberFunctions(this);
|
|
1963
2467
|
if (callback && !this.isInitialized && !options.isClone) {
|
|
1964
|
-
if (!this.options.
|
|
2468
|
+
if (!this.options.initImmediate) {
|
|
1965
2469
|
this.init(options, callback);
|
|
1966
2470
|
return this;
|
|
1967
2471
|
}
|
|
@@ -1970,13 +2474,16 @@ class I18n extends EventEmitter {
|
|
|
1970
2474
|
}, 0);
|
|
1971
2475
|
}
|
|
1972
2476
|
}
|
|
1973
|
-
init(
|
|
2477
|
+
init() {
|
|
2478
|
+
var _this = this;
|
|
2479
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
2480
|
+
let callback = arguments.length > 1 ? arguments[1] : undefined;
|
|
1974
2481
|
this.isInitializing = true;
|
|
1975
2482
|
if (typeof options === 'function') {
|
|
1976
2483
|
callback = options;
|
|
1977
2484
|
options = {};
|
|
1978
2485
|
}
|
|
1979
|
-
if (options.defaultNS
|
|
2486
|
+
if (!options.defaultNS && options.defaultNS !== false && options.ns) {
|
|
1980
2487
|
if (isString(options.ns)) {
|
|
1981
2488
|
options.defaultNS = options.ns;
|
|
1982
2489
|
} else if (options.ns.indexOf('translation') < 0) {
|
|
@@ -1989,23 +2496,18 @@ class I18n extends EventEmitter {
|
|
|
1989
2496
|
...this.options,
|
|
1990
2497
|
...transformOptions(options)
|
|
1991
2498
|
};
|
|
1992
|
-
this.options.
|
|
1993
|
-
|
|
1994
|
-
|
|
1995
|
-
|
|
2499
|
+
if (this.options.compatibilityAPI !== 'v1') {
|
|
2500
|
+
this.options.interpolation = {
|
|
2501
|
+
...defOpts.interpolation,
|
|
2502
|
+
...this.options.interpolation
|
|
2503
|
+
};
|
|
2504
|
+
}
|
|
1996
2505
|
if (options.keySeparator !== undefined) {
|
|
1997
2506
|
this.options.userDefinedKeySeparator = options.keySeparator;
|
|
1998
2507
|
}
|
|
1999
2508
|
if (options.nsSeparator !== undefined) {
|
|
2000
2509
|
this.options.userDefinedNsSeparator = options.nsSeparator;
|
|
2001
2510
|
}
|
|
2002
|
-
if (typeof this.options.overloadTranslationOptionHandler !== 'function') {
|
|
2003
|
-
this.options.overloadTranslationOptionHandler = defOpts.overloadTranslationOptionHandler;
|
|
2004
|
-
}
|
|
2005
|
-
if (this.options.showSupportNotice !== false && !usesLocize(this) && !supportNoticeShown) {
|
|
2006
|
-
if (typeof console !== 'undefined' && typeof console.info !== 'undefined') console.info('🌐 i18next is maintained with support from Locize — consider powering your project with managed localization (AI, CDN, integrations): https://locize.com 💙');
|
|
2007
|
-
supportNoticeShown = true;
|
|
2008
|
-
}
|
|
2009
2511
|
const createClassOnDemand = ClassOrObject => {
|
|
2010
2512
|
if (!ClassOrObject) return null;
|
|
2011
2513
|
if (typeof ClassOrObject === 'function') return new ClassOrObject();
|
|
@@ -2020,7 +2522,7 @@ class I18n extends EventEmitter {
|
|
|
2020
2522
|
let formatter;
|
|
2021
2523
|
if (this.modules.formatter) {
|
|
2022
2524
|
formatter = this.modules.formatter;
|
|
2023
|
-
} else {
|
|
2525
|
+
} else if (typeof Intl !== 'undefined') {
|
|
2024
2526
|
formatter = Formatter;
|
|
2025
2527
|
}
|
|
2026
2528
|
const lu = new LanguageUtil(this.options);
|
|
@@ -2031,15 +2533,12 @@ class I18n extends EventEmitter {
|
|
|
2031
2533
|
s.languageUtils = lu;
|
|
2032
2534
|
s.pluralResolver = new PluralResolver(lu, {
|
|
2033
2535
|
prepend: this.options.pluralSeparator,
|
|
2536
|
+
compatibilityJSON: this.options.compatibilityJSON,
|
|
2034
2537
|
simplifyPluralSuffix: this.options.simplifyPluralSuffix
|
|
2035
2538
|
});
|
|
2036
|
-
const usingLegacyFormatFunction = this.options.interpolation.format && this.options.interpolation.format !== defOpts.interpolation.format;
|
|
2037
|
-
if (usingLegacyFormatFunction) {
|
|
2038
|
-
this.logger.deprecate(`init: you are still using the legacy format function, please use the new approach: https://www.i18next.com/translation-function/formatting`);
|
|
2039
|
-
}
|
|
2040
2539
|
if (formatter && (!this.options.interpolation.format || this.options.interpolation.format === defOpts.interpolation.format)) {
|
|
2041
2540
|
s.formatter = createClassOnDemand(formatter);
|
|
2042
|
-
|
|
2541
|
+
s.formatter.init(s, this.options);
|
|
2043
2542
|
this.options.interpolation.format = s.formatter.format.bind(s.formatter);
|
|
2044
2543
|
}
|
|
2045
2544
|
s.interpolator = new Interpolator(this.options);
|
|
@@ -2047,8 +2546,11 @@ class I18n extends EventEmitter {
|
|
|
2047
2546
|
hasLoadedNamespace: this.hasLoadedNamespace.bind(this)
|
|
2048
2547
|
};
|
|
2049
2548
|
s.backendConnector = new Connector(createClassOnDemand(this.modules.backend), s.resourceStore, s, this.options);
|
|
2050
|
-
s.backendConnector.on('*', (event
|
|
2051
|
-
|
|
2549
|
+
s.backendConnector.on('*', function (event) {
|
|
2550
|
+
for (var _len = arguments.length, args = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
|
|
2551
|
+
args[_key - 1] = arguments[_key];
|
|
2552
|
+
}
|
|
2553
|
+
_this.emit(event, ...args);
|
|
2052
2554
|
});
|
|
2053
2555
|
if (this.modules.languageDetector) {
|
|
2054
2556
|
s.languageDetector = createClassOnDemand(this.modules.languageDetector);
|
|
@@ -2059,8 +2561,11 @@ class I18n extends EventEmitter {
|
|
|
2059
2561
|
if (s.i18nFormat.init) s.i18nFormat.init(this);
|
|
2060
2562
|
}
|
|
2061
2563
|
this.translator = new Translator(this.services, this.options);
|
|
2062
|
-
this.translator.on('*', (event
|
|
2063
|
-
|
|
2564
|
+
this.translator.on('*', function (event) {
|
|
2565
|
+
for (var _len2 = arguments.length, args = new Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {
|
|
2566
|
+
args[_key2 - 1] = arguments[_key2];
|
|
2567
|
+
}
|
|
2568
|
+
_this.emit(event, ...args);
|
|
2064
2569
|
});
|
|
2065
2570
|
this.modules.external.forEach(m => {
|
|
2066
2571
|
if (m.init) m.init(this);
|
|
@@ -2077,13 +2582,15 @@ class I18n extends EventEmitter {
|
|
|
2077
2582
|
}
|
|
2078
2583
|
const storeApi = ['getResource', 'hasResourceBundle', 'getResourceBundle', 'getDataByLanguage'];
|
|
2079
2584
|
storeApi.forEach(fcName => {
|
|
2080
|
-
this[fcName] = (
|
|
2585
|
+
this[fcName] = function () {
|
|
2586
|
+
return _this.store[fcName](...arguments);
|
|
2587
|
+
};
|
|
2081
2588
|
});
|
|
2082
2589
|
const storeApiChained = ['addResource', 'addResources', 'addResourceBundle', 'removeResourceBundle'];
|
|
2083
2590
|
storeApiChained.forEach(fcName => {
|
|
2084
|
-
this[fcName] = (
|
|
2085
|
-
|
|
2086
|
-
return
|
|
2591
|
+
this[fcName] = function () {
|
|
2592
|
+
_this.store[fcName](...arguments);
|
|
2593
|
+
return _this;
|
|
2087
2594
|
};
|
|
2088
2595
|
});
|
|
2089
2596
|
const deferred = defer();
|
|
@@ -2097,22 +2604,23 @@ class I18n extends EventEmitter {
|
|
|
2097
2604
|
deferred.resolve(t);
|
|
2098
2605
|
callback(err, t);
|
|
2099
2606
|
};
|
|
2100
|
-
if (this.languages && !this.isInitialized) return finish(null, this.t.bind(this));
|
|
2607
|
+
if (this.languages && this.options.compatibilityAPI !== 'v1' && !this.isInitialized) return finish(null, this.t.bind(this));
|
|
2101
2608
|
this.changeLanguage(this.options.lng, finish);
|
|
2102
2609
|
};
|
|
2103
|
-
if (this.options.resources || !this.options.
|
|
2610
|
+
if (this.options.resources || !this.options.initImmediate) {
|
|
2104
2611
|
load();
|
|
2105
2612
|
} else {
|
|
2106
2613
|
setTimeout(load, 0);
|
|
2107
2614
|
}
|
|
2108
2615
|
return deferred;
|
|
2109
2616
|
}
|
|
2110
|
-
loadResources(language
|
|
2617
|
+
loadResources(language) {
|
|
2618
|
+
let callback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : noop;
|
|
2111
2619
|
let usedCallback = callback;
|
|
2112
2620
|
const usedLng = isString(language) ? language : this.language;
|
|
2113
2621
|
if (typeof language === 'function') usedCallback = language;
|
|
2114
2622
|
if (!this.options.resources || this.options.partialBundledLanguages) {
|
|
2115
|
-
if (usedLng
|
|
2623
|
+
if (usedLng && usedLng.toLowerCase() === 'cimode' && (!this.options.preload || this.options.preload.length === 0)) return usedCallback();
|
|
2116
2624
|
const toLoad = [];
|
|
2117
2625
|
const append = lng => {
|
|
2118
2626
|
if (!lng) return;
|
|
@@ -2129,7 +2637,9 @@ class I18n extends EventEmitter {
|
|
|
2129
2637
|
} else {
|
|
2130
2638
|
append(usedLng);
|
|
2131
2639
|
}
|
|
2132
|
-
this.options.preload
|
|
2640
|
+
if (this.options.preload) {
|
|
2641
|
+
this.options.preload.forEach(l => append(l));
|
|
2642
|
+
}
|
|
2133
2643
|
this.services.backendConnector.load(toLoad, this.options.ns, e => {
|
|
2134
2644
|
if (!e && !this.resolvedLanguage && this.language) this.setResolvedLanguage(this.language);
|
|
2135
2645
|
usedCallback(e);
|
|
@@ -2194,542 +2704,249 @@ class I18n extends EventEmitter {
|
|
|
2194
2704
|
break;
|
|
2195
2705
|
}
|
|
2196
2706
|
}
|
|
2197
|
-
if (!this.resolvedLanguage && this.languages.indexOf(l) < 0 && this.store.hasLanguageSomeTranslations(l)) {
|
|
2198
|
-
this.resolvedLanguage = l;
|
|
2199
|
-
this.languages.unshift(l);
|
|
2200
|
-
}
|
|
2201
2707
|
}
|
|
2202
2708
|
changeLanguage(lng, callback) {
|
|
2709
|
+
var _this2 = this;
|
|
2203
2710
|
this.isLanguageChangingTo = lng;
|
|
2204
2711
|
const deferred = defer();
|
|
2205
2712
|
this.emit('languageChanging', lng);
|
|
2206
|
-
const setLngProps = l => {
|
|
2207
|
-
this.language = l;
|
|
2208
|
-
this.languages = this.services.languageUtils.toResolveHierarchy(l);
|
|
2209
|
-
this.resolvedLanguage = undefined;
|
|
2210
|
-
this.setResolvedLanguage(l);
|
|
2211
|
-
};
|
|
2212
|
-
const done = (err, l) => {
|
|
2213
|
-
if (l) {
|
|
2214
|
-
if (this.isLanguageChangingTo === lng) {
|
|
2215
|
-
setLngProps(l);
|
|
2216
|
-
this.translator.changeLanguage(l);
|
|
2217
|
-
this.isLanguageChangingTo = undefined;
|
|
2218
|
-
this.emit('languageChanged', l);
|
|
2219
|
-
this.logger.log('languageChanged', l);
|
|
2220
|
-
}
|
|
2221
|
-
} else {
|
|
2222
|
-
this.isLanguageChangingTo = undefined;
|
|
2223
|
-
}
|
|
2224
|
-
deferred.resolve((...args) => this.t(...args));
|
|
2225
|
-
if (callback) callback(err, (...args) => this.t(...args));
|
|
2226
|
-
};
|
|
2227
|
-
const setLng = lngs => {
|
|
2228
|
-
if (!lng && !lngs && this.services.languageDetector) lngs = [];
|
|
2229
|
-
const fl = isString(lngs) ? lngs : lngs && lngs[0];
|
|
2230
|
-
const l = this.store.hasLanguageSomeTranslations(fl) ? fl : this.services.languageUtils.getBestMatchFromCodes(isString(lngs) ? [lngs] : lngs);
|
|
2231
|
-
if (l) {
|
|
2232
|
-
if (!this.language) {
|
|
2233
|
-
setLngProps(l);
|
|
2234
|
-
}
|
|
2235
|
-
if (!this.translator.language) this.translator.changeLanguage(l);
|
|
2236
|
-
this.services.languageDetector?.cacheUserLanguage?.(l);
|
|
2237
|
-
}
|
|
2238
|
-
this.loadResources(l, err => {
|
|
2239
|
-
done(err, l);
|
|
2240
|
-
});
|
|
2241
|
-
};
|
|
2242
|
-
if (!lng && this.services.languageDetector && !this.services.languageDetector.async) {
|
|
2243
|
-
setLng(this.services.languageDetector.detect());
|
|
2244
|
-
} else if (!lng && this.services.languageDetector && this.services.languageDetector.async) {
|
|
2245
|
-
if (this.services.languageDetector.detect.length === 0) {
|
|
2246
|
-
this.services.languageDetector.detect().then(setLng);
|
|
2247
|
-
} else {
|
|
2248
|
-
this.services.languageDetector.detect(setLng);
|
|
2249
|
-
}
|
|
2250
|
-
} else {
|
|
2251
|
-
setLng(lng);
|
|
2252
|
-
}
|
|
2253
|
-
return deferred;
|
|
2254
|
-
}
|
|
2255
|
-
getFixedT(lng, ns, keyPrefix) {
|
|
2256
|
-
const fixedT = (key, opts, ...rest) => {
|
|
2257
|
-
let o;
|
|
2258
|
-
if (typeof opts !== 'object') {
|
|
2259
|
-
o = this.options.overloadTranslationOptionHandler([key, opts].concat(rest));
|
|
2260
|
-
} else {
|
|
2261
|
-
o = {
|
|
2262
|
-
...opts
|
|
2263
|
-
};
|
|
2264
|
-
}
|
|
2265
|
-
o.lng = o.lng || fixedT.lng;
|
|
2266
|
-
o.lngs = o.lngs || fixedT.lngs;
|
|
2267
|
-
o.ns = o.ns || fixedT.ns;
|
|
2268
|
-
if (o.keyPrefix !== '') o.keyPrefix = o.keyPrefix || keyPrefix || fixedT.keyPrefix;
|
|
2269
|
-
const keySeparator = this.options.keySeparator || '.';
|
|
2270
|
-
let resultKey;
|
|
2271
|
-
if (o.keyPrefix && Array.isArray(key)) {
|
|
2272
|
-
resultKey = key.map(k => {
|
|
2273
|
-
if (typeof k === 'function') k = keysFromSelector(k, {
|
|
2274
|
-
...this.options,
|
|
2275
|
-
...opts
|
|
2276
|
-
});
|
|
2277
|
-
return `${o.keyPrefix}${keySeparator}${k}`;
|
|
2278
|
-
});
|
|
2279
|
-
} else {
|
|
2280
|
-
if (typeof key === 'function') key = keysFromSelector(key, {
|
|
2281
|
-
...this.options,
|
|
2282
|
-
...opts
|
|
2283
|
-
});
|
|
2284
|
-
resultKey = o.keyPrefix ? `${o.keyPrefix}${keySeparator}${key}` : key;
|
|
2285
|
-
}
|
|
2286
|
-
return this.t(resultKey, o);
|
|
2287
|
-
};
|
|
2288
|
-
if (isString(lng)) {
|
|
2289
|
-
fixedT.lng = lng;
|
|
2290
|
-
} else {
|
|
2291
|
-
fixedT.lngs = lng;
|
|
2292
|
-
}
|
|
2293
|
-
fixedT.ns = ns;
|
|
2294
|
-
fixedT.keyPrefix = keyPrefix;
|
|
2295
|
-
return fixedT;
|
|
2296
|
-
}
|
|
2297
|
-
t(...args) {
|
|
2298
|
-
return this.translator?.translate(...args);
|
|
2299
|
-
}
|
|
2300
|
-
exists(...args) {
|
|
2301
|
-
return this.translator?.exists(...args);
|
|
2302
|
-
}
|
|
2303
|
-
setDefaultNamespace(ns) {
|
|
2304
|
-
this.options.defaultNS = ns;
|
|
2305
|
-
}
|
|
2306
|
-
hasLoadedNamespace(ns, options = {}) {
|
|
2307
|
-
if (!this.isInitialized) {
|
|
2308
|
-
this.logger.warn('hasLoadedNamespace: i18next was not initialized', this.languages);
|
|
2309
|
-
return false;
|
|
2310
|
-
}
|
|
2311
|
-
if (!this.languages || !this.languages.length) {
|
|
2312
|
-
this.logger.warn('hasLoadedNamespace: i18n.languages were undefined or empty', this.languages);
|
|
2313
|
-
return false;
|
|
2314
|
-
}
|
|
2315
|
-
const lng = options.lng || this.resolvedLanguage || this.languages[0];
|
|
2316
|
-
const fallbackLng = this.options ? this.options.fallbackLng : false;
|
|
2317
|
-
const lastLng = this.languages[this.languages.length - 1];
|
|
2318
|
-
if (lng.toLowerCase() === 'cimode') return true;
|
|
2319
|
-
const loadNotPending = (l, n) => {
|
|
2320
|
-
const loadState = this.services.backendConnector.state[`${l}|${n}`];
|
|
2321
|
-
return loadState === -1 || loadState === 0 || loadState === 2;
|
|
2322
|
-
};
|
|
2323
|
-
if (options.precheck) {
|
|
2324
|
-
const preResult = options.precheck(this, loadNotPending);
|
|
2325
|
-
if (preResult !== undefined) return preResult;
|
|
2326
|
-
}
|
|
2327
|
-
if (this.hasResourceBundle(lng, ns)) return true;
|
|
2328
|
-
if (!this.services.backendConnector.backend || this.options.resources && !this.options.partialBundledLanguages) return true;
|
|
2329
|
-
if (loadNotPending(lng, ns) && (!fallbackLng || loadNotPending(lastLng, ns))) return true;
|
|
2330
|
-
return false;
|
|
2331
|
-
}
|
|
2332
|
-
loadNamespaces(ns, callback) {
|
|
2333
|
-
const deferred = defer();
|
|
2334
|
-
if (!this.options.ns) {
|
|
2335
|
-
if (callback) callback();
|
|
2336
|
-
return Promise.resolve();
|
|
2337
|
-
}
|
|
2338
|
-
if (isString(ns)) ns = [ns];
|
|
2339
|
-
ns.forEach(n => {
|
|
2340
|
-
if (this.options.ns.indexOf(n) < 0) this.options.ns.push(n);
|
|
2341
|
-
});
|
|
2342
|
-
this.loadResources(err => {
|
|
2343
|
-
deferred.resolve();
|
|
2344
|
-
if (callback) callback(err);
|
|
2345
|
-
});
|
|
2346
|
-
return deferred;
|
|
2347
|
-
}
|
|
2348
|
-
loadLanguages(lngs, callback) {
|
|
2349
|
-
const deferred = defer();
|
|
2350
|
-
if (isString(lngs)) lngs = [lngs];
|
|
2351
|
-
const preloaded = this.options.preload || [];
|
|
2352
|
-
const newLngs = lngs.filter(lng => preloaded.indexOf(lng) < 0 && this.services.languageUtils.isSupportedCode(lng));
|
|
2353
|
-
if (!newLngs.length) {
|
|
2354
|
-
if (callback) callback();
|
|
2355
|
-
return Promise.resolve();
|
|
2356
|
-
}
|
|
2357
|
-
this.options.preload = preloaded.concat(newLngs);
|
|
2358
|
-
this.loadResources(err => {
|
|
2359
|
-
deferred.resolve();
|
|
2360
|
-
if (callback) callback(err);
|
|
2361
|
-
});
|
|
2362
|
-
return deferred;
|
|
2363
|
-
}
|
|
2364
|
-
dir(lng) {
|
|
2365
|
-
if (!lng) lng = this.resolvedLanguage || (this.languages?.length > 0 ? this.languages[0] : this.language);
|
|
2366
|
-
if (!lng) return 'rtl';
|
|
2367
|
-
try {
|
|
2368
|
-
const l = new Intl.Locale(lng);
|
|
2369
|
-
if (l && l.getTextInfo) {
|
|
2370
|
-
const ti = l.getTextInfo();
|
|
2371
|
-
if (ti && ti.direction) return ti.direction;
|
|
2372
|
-
}
|
|
2373
|
-
} catch (e) {}
|
|
2374
|
-
const rtlLngs = ['ar', 'shu', 'sqr', 'ssh', 'xaa', 'yhd', 'yud', 'aao', 'abh', 'abv', 'acm', 'acq', 'acw', 'acx', 'acy', 'adf', 'ads', 'aeb', 'aec', 'afb', 'ajp', 'apc', 'apd', 'arb', 'arq', 'ars', 'ary', 'arz', 'auz', 'avl', 'ayh', 'ayl', 'ayn', 'ayp', 'bbz', 'pga', 'he', 'iw', 'ps', 'pbt', 'pbu', 'pst', 'prp', 'prd', 'ug', 'ur', 'ydd', 'yds', 'yih', 'ji', 'yi', 'hbo', 'men', 'xmn', 'fa', 'jpr', 'peo', 'pes', 'prs', 'dv', 'sam', 'ckb'];
|
|
2375
|
-
const languageUtils = this.services?.languageUtils || new LanguageUtil(get());
|
|
2376
|
-
if (lng.toLowerCase().indexOf('-latn') > 1) return 'ltr';
|
|
2377
|
-
return rtlLngs.indexOf(languageUtils.getLanguagePartFromCode(lng)) > -1 || lng.toLowerCase().indexOf('-arab') > 1 ? 'rtl' : 'ltr';
|
|
2378
|
-
}
|
|
2379
|
-
static createInstance(options = {}, callback) {
|
|
2380
|
-
const instance = new I18n(options, callback);
|
|
2381
|
-
instance.createInstance = I18n.createInstance;
|
|
2382
|
-
return instance;
|
|
2383
|
-
}
|
|
2384
|
-
cloneInstance(options = {}, callback = noop) {
|
|
2385
|
-
const forkResourceStore = options.forkResourceStore;
|
|
2386
|
-
if (forkResourceStore) delete options.forkResourceStore;
|
|
2387
|
-
const mergedOptions = {
|
|
2388
|
-
...this.options,
|
|
2389
|
-
...options,
|
|
2390
|
-
...{
|
|
2391
|
-
isClone: true
|
|
2392
|
-
}
|
|
2713
|
+
const setLngProps = l => {
|
|
2714
|
+
this.language = l;
|
|
2715
|
+
this.languages = this.services.languageUtils.toResolveHierarchy(l);
|
|
2716
|
+
this.resolvedLanguage = undefined;
|
|
2717
|
+
this.setResolvedLanguage(l);
|
|
2393
2718
|
};
|
|
2394
|
-
const
|
|
2395
|
-
|
|
2396
|
-
|
|
2397
|
-
|
|
2398
|
-
|
|
2399
|
-
|
|
2400
|
-
|
|
2401
|
-
|
|
2402
|
-
|
|
2403
|
-
|
|
2719
|
+
const done = (err, l) => {
|
|
2720
|
+
if (l) {
|
|
2721
|
+
setLngProps(l);
|
|
2722
|
+
this.translator.changeLanguage(l);
|
|
2723
|
+
this.isLanguageChangingTo = undefined;
|
|
2724
|
+
this.emit('languageChanged', l);
|
|
2725
|
+
this.logger.log('languageChanged', l);
|
|
2726
|
+
} else {
|
|
2727
|
+
this.isLanguageChangingTo = undefined;
|
|
2728
|
+
}
|
|
2729
|
+
deferred.resolve(function () {
|
|
2730
|
+
return _this2.t(...arguments);
|
|
2731
|
+
});
|
|
2732
|
+
if (callback) callback(err, function () {
|
|
2733
|
+
return _this2.t(...arguments);
|
|
2734
|
+
});
|
|
2404
2735
|
};
|
|
2405
|
-
|
|
2406
|
-
|
|
2736
|
+
const setLng = lngs => {
|
|
2737
|
+
if (!lng && !lngs && this.services.languageDetector) lngs = [];
|
|
2738
|
+
const l = isString(lngs) ? lngs : this.services.languageUtils.getBestMatchFromCodes(lngs);
|
|
2739
|
+
if (l) {
|
|
2740
|
+
if (!this.language) {
|
|
2741
|
+
setLngProps(l);
|
|
2742
|
+
}
|
|
2743
|
+
if (!this.translator.language) this.translator.changeLanguage(l);
|
|
2744
|
+
if (this.services.languageDetector && this.services.languageDetector.cacheUserLanguage) this.services.languageDetector.cacheUserLanguage(l);
|
|
2745
|
+
}
|
|
2746
|
+
this.loadResources(l, err => {
|
|
2747
|
+
done(err, l);
|
|
2748
|
+
});
|
|
2407
2749
|
};
|
|
2408
|
-
if (
|
|
2409
|
-
|
|
2410
|
-
|
|
2411
|
-
|
|
2412
|
-
|
|
2413
|
-
|
|
2414
|
-
|
|
2415
|
-
|
|
2416
|
-
|
|
2417
|
-
|
|
2418
|
-
}, prev[l]);
|
|
2419
|
-
return prev;
|
|
2420
|
-
}, {});
|
|
2421
|
-
clone.store = new ResourceStore(clonedData, mergedOptions);
|
|
2422
|
-
clone.services.resourceStore = clone.store;
|
|
2423
|
-
}
|
|
2424
|
-
if (options.interpolation) {
|
|
2425
|
-
const defOpts = get();
|
|
2426
|
-
const mergedInterpolation = {
|
|
2427
|
-
...defOpts.interpolation,
|
|
2428
|
-
...this.options.interpolation,
|
|
2429
|
-
...options.interpolation
|
|
2430
|
-
};
|
|
2431
|
-
const mergedForInterpolator = {
|
|
2432
|
-
...mergedOptions,
|
|
2433
|
-
interpolation: mergedInterpolation
|
|
2434
|
-
};
|
|
2435
|
-
clone.services.interpolator = new Interpolator(mergedForInterpolator);
|
|
2750
|
+
if (!lng && this.services.languageDetector && !this.services.languageDetector.async) {
|
|
2751
|
+
setLng(this.services.languageDetector.detect());
|
|
2752
|
+
} else if (!lng && this.services.languageDetector && this.services.languageDetector.async) {
|
|
2753
|
+
if (this.services.languageDetector.detect.length === 0) {
|
|
2754
|
+
this.services.languageDetector.detect().then(setLng);
|
|
2755
|
+
} else {
|
|
2756
|
+
this.services.languageDetector.detect(setLng);
|
|
2757
|
+
}
|
|
2758
|
+
} else {
|
|
2759
|
+
setLng(lng);
|
|
2436
2760
|
}
|
|
2437
|
-
|
|
2438
|
-
clone.translator.on('*', (event, ...args) => {
|
|
2439
|
-
clone.emit(event, ...args);
|
|
2440
|
-
});
|
|
2441
|
-
clone.init(mergedOptions, callback);
|
|
2442
|
-
clone.translator.options = mergedOptions;
|
|
2443
|
-
clone.translator.backendConnector.services.utils = {
|
|
2444
|
-
hasLoadedNamespace: clone.hasLoadedNamespace.bind(clone)
|
|
2445
|
-
};
|
|
2446
|
-
return clone;
|
|
2761
|
+
return deferred;
|
|
2447
2762
|
}
|
|
2448
|
-
|
|
2449
|
-
|
|
2450
|
-
|
|
2451
|
-
|
|
2452
|
-
|
|
2453
|
-
|
|
2454
|
-
|
|
2763
|
+
getFixedT(lng, ns, keyPrefix) {
|
|
2764
|
+
var _this3 = this;
|
|
2765
|
+
const fixedT = function (key, opts) {
|
|
2766
|
+
let options;
|
|
2767
|
+
if (typeof opts !== 'object') {
|
|
2768
|
+
for (var _len3 = arguments.length, rest = new Array(_len3 > 2 ? _len3 - 2 : 0), _key3 = 2; _key3 < _len3; _key3++) {
|
|
2769
|
+
rest[_key3 - 2] = arguments[_key3];
|
|
2770
|
+
}
|
|
2771
|
+
options = _this3.options.overloadTranslationOptionHandler([key, opts].concat(rest));
|
|
2772
|
+
} else {
|
|
2773
|
+
options = {
|
|
2774
|
+
...opts
|
|
2775
|
+
};
|
|
2776
|
+
}
|
|
2777
|
+
options.lng = options.lng || fixedT.lng;
|
|
2778
|
+
options.lngs = options.lngs || fixedT.lngs;
|
|
2779
|
+
options.ns = options.ns || fixedT.ns;
|
|
2780
|
+
if (options.keyPrefix !== '') options.keyPrefix = options.keyPrefix || keyPrefix || fixedT.keyPrefix;
|
|
2781
|
+
const keySeparator = _this3.options.keySeparator || '.';
|
|
2782
|
+
let resultKey;
|
|
2783
|
+
if (options.keyPrefix && Array.isArray(key)) {
|
|
2784
|
+
resultKey = key.map(k => `${options.keyPrefix}${keySeparator}${k}`);
|
|
2785
|
+
} else {
|
|
2786
|
+
resultKey = options.keyPrefix ? `${options.keyPrefix}${keySeparator}${key}` : key;
|
|
2787
|
+
}
|
|
2788
|
+
return _this3.t(resultKey, options);
|
|
2455
2789
|
};
|
|
2456
|
-
|
|
2457
|
-
|
|
2458
|
-
|
|
2459
|
-
|
|
2460
|
-
instance.createInstance;
|
|
2461
|
-
instance.dir;
|
|
2462
|
-
instance.init;
|
|
2463
|
-
instance.loadResources;
|
|
2464
|
-
instance.reloadResources;
|
|
2465
|
-
instance.use;
|
|
2466
|
-
instance.changeLanguage;
|
|
2467
|
-
instance.getFixedT;
|
|
2468
|
-
instance.t;
|
|
2469
|
-
instance.exists;
|
|
2470
|
-
instance.setDefaultNamespace;
|
|
2471
|
-
instance.hasLoadedNamespace;
|
|
2472
|
-
instance.loadNamespaces;
|
|
2473
|
-
instance.loadLanguages;
|
|
2474
|
-
|
|
2475
|
-
function warn() {
|
|
2476
|
-
if (console && console.warn) {
|
|
2477
|
-
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
2478
|
-
args[_key] = arguments[_key];
|
|
2790
|
+
if (isString(lng)) {
|
|
2791
|
+
fixedT.lng = lng;
|
|
2792
|
+
} else {
|
|
2793
|
+
fixedT.lngs = lng;
|
|
2479
2794
|
}
|
|
2480
|
-
|
|
2481
|
-
|
|
2482
|
-
|
|
2483
|
-
}
|
|
2484
|
-
const alreadyWarned = {};
|
|
2485
|
-
function warnOnce() {
|
|
2486
|
-
for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
|
|
2487
|
-
args[_key2] = arguments[_key2];
|
|
2795
|
+
fixedT.ns = ns;
|
|
2796
|
+
fixedT.keyPrefix = keyPrefix;
|
|
2797
|
+
return fixedT;
|
|
2488
2798
|
}
|
|
2489
|
-
|
|
2490
|
-
|
|
2491
|
-
warn(...args);
|
|
2492
|
-
}
|
|
2493
|
-
const loadedClb = (i18n, cb) => () => {
|
|
2494
|
-
if (i18n.isInitialized) {
|
|
2495
|
-
cb();
|
|
2496
|
-
} else {
|
|
2497
|
-
const initialized = () => {
|
|
2498
|
-
setTimeout(() => {
|
|
2499
|
-
i18n.off('initialized', initialized);
|
|
2500
|
-
}, 0);
|
|
2501
|
-
cb();
|
|
2502
|
-
};
|
|
2503
|
-
i18n.on('initialized', initialized);
|
|
2799
|
+
t() {
|
|
2800
|
+
return this.translator && this.translator.translate(...arguments);
|
|
2504
2801
|
}
|
|
2505
|
-
|
|
2506
|
-
|
|
2507
|
-
i18n.loadNamespaces(ns, loadedClb(i18n, cb));
|
|
2508
|
-
}
|
|
2509
|
-
function loadLanguages(i18n, lng, ns, cb) {
|
|
2510
|
-
if (typeof ns === 'string') ns = [ns];
|
|
2511
|
-
ns.forEach(n => {
|
|
2512
|
-
if (i18n.options.ns.indexOf(n) < 0) i18n.options.ns.push(n);
|
|
2513
|
-
});
|
|
2514
|
-
i18n.loadLanguages(lng, loadedClb(i18n, cb));
|
|
2515
|
-
}
|
|
2516
|
-
function oldI18nextHasLoadedNamespace(ns, i18n) {
|
|
2517
|
-
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
2518
|
-
const lng = i18n.languages[0];
|
|
2519
|
-
const fallbackLng = i18n.options ? i18n.options.fallbackLng : false;
|
|
2520
|
-
const lastLng = i18n.languages[i18n.languages.length - 1];
|
|
2521
|
-
if (lng.toLowerCase() === 'cimode') return true;
|
|
2522
|
-
const loadNotPending = (l, n) => {
|
|
2523
|
-
const loadState = i18n.services.backendConnector.state[`${l}|${n}`];
|
|
2524
|
-
return loadState === -1 || loadState === 2;
|
|
2525
|
-
};
|
|
2526
|
-
if (options.bindI18n && options.bindI18n.indexOf('languageChanging') > -1 && i18n.services.backendConnector.backend && i18n.isLanguageChangingTo && !loadNotPending(i18n.isLanguageChangingTo, ns)) return false;
|
|
2527
|
-
if (i18n.hasResourceBundle(lng, ns)) return true;
|
|
2528
|
-
if (!i18n.services.backendConnector.backend || i18n.options.resources && !i18n.options.partialBundledLanguages) return true;
|
|
2529
|
-
if (loadNotPending(lng, ns) && (!fallbackLng || loadNotPending(lastLng, ns))) return true;
|
|
2530
|
-
return false;
|
|
2531
|
-
}
|
|
2532
|
-
function hasLoadedNamespace(ns, i18n) {
|
|
2533
|
-
let options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
2534
|
-
if (!i18n.languages || !i18n.languages.length) {
|
|
2535
|
-
warnOnce('i18n.languages were undefined or empty', i18n.languages);
|
|
2536
|
-
return true;
|
|
2802
|
+
exists() {
|
|
2803
|
+
return this.translator && this.translator.exists(...arguments);
|
|
2537
2804
|
}
|
|
2538
|
-
|
|
2539
|
-
|
|
2540
|
-
return oldI18nextHasLoadedNamespace(ns, i18n, options);
|
|
2805
|
+
setDefaultNamespace(ns) {
|
|
2806
|
+
this.options.defaultNS = ns;
|
|
2541
2807
|
}
|
|
2542
|
-
|
|
2543
|
-
|
|
2544
|
-
|
|
2545
|
-
|
|
2808
|
+
hasLoadedNamespace(ns) {
|
|
2809
|
+
let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
2810
|
+
if (!this.isInitialized) {
|
|
2811
|
+
this.logger.warn('hasLoadedNamespace: i18next was not initialized', this.languages);
|
|
2812
|
+
return false;
|
|
2546
2813
|
}
|
|
2547
|
-
|
|
2548
|
-
|
|
2549
|
-
|
|
2550
|
-
|
|
2551
|
-
const
|
|
2552
|
-
|
|
2553
|
-
|
|
2554
|
-
|
|
2555
|
-
|
|
2556
|
-
|
|
2557
|
-
|
|
2558
|
-
|
|
2559
|
-
|
|
2560
|
-
|
|
2561
|
-
|
|
2562
|
-
|
|
2563
|
-
|
|
2564
|
-
|
|
2565
|
-
|
|
2566
|
-
|
|
2567
|
-
'®': '®',
|
|
2568
|
-
'…': '…',
|
|
2569
|
-
'…': '…',
|
|
2570
|
-
'/': '/',
|
|
2571
|
-
'/': '/'
|
|
2572
|
-
};
|
|
2573
|
-
const unescapeHtmlEntity = m => htmlEntities[m];
|
|
2574
|
-
const unescape = text => text.replace(matchHtmlEntity, unescapeHtmlEntity);
|
|
2575
|
-
|
|
2576
|
-
let defaultOptions$1 = {
|
|
2577
|
-
bindI18n: 'languageChanged',
|
|
2578
|
-
bindI18nStore: '',
|
|
2579
|
-
transEmptyNodeValue: '',
|
|
2580
|
-
transSupportBasicHtmlNodes: true,
|
|
2581
|
-
transWrapTextNodes: '',
|
|
2582
|
-
transKeepBasicHtmlNodesFor: ['br', 'strong', 'i', 'p'],
|
|
2583
|
-
useSuspense: true,
|
|
2584
|
-
unescape
|
|
2585
|
-
};
|
|
2586
|
-
function setDefaults() {
|
|
2587
|
-
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
2588
|
-
defaultOptions$1 = {
|
|
2589
|
-
...defaultOptions$1,
|
|
2590
|
-
...options
|
|
2591
|
-
};
|
|
2592
|
-
}
|
|
2593
|
-
function getDefaults() {
|
|
2594
|
-
return defaultOptions$1;
|
|
2595
|
-
}
|
|
2596
|
-
|
|
2597
|
-
let i18nInstance;
|
|
2598
|
-
function setI18n(instance) {
|
|
2599
|
-
i18nInstance = instance;
|
|
2600
|
-
}
|
|
2601
|
-
function getI18n() {
|
|
2602
|
-
return i18nInstance;
|
|
2603
|
-
}
|
|
2604
|
-
|
|
2605
|
-
const initReactI18next = {
|
|
2606
|
-
type: '3rdParty',
|
|
2607
|
-
init(instance) {
|
|
2608
|
-
setDefaults(instance.options.react);
|
|
2609
|
-
setI18n(instance);
|
|
2610
|
-
}
|
|
2611
|
-
};
|
|
2612
|
-
|
|
2613
|
-
const I18nContext = React.createContext();
|
|
2614
|
-
class ReportNamespaces {
|
|
2615
|
-
constructor() {
|
|
2616
|
-
this.usedNamespaces = {};
|
|
2814
|
+
if (!this.languages || !this.languages.length) {
|
|
2815
|
+
this.logger.warn('hasLoadedNamespace: i18n.languages were undefined or empty', this.languages);
|
|
2816
|
+
return false;
|
|
2817
|
+
}
|
|
2818
|
+
const lng = options.lng || this.resolvedLanguage || this.languages[0];
|
|
2819
|
+
const fallbackLng = this.options ? this.options.fallbackLng : false;
|
|
2820
|
+
const lastLng = this.languages[this.languages.length - 1];
|
|
2821
|
+
if (lng.toLowerCase() === 'cimode') return true;
|
|
2822
|
+
const loadNotPending = (l, n) => {
|
|
2823
|
+
const loadState = this.services.backendConnector.state[`${l}|${n}`];
|
|
2824
|
+
return loadState === -1 || loadState === 0 || loadState === 2;
|
|
2825
|
+
};
|
|
2826
|
+
if (options.precheck) {
|
|
2827
|
+
const preResult = options.precheck(this, loadNotPending);
|
|
2828
|
+
if (preResult !== undefined) return preResult;
|
|
2829
|
+
}
|
|
2830
|
+
if (this.hasResourceBundle(lng, ns)) return true;
|
|
2831
|
+
if (!this.services.backendConnector.backend || this.options.resources && !this.options.partialBundledLanguages) return true;
|
|
2832
|
+
if (loadNotPending(lng, ns) && (!fallbackLng || loadNotPending(lastLng, ns))) return true;
|
|
2833
|
+
return false;
|
|
2617
2834
|
}
|
|
2618
|
-
|
|
2619
|
-
|
|
2620
|
-
|
|
2835
|
+
loadNamespaces(ns, callback) {
|
|
2836
|
+
const deferred = defer();
|
|
2837
|
+
if (!this.options.ns) {
|
|
2838
|
+
if (callback) callback();
|
|
2839
|
+
return Promise.resolve();
|
|
2840
|
+
}
|
|
2841
|
+
if (isString(ns)) ns = [ns];
|
|
2842
|
+
ns.forEach(n => {
|
|
2843
|
+
if (this.options.ns.indexOf(n) < 0) this.options.ns.push(n);
|
|
2621
2844
|
});
|
|
2845
|
+
this.loadResources(err => {
|
|
2846
|
+
deferred.resolve();
|
|
2847
|
+
if (callback) callback(err);
|
|
2848
|
+
});
|
|
2849
|
+
return deferred;
|
|
2622
2850
|
}
|
|
2623
|
-
|
|
2624
|
-
|
|
2851
|
+
loadLanguages(lngs, callback) {
|
|
2852
|
+
const deferred = defer();
|
|
2853
|
+
if (isString(lngs)) lngs = [lngs];
|
|
2854
|
+
const preloaded = this.options.preload || [];
|
|
2855
|
+
const newLngs = lngs.filter(lng => preloaded.indexOf(lng) < 0 && this.services.languageUtils.isSupportedCode(lng));
|
|
2856
|
+
if (!newLngs.length) {
|
|
2857
|
+
if (callback) callback();
|
|
2858
|
+
return Promise.resolve();
|
|
2859
|
+
}
|
|
2860
|
+
this.options.preload = preloaded.concat(newLngs);
|
|
2861
|
+
this.loadResources(err => {
|
|
2862
|
+
deferred.resolve();
|
|
2863
|
+
if (callback) callback(err);
|
|
2864
|
+
});
|
|
2865
|
+
return deferred;
|
|
2625
2866
|
}
|
|
2626
|
-
|
|
2627
|
-
|
|
2628
|
-
|
|
2629
|
-
|
|
2630
|
-
|
|
2631
|
-
|
|
2632
|
-
}, [value, ignore]);
|
|
2633
|
-
return ref.current;
|
|
2634
|
-
};
|
|
2635
|
-
function useTranslation(ns) {
|
|
2636
|
-
let props = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
2637
|
-
const {
|
|
2638
|
-
i18n: i18nFromProps
|
|
2639
|
-
} = props;
|
|
2640
|
-
const {
|
|
2641
|
-
i18n: i18nFromContext,
|
|
2642
|
-
defaultNS: defaultNSFromContext
|
|
2643
|
-
} = React.useContext(I18nContext) || {};
|
|
2644
|
-
const i18n = i18nFromProps || i18nFromContext || getI18n();
|
|
2645
|
-
if (i18n && !i18n.reportNamespaces) i18n.reportNamespaces = new ReportNamespaces();
|
|
2646
|
-
if (!i18n) {
|
|
2647
|
-
warnOnce('You will need to pass in an i18next instance by using initReactI18next');
|
|
2648
|
-
const notReadyT = (k, optsOrDefaultValue) => {
|
|
2649
|
-
if (typeof optsOrDefaultValue === 'string') return optsOrDefaultValue;
|
|
2650
|
-
if (optsOrDefaultValue && typeof optsOrDefaultValue === 'object' && typeof optsOrDefaultValue.defaultValue === 'string') return optsOrDefaultValue.defaultValue;
|
|
2651
|
-
return Array.isArray(k) ? k[k.length - 1] : k;
|
|
2652
|
-
};
|
|
2653
|
-
const retNotReady = [notReadyT, {}, false];
|
|
2654
|
-
retNotReady.t = notReadyT;
|
|
2655
|
-
retNotReady.i18n = {};
|
|
2656
|
-
retNotReady.ready = false;
|
|
2657
|
-
return retNotReady;
|
|
2867
|
+
dir(lng) {
|
|
2868
|
+
if (!lng) lng = this.resolvedLanguage || (this.languages && this.languages.length > 0 ? this.languages[0] : this.language);
|
|
2869
|
+
if (!lng) return 'rtl';
|
|
2870
|
+
const rtlLngs = ['ar', 'shu', 'sqr', 'ssh', 'xaa', 'yhd', 'yud', 'aao', 'abh', 'abv', 'acm', 'acq', 'acw', 'acx', 'acy', 'adf', 'ads', 'aeb', 'aec', 'afb', 'ajp', 'apc', 'apd', 'arb', 'arq', 'ars', 'ary', 'arz', 'auz', 'avl', 'ayh', 'ayl', 'ayn', 'ayp', 'bbz', 'pga', 'he', 'iw', 'ps', 'pbt', 'pbu', 'pst', 'prp', 'prd', 'ug', 'ur', 'ydd', 'yds', 'yih', 'ji', 'yi', 'hbo', 'men', 'xmn', 'fa', 'jpr', 'peo', 'pes', 'prs', 'dv', 'sam', 'ckb'];
|
|
2871
|
+
const languageUtils = this.services && this.services.languageUtils || new LanguageUtil(get());
|
|
2872
|
+
return rtlLngs.indexOf(languageUtils.getLanguagePartFromCode(lng)) > -1 || lng.toLowerCase().indexOf('-arab') > 1 ? 'rtl' : 'ltr';
|
|
2658
2873
|
}
|
|
2659
|
-
|
|
2660
|
-
|
|
2661
|
-
|
|
2662
|
-
|
|
2663
|
-
...props
|
|
2664
|
-
};
|
|
2665
|
-
const {
|
|
2666
|
-
useSuspense,
|
|
2667
|
-
keyPrefix
|
|
2668
|
-
} = i18nOptions;
|
|
2669
|
-
let namespaces = ns || defaultNSFromContext || i18n.options && i18n.options.defaultNS;
|
|
2670
|
-
namespaces = typeof namespaces === 'string' ? [namespaces] : namespaces || ['translation'];
|
|
2671
|
-
if (i18n.reportNamespaces.addUsedNamespaces) i18n.reportNamespaces.addUsedNamespaces(namespaces);
|
|
2672
|
-
const ready = (i18n.isInitialized || i18n.initializedStoreOnce) && namespaces.every(n => hasLoadedNamespace(n, i18n, i18nOptions));
|
|
2673
|
-
function getT() {
|
|
2674
|
-
return i18n.getFixedT(props.lng || null, i18nOptions.nsMode === 'fallback' ? namespaces : namespaces[0], keyPrefix);
|
|
2874
|
+
static createInstance() {
|
|
2875
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
2876
|
+
let callback = arguments.length > 1 ? arguments[1] : undefined;
|
|
2877
|
+
return new I18n(options, callback);
|
|
2675
2878
|
}
|
|
2676
|
-
|
|
2677
|
-
|
|
2678
|
-
|
|
2679
|
-
|
|
2680
|
-
|
|
2681
|
-
|
|
2682
|
-
|
|
2683
|
-
|
|
2684
|
-
|
|
2685
|
-
|
|
2686
|
-
isMounted.current = true;
|
|
2687
|
-
if (!ready && !useSuspense) {
|
|
2688
|
-
if (props.lng) {
|
|
2689
|
-
loadLanguages(i18n, props.lng, namespaces, () => {
|
|
2690
|
-
if (isMounted.current) setT(getT);
|
|
2691
|
-
});
|
|
2692
|
-
} else {
|
|
2693
|
-
loadNamespaces(i18n, namespaces, () => {
|
|
2694
|
-
if (isMounted.current) setT(getT);
|
|
2695
|
-
});
|
|
2879
|
+
cloneInstance() {
|
|
2880
|
+
let options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
|
|
2881
|
+
let callback = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : noop;
|
|
2882
|
+
const forkResourceStore = options.forkResourceStore;
|
|
2883
|
+
if (forkResourceStore) delete options.forkResourceStore;
|
|
2884
|
+
const mergedOptions = {
|
|
2885
|
+
...this.options,
|
|
2886
|
+
...options,
|
|
2887
|
+
...{
|
|
2888
|
+
isClone: true
|
|
2696
2889
|
}
|
|
2697
|
-
}
|
|
2698
|
-
if (ready && previousJoinedNS && previousJoinedNS !== joinedNS && isMounted.current) {
|
|
2699
|
-
setT(getT);
|
|
2700
|
-
}
|
|
2701
|
-
function boundReset() {
|
|
2702
|
-
if (isMounted.current) setT(getT);
|
|
2703
|
-
}
|
|
2704
|
-
if (bindI18n && i18n) i18n.on(bindI18n, boundReset);
|
|
2705
|
-
if (bindI18nStore && i18n) i18n.store.on(bindI18nStore, boundReset);
|
|
2706
|
-
return () => {
|
|
2707
|
-
isMounted.current = false;
|
|
2708
|
-
if (bindI18n && i18n) bindI18n.split(' ').forEach(e => i18n.off(e, boundReset));
|
|
2709
|
-
if (bindI18nStore && i18n) bindI18nStore.split(' ').forEach(e => i18n.store.off(e, boundReset));
|
|
2710
2890
|
};
|
|
2711
|
-
|
|
2712
|
-
|
|
2713
|
-
|
|
2714
|
-
if (isMounted.current && !isInitial.current) {
|
|
2715
|
-
setT(getT);
|
|
2891
|
+
const clone = new I18n(mergedOptions);
|
|
2892
|
+
if (options.debug !== undefined || options.prefix !== undefined) {
|
|
2893
|
+
clone.logger = clone.logger.clone(options);
|
|
2716
2894
|
}
|
|
2717
|
-
|
|
2718
|
-
|
|
2719
|
-
|
|
2720
|
-
|
|
2721
|
-
|
|
2722
|
-
|
|
2723
|
-
|
|
2724
|
-
|
|
2725
|
-
|
|
2726
|
-
|
|
2727
|
-
|
|
2728
|
-
|
|
2729
|
-
|
|
2895
|
+
const membersToCopy = ['store', 'services', 'language'];
|
|
2896
|
+
membersToCopy.forEach(m => {
|
|
2897
|
+
clone[m] = this[m];
|
|
2898
|
+
});
|
|
2899
|
+
clone.services = {
|
|
2900
|
+
...this.services
|
|
2901
|
+
};
|
|
2902
|
+
clone.services.utils = {
|
|
2903
|
+
hasLoadedNamespace: clone.hasLoadedNamespace.bind(clone)
|
|
2904
|
+
};
|
|
2905
|
+
if (forkResourceStore) {
|
|
2906
|
+
clone.store = new ResourceStore(this.store.data, mergedOptions);
|
|
2907
|
+
clone.services.resourceStore = clone.store;
|
|
2730
2908
|
}
|
|
2731
|
-
|
|
2909
|
+
clone.translator = new Translator(clone.services, mergedOptions);
|
|
2910
|
+
clone.translator.on('*', function (event) {
|
|
2911
|
+
for (var _len4 = arguments.length, args = new Array(_len4 > 1 ? _len4 - 1 : 0), _key4 = 1; _key4 < _len4; _key4++) {
|
|
2912
|
+
args[_key4 - 1] = arguments[_key4];
|
|
2913
|
+
}
|
|
2914
|
+
clone.emit(event, ...args);
|
|
2915
|
+
});
|
|
2916
|
+
clone.init(mergedOptions, callback);
|
|
2917
|
+
clone.translator.options = mergedOptions;
|
|
2918
|
+
clone.translator.backendConnector.services.utils = {
|
|
2919
|
+
hasLoadedNamespace: clone.hasLoadedNamespace.bind(clone)
|
|
2920
|
+
};
|
|
2921
|
+
return clone;
|
|
2922
|
+
}
|
|
2923
|
+
toJSON() {
|
|
2924
|
+
return {
|
|
2925
|
+
options: this.options,
|
|
2926
|
+
store: this.store,
|
|
2927
|
+
language: this.language,
|
|
2928
|
+
languages: this.languages,
|
|
2929
|
+
resolvedLanguage: this.resolvedLanguage
|
|
2930
|
+
};
|
|
2931
|
+
}
|
|
2732
2932
|
}
|
|
2933
|
+
const instance = I18n.createInstance();
|
|
2934
|
+
instance.createInstance = I18n.createInstance;
|
|
2935
|
+
|
|
2936
|
+
instance.createInstance;
|
|
2937
|
+
instance.dir;
|
|
2938
|
+
instance.init;
|
|
2939
|
+
instance.loadResources;
|
|
2940
|
+
instance.reloadResources;
|
|
2941
|
+
instance.use;
|
|
2942
|
+
instance.changeLanguage;
|
|
2943
|
+
instance.getFixedT;
|
|
2944
|
+
instance.t;
|
|
2945
|
+
instance.exists;
|
|
2946
|
+
instance.setDefaultNamespace;
|
|
2947
|
+
instance.hasLoadedNamespace;
|
|
2948
|
+
instance.loadNamespaces;
|
|
2949
|
+
instance.loadLanguages;
|
|
2733
2950
|
|
|
2734
2951
|
var locations$1 = {
|
|
2735
2952
|
label: "Location",
|
|
@@ -2871,70 +3088,30 @@ var fiCommon = {
|
|
|
2871
3088
|
errors: errors
|
|
2872
3089
|
};
|
|
2873
3090
|
|
|
2874
|
-
var
|
|
2875
|
-
|
|
2876
|
-
:
|
|
2877
|
-
var localeFromUrl = (urlParams === null || urlParams === void 0 ? void 0 : urlParams.get('locale')) || 'fi';
|
|
2878
|
-
instance.use(initReactI18next).init({
|
|
2879
|
-
resources: {
|
|
2880
|
-
en: { filterBar: enFilterBar, common: enCommon },
|
|
2881
|
-
fi: { filterBar: fiFilterBar, common: fiCommon },
|
|
2882
|
-
},
|
|
2883
|
-
lng: localeFromUrl,
|
|
2884
|
-
fallbackLng: 'fi',
|
|
2885
|
-
interpolation: {
|
|
2886
|
-
escapeValue: false,
|
|
2887
|
-
},
|
|
2888
|
-
});
|
|
2889
|
-
|
|
2890
|
-
var useUpdateTranslations = function (_a) {
|
|
2891
|
-
var language = _a.language;
|
|
2892
|
-
var _b = __read(React.useState(0), 2); _b[0]; var setRerenderKey = _b[1];
|
|
2893
|
-
React.useEffect(function () {
|
|
2894
|
-
instance.changeLanguage(language);
|
|
2895
|
-
setRerenderKey(function (prevKey) { return prevKey + 1; });
|
|
2896
|
-
}, [language]);
|
|
3091
|
+
var resources = {
|
|
3092
|
+
en: { filterBar: enFilterBar, common: enCommon },
|
|
3093
|
+
fi: { filterBar: fiFilterBar, common: fiCommon },
|
|
2897
3094
|
};
|
|
2898
|
-
|
|
2899
|
-
|
|
2900
|
-
|
|
2901
|
-
|
|
2902
|
-
|
|
2903
|
-
|
|
2904
|
-
|
|
2905
|
-
|
|
2906
|
-
|
|
2907
|
-
|
|
2908
|
-
|
|
2909
|
-
}
|
|
2910
|
-
|
|
2911
|
-
|
|
2912
|
-
document.removeEventListener('mousedown', handleClickOutside);
|
|
2913
|
-
};
|
|
2914
|
-
}, [filterSectionRef]);
|
|
2915
|
-
return { filterSectionRef: filterSectionRef };
|
|
3095
|
+
var readLocaleFromUrl = function () {
|
|
3096
|
+
if (typeof window === 'undefined')
|
|
3097
|
+
return null;
|
|
3098
|
+
return new URLSearchParams(window.location.search).get('locale');
|
|
3099
|
+
};
|
|
3100
|
+
var createI18nInstance = function (language) {
|
|
3101
|
+
var instance$1 = instance.createInstance();
|
|
3102
|
+
instance$1.use(initReactI18next).init({
|
|
3103
|
+
resources: resources,
|
|
3104
|
+
lng: language || readLocaleFromUrl() || 'fi',
|
|
3105
|
+
fallbackLng: 'fi',
|
|
3106
|
+
interpolation: { escapeValue: false },
|
|
3107
|
+
});
|
|
3108
|
+
return instance$1;
|
|
2916
3109
|
};
|
|
2917
3110
|
|
|
2918
|
-
var
|
|
2919
|
-
var
|
|
2920
|
-
React.
|
|
2921
|
-
|
|
2922
|
-
return;
|
|
2923
|
-
var attemptFocus = function (attempts) {
|
|
2924
|
-
if (attempts === void 0) { attempts = 0; }
|
|
2925
|
-
if (attempts > 20 || !ref.current)
|
|
2926
|
-
return;
|
|
2927
|
-
var focusable = ref.current.querySelector('button:not([disabled]), [tabindex]:not([tabindex="-1"])');
|
|
2928
|
-
if (focusable) {
|
|
2929
|
-
focusable.focus();
|
|
2930
|
-
}
|
|
2931
|
-
else {
|
|
2932
|
-
requestAnimationFrame(function () { return attemptFocus(attempts + 1); });
|
|
2933
|
-
}
|
|
2934
|
-
};
|
|
2935
|
-
requestAnimationFrame(function () { return attemptFocus(); });
|
|
2936
|
-
}, [autoFocus]);
|
|
2937
|
-
return ref;
|
|
3111
|
+
var I18nProvider = function (_a) {
|
|
3112
|
+
var language = _a.language, children = _a.children;
|
|
3113
|
+
var i18n = React.useMemo(function () { return createI18nInstance(language); }, []);
|
|
3114
|
+
return React.createElement(I18nextProvider, { i18n: i18n }, children);
|
|
2938
3115
|
};
|
|
2939
3116
|
|
|
2940
3117
|
var css_248z$j = ".will-filter-bar-select-button {\n width: 100%;\n height: auto;\n background-color: transparent;\n border: none;\n padding: 0 20px;\n border-radius: 20px;\n cursor: pointer;\n font-size: 14px;\n text-align: initial;\n user-select: none;\n}\n\n.will-filter-bar-select-button.disabled {\n cursor: not-allowed;\n}\n\n.will-filter-bar-select-button .select-button-wrapper {\n display: flex;\n align-items: center;\n flex-wrap: wrap;\n gap: 10px;\n}\n\n.will-filter-bar-select-button .select-button-wrapper > div {\n display: grid;\n}\n\n.will-filter-bar-select-button .select-button-label {\n color: var(--will-black);\n font-weight: 600;\n}\n\n.will-filter-bar-select-button .select-button-description {\n color: var(--will-black);\n font-weight: 400;\n opacity: 0.5;\n white-space: nowrap;\n min-height: 19px;\n overflow: hidden;\n text-overflow: ellipsis;\n}\n\n.will-filter-bar-select-button .select-button-description span {\n font: inherit;\n}\n\n.will-filter-bar-select-button .select-button-label.active,\n.will-filter-bar-select-button .select-button-description.active {\n font-weight: 700;\n font-size: 15px;\n opacity: 1;\n}\n\n@media (max-width: 960px) {\n .will-filter-bar-select-button {\n padding: 15px 0;\n }\n\n .will-filter-bar-select-button:first-child {\n padding: 0 0 15px 0;\n }\n\n .will-filter-bar-select-button .select-button-wrapper {\n justify-content: center;\n text-align: center;\n }\n\n .will-filter-bar-select-button .select-button-description {\n white-space: wrap;\n }\n\n .will-filter-bar-select-button .select-button-divider {\n display: none;\n }\n}\n";
|
|
@@ -12231,7 +12408,7 @@ var FilterControls = function () {
|
|
|
12231
12408
|
tabsRef.current = el;
|
|
12232
12409
|
}
|
|
12233
12410
|
} },
|
|
12234
|
-
((_a = locations === null || locations === void 0 ? void 0 : locations.data) === null || _a === void 0 ? void 0 : _a.length) && locations.data.length > 1 && (React.createElement(React.Fragment, null,
|
|
12411
|
+
!!((_a = locations === null || locations === void 0 ? void 0 : locations.data) === null || _a === void 0 ? void 0 : _a.length) && locations.data.length > 1 && (React.createElement(React.Fragment, null,
|
|
12235
12412
|
React.createElement(SelectButton, { ref: function (el) { return (buttonRefs.current[FilterSections.LOCATIONS] = el); }, label: t('locations.label'), description: parsedLocations, onClick: function (e) {
|
|
12236
12413
|
previouslyFocusedButtonRef.current = e.currentTarget;
|
|
12237
12414
|
handleSelectedFilter(FilterSections.LOCATIONS);
|
|
@@ -12277,12 +12454,12 @@ styleInject(css_248z$2);
|
|
|
12277
12454
|
var css_248z$1 = ".will-root {\n z-index: 999;\n width: fit-content;\n min-width: 796px;\n max-height: 100vh;\n position: relative;\n}\n\n.will-root.is-full-width {\n width: 100%;\n}\n\n.will-filter-bar {\n box-sizing: border-box;\n position: relative;\n}\n\n@media (max-width: 960px) {\n .will-root {\n width: 100%;\n min-width: auto;\n }\n}\n\n/* Common */\n\n.will-filter-bar-controls.dark,\n.will-filter-bar-panels.dark {\n box-shadow: var(--will-box-shadow-dark);\n}\n\n.will-filter-bar-controls.light,\n.will-filter-bar-panels.light {\n box-shadow: var(--will-box-shadow-light);\n}\n";
|
|
12278
12455
|
styleInject(css_248z$1);
|
|
12279
12456
|
|
|
12280
|
-
var FilterBar = function (
|
|
12457
|
+
var FilterBar = function (props) { return (React.createElement(I18nProvider, { language: props.language },
|
|
12458
|
+
React.createElement(FilterBarInner, __assign$2({}, props)))); };
|
|
12459
|
+
var FilterBarInner = function (_a) {
|
|
12281
12460
|
var language = _a.language, ageCategories = _a.ageCategories, _b = _a.redirectUrl, redirectUrl = _b === void 0 ? REDIRECT_URL_FALLBACK : _b, palette = _a.palette, onSubmit = _a.onSubmit, fullWidth = _a.fullWidth, disableCalendarDates = _a.disableCalendarDates, mode = _a.mode, tabs = _a.tabs, outerLoading = _a.outerLoading, locations = _a.locations;
|
|
12282
12461
|
var themePalette = useTheme({ palette: palette });
|
|
12283
|
-
// Translations
|
|
12284
12462
|
useUpdateTranslations({ language: language });
|
|
12285
|
-
// Display component after fully loaded
|
|
12286
12463
|
useAwaitRender();
|
|
12287
12464
|
return (React.createElement(FilterBarProvider, { language: language, ageCategories: ageCategories, redirectUrl: redirectUrl, palette: palette, onSubmit: onSubmit, fullWidth: fullWidth, disableCalendarDates: disableCalendarDates, mode: mode, tabs: tabs, outerLoading: outerLoading, locations: locations },
|
|
12288
12465
|
React.createElement("div", { className: "will-root ".concat(fullWidth ? 'is-full-width' : ''), style: themePalette },
|
|
@@ -12449,7 +12626,11 @@ var renderCalendarErrorMessage = function (_a) {
|
|
|
12449
12626
|
var css_248z = ".will-root .will-calendar-wrapper {\n box-shadow: var(--will-box-shadow-dark);\n border-radius: 20px;\n background-color: var(--will-white);\n position: absolute;\n top: 0;\n left: 0;\n \n}\n\n.will-root .will-calendar-wrapper .will-calendar-header,\n.will-root .will-calendar-wrapper .will-calendar-main,\n.will-root .will-calendar-wrapper .will-calendar-footer {\n padding: 20px;\n}\n\n/* Header */\n\n.will-root .will-calendar-wrapper .will-calendar-header {\n display: flex;\n justify-content: space-between;\n border-bottom: 1px solid var(--will-grey);\n align-items: center;\n}\n\n/* Footer */\n\n.will-root .will-calendar-wrapper .will-calendar-footer {\n border-top: 1px solid var(--will-grey);\n}\n\n/* Footer actions */\n\n.will-root .will-calendar-wrapper .will-calendar-footer-actions-wrapper {\n display: flex;\n justify-content: space-between;\n}\n\n.will-root .will-calendar-wrapper .will-calendar-footer-dates > div {\n margin-bottom: 5px;\n}\n\n.will-root .will-calendar-wrapper .will-calendar-footer-dates-separator {\n margin: 0 15px;\n}\n\n.will-root .will-calendar-wrapper .will-calendar-footer-dates .will-calendar-footer-booked {\n display: flex;\n min-height: 20.5px;\n margin-top: 10px;\n}\n\n.will-root .will-calendar-wrapper .will-calendar-footer-error {\n display: flex;\n max-width: 80%;\n}\n\n.will-root .will-calendar-wrapper .will-calendar-footer-error span {\n display: inline-block;\n margin-left: 10px;\n}\n\n@media (max-width: 960px) {\n .will-root .will-calendar-wrapper {\n width: -webkit-fill-available;\n margin: 0 -6%;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-header,\n .will-root .will-calendar-wrapper .will-calendar-main,\n .will-root .will-calendar-wrapper .will-calendar-footer {\n padding: 20px 10px;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-actions-wrapper {\n flex-direction: column;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-dates {\n text-align: center;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-dates .will-calendar-footer-booked {\n justify-content: center;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-actions {\n flex-direction: column;\n width: 100%;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-actions button{\n width: 100%;\n margin-top: 10px;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-error {\n max-width: 100%;\n }\n\n .will-root .will-calendar-wrapper .will-calendar-footer-error span {\n text-align: center;\n margin-left: 5px;\n }\n }\n\n.will-root .will-calendar-wrapper .will-calendar-header .will-filter-bar-close-button {\n position: initial;\n}";
|
|
12450
12627
|
styleInject(css_248z);
|
|
12451
12628
|
|
|
12452
|
-
function FilterCalendar(
|
|
12629
|
+
function FilterCalendar(props) {
|
|
12630
|
+
return (React.createElement(I18nProvider, { language: props.language },
|
|
12631
|
+
React.createElement(FilterCalendarInner, __assign$2({}, props))));
|
|
12632
|
+
}
|
|
12633
|
+
function FilterCalendarInner(_a) {
|
|
12453
12634
|
var calendarOffset = _a.calendarOffset, language = _a.language, palette = _a.palette, onSubmit = _a.onSubmit, outerDisableCalendarDates = _a.disableCalendarDates, toggleCalendar = _a.toggleCalendar, loadingData = _a.loadingData, setToggleCalendar = _a.setToggleCalendar, requestDates = _a.requestDates, showFeedback = _a.showFeedback, noActiveSelection = _a.noActiveSelection, outerRangeContext = _a.rangeContext;
|
|
12454
12635
|
var themePalette = useTheme({ palette: palette });
|
|
12455
12636
|
// Translations
|