From 46b5faab31c09b19600468887cfbe215e1590cb9 Mon Sep 17 00:00:00 2001 From: Sorin Davidoi Date: Tue, 19 Nov 2024 00:31:29 +0200 Subject: [PATCH] fix(lang): respect fallback languages If `navigator.languages` returns `['da', 'en-US', 'en']`, and the Danish language is not available, the user interface should be in English. Currently it is shown in Norwegian, because only `'da'` is taken into account when deciding on the preferred language (and `match` selects `nb-NO` using the default `'best fit'` algorithm). While the Norwegian and Danish languages are similar, I would argue that this is a bug, as `navigator.languages` cleary states that the fallback language should be English. Another potential solution would be to pass `{ algorithm: 'lookup' }` to the `match` function. However, this might break some cases when a `'best fit'` approach would be appropriate (e.g. Swiss German falling back to German). See https://helvede.net/@jwcph/113497955274343365. --- src/utils/lang.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/utils/lang.js b/src/utils/lang.js index 2ef1b135..9a147c28 100644 --- a/src/utils/lang.js +++ b/src/utils/lang.js @@ -1,9 +1,9 @@ import { i18n } from '@lingui/core'; import { - detect, fromNavigator, fromStorage, fromUrl, + multipleDetect, } from '@lingui/detect-locale'; import Locale from 'intl-locale-textinfo-polyfill'; @@ -54,7 +54,7 @@ export async function activateLang(lang) { } export function initActivateLang() { - const lang = detect( + const languages = multipleDetect( fromUrl('lang'), fromStorage('lang'), fromNavigator(), @@ -62,7 +62,8 @@ export function initActivateLang() { DEFAULT_LANG, ); const matchedLang = - ALL_LOCALES.find((l) => l === lang) || localeMatch(lang, ALL_LOCALES); + languages.find((l) => ALL_LOCALES.includes(l)) || + localeMatch(languages, ALL_LOCALES); activateLang(matchedLang); // const yes = confirm(t`Reload to apply language setting?`);