Fix missing "custom app languages"

Regression c1ac58f4d6
This commit is contained in:
schroda
2026-01-14 16:33:37 +01:00
parent 65a9a905be
commit 0fd5bb3284
6 changed files with 24 additions and 17 deletions

View File

@@ -21,8 +21,7 @@ import { Virtuoso } from 'react-virtuoso';
import { useLingui } from '@lingui/react/macro'; import { useLingui } from '@lingui/react/macro';
import { CustomTooltip } from '@/base/components/CustomTooltip.tsx'; import { CustomTooltip } from '@/base/components/CustomTooltip.tsx';
import { translateExtensionLanguage } from '@/features/extension/Extensions.utils.ts'; import { translateExtensionLanguage } from '@/features/extension/Extensions.utils.ts';
import { languageSortComparator } from '@/base/utils/Languages.ts'; import { languageSortComparator, toUniqueLanguageCodes } from '@/base/utils/Languages.ts';
import { toUniqueISOLanguageCodes } from '@/lib/ISOLanguageUtil.ts';
interface IProps { interface IProps {
selectedLanguages: string[]; selectedLanguages: string[];
@@ -34,12 +33,12 @@ export function LanguageSelect(props: IProps) {
const { t } = useLingui(); const { t } = useLingui();
const { selectedLanguages, setSelectedLanguages, languages } = props; const { selectedLanguages, setSelectedLanguages, languages } = props;
const [tmpSelectedLanguages, setTmpSelectedLanguages] = useState(toUniqueISOLanguageCodes(selectedLanguages)); const [tmpSelectedLanguages, setTmpSelectedLanguages] = useState(toUniqueLanguageCodes(selectedLanguages));
const [open, setOpen] = useState<boolean>(false); const [open, setOpen] = useState<boolean>(false);
const languagesSortedBySelectState = useMemo( const languagesSortedBySelectState = useMemo(
() => () =>
toUniqueISOLanguageCodes([ toUniqueLanguageCodes([
...tmpSelectedLanguages.toSorted(languageSortComparator), ...tmpSelectedLanguages.toSorted(languageSortComparator),
...languages.toSorted(languageSortComparator), ...languages.toSorted(languageSortComparator),
]), ]),
@@ -48,12 +47,12 @@ export function LanguageSelect(props: IProps) {
const handleCancel = () => { const handleCancel = () => {
setOpen(false); setOpen(false);
setTmpSelectedLanguages(toUniqueISOLanguageCodes(selectedLanguages)); setTmpSelectedLanguages(toUniqueLanguageCodes(selectedLanguages));
}; };
const handleOk = () => { const handleOk = () => {
setOpen(false); setOpen(false);
setSelectedLanguages(toUniqueISOLanguageCodes(tmpSelectedLanguages)); setSelectedLanguages(toUniqueLanguageCodes(tmpSelectedLanguages));
}; };
const handleChange = (language: string, selected: boolean) => { const handleChange = (language: string, selected: boolean) => {

View File

@@ -53,6 +53,15 @@ export function languageCodeToName(code: string): string {
return getLanguage(code).nativeName; return getLanguage(code).nativeName;
} }
export const toUniqueLanguageCodes = (codes: string[]): string[] => {
const languages = codes.map((code) => getLanguage(code));
const languagesByIsoCode = Object.groupBy(languages, (language) => language.isoCode);
return Object.entries(languagesByIsoCode)
.filter(([, languagesOfIsoCode]) => !!languagesOfIsoCode?.length)
.map(([, languagesOfIsoCode]) => languagesOfIsoCode![0].orgCode);
};
export const toComparableLanguage = (code: string): string => getLanguage(code).isoCode; export const toComparableLanguage = (code: string): string => getLanguage(code).isoCode;
export const toComparableLanguages = (codes: string[]): string[] => codes.map(toComparableLanguage); export const toComparableLanguages = (codes: string[]): string[] => codes.map(toComparableLanguage);

View File

@@ -20,6 +20,7 @@ import {
languageSpecialSortComparator, languageSpecialSortComparator,
toComparableLanguage, toComparableLanguage,
toComparableLanguages, toComparableLanguages,
toUniqueLanguageCodes,
} from '@/base/utils/Languages.ts'; } from '@/base/utils/Languages.ts';
import { import {
EXTENSION_ACTION_TO_FAILURE_TRANSLATION_MAP, EXTENSION_ACTION_TO_FAILURE_TRANSLATION_MAP,
@@ -29,7 +30,6 @@ import { enhancedCleanup } from '@/base/utils/Strings.ts';
import { requestManager } from '@/lib/requests/RequestManager.ts'; import { requestManager } from '@/lib/requests/RequestManager.ts';
import { makeToast } from '@/base/utils/Toast.ts'; import { makeToast } from '@/base/utils/Toast.ts';
import { getErrorMessage } from '@/lib/HelperFunctions.ts'; import { getErrorMessage } from '@/lib/HelperFunctions.ts';
import { toUniqueISOLanguageCodes } from '@/lib/ISOLanguageUtil.ts';
import { i18n } from '@/i18n'; import { i18n } from '@/i18n';
export const getInstalledState = ( export const getInstalledState = (
@@ -131,7 +131,7 @@ export const filterExtensions = (
query?: string | null | undefined; query?: string | null | undefined;
} = {}, } = {},
): TExtension[] => { ): TExtension[] => {
const normalizedSelectedLanguages = toComparableLanguages(toUniqueISOLanguageCodes(selectedLanguages ?? [])); const normalizedSelectedLanguages = toComparableLanguages(toUniqueLanguageCodes(selectedLanguages ?? []));
return extensions return extensions
.filter( .filter(

View File

@@ -23,7 +23,7 @@ import ListItemAvatar from '@mui/material/ListItemAvatar';
import { useLingui } from '@lingui/react/macro'; import { useLingui } from '@lingui/react/macro';
import { CustomTooltip } from '@/base/components/CustomTooltip.tsx'; import { CustomTooltip } from '@/base/components/CustomTooltip.tsx';
import { translateExtensionLanguage } from '@/features/extension/Extensions.utils.ts'; import { translateExtensionLanguage } from '@/features/extension/Extensions.utils.ts';
import { languageSortComparator } from '@/base/utils/Languages.ts'; import { languageSortComparator, toUniqueLanguageCodes } from '@/base/utils/Languages.ts';
import { import {
SourceDisplayNameInfo, SourceDisplayNameInfo,
SourceIconInfo, SourceIconInfo,
@@ -38,7 +38,6 @@ import { requestManager } from '@/lib/requests/RequestManager.ts';
import { ListCardAvatar } from '@/base/components/lists/cards/ListCardAvatar.tsx'; import { ListCardAvatar } from '@/base/components/lists/cards/ListCardAvatar.tsx';
import { makeToast } from '@/base/utils/Toast.ts'; import { makeToast } from '@/base/utils/Toast.ts';
import { getErrorMessage } from '@/lib/HelperFunctions.ts'; import { getErrorMessage } from '@/lib/HelperFunctions.ts';
import { toUniqueISOLanguageCodes } from '@/lib/ISOLanguageUtil.ts';
export const SourceLanguageSelect = ({ export const SourceLanguageSelect = ({
selectedLanguages, selectedLanguages,
@@ -60,14 +59,14 @@ export const SourceLanguageSelect = ({
const [tmpSourceIdToEnabledState, setTmpSourceIdToEnabledState] = useState<Record<SourceIdInfo['id'], boolean>>({}); const [tmpSourceIdToEnabledState, setTmpSourceIdToEnabledState] = useState<Record<SourceIdInfo['id'], boolean>>({});
const [tmpSelectedLanguages, setTmpSelectedLanguages] = useState(toUniqueISOLanguageCodes(selectedLanguages)); const [tmpSelectedLanguages, setTmpSelectedLanguages] = useState(toUniqueLanguageCodes(selectedLanguages));
const [open, setOpen] = useState<boolean>(false); const [open, setOpen] = useState<boolean>(false);
const sourcesByLanguage = useMemo(() => Sources.groupByLanguage(sources), [sources]); const sourcesByLanguage = useMemo(() => Sources.groupByLanguage(sources), [sources]);
const languagesSortedBySelectState = useMemo( const languagesSortedBySelectState = useMemo(
() => () =>
toUniqueISOLanguageCodes([ toUniqueLanguageCodes([
...tmpSelectedLanguages.toSorted(languageSortComparator), ...tmpSelectedLanguages.toSorted(languageSortComparator),
...languages.toSorted(languageSortComparator), ...languages.toSorted(languageSortComparator),
]), ]),
@@ -78,7 +77,7 @@ export const SourceLanguageSelect = ({
setOpen(false); setOpen(false);
setTmpSourceIdToEnabledState({}); setTmpSourceIdToEnabledState({});
setTmpSelectedLanguages(toUniqueISOLanguageCodes(selectedLanguages)); setTmpSelectedLanguages(toUniqueLanguageCodes(selectedLanguages));
}; };
const handleOk = () => { const handleOk = () => {
@@ -90,7 +89,7 @@ export const SourceLanguageSelect = ({
), ),
).catch((e) => makeToast(t`Failed to save changes`, 'error', getErrorMessage(e))); ).catch((e) => makeToast(t`Failed to save changes`, 'error', getErrorMessage(e)));
setTmpSourceIdToEnabledState({}); setTmpSourceIdToEnabledState({});
setSelectedLanguages(toUniqueISOLanguageCodes(tmpSelectedLanguages)); setSelectedLanguages(toUniqueLanguageCodes(tmpSelectedLanguages));
}; };
const handleChange = (language: string, selected: boolean) => { const handleChange = (language: string, selected: boolean) => {

View File

@@ -21,6 +21,7 @@ import {
languageSpecialSortComparator, languageSpecialSortComparator,
toComparableLanguage, toComparableLanguage,
toComparableLanguages, toComparableLanguages,
toUniqueLanguageCodes,
} from '@/base/utils/Languages.ts'; } from '@/base/utils/Languages.ts';
import { getSourceMetadata } from '@/features/source/services/SourceMetadata.ts'; import { getSourceMetadata } from '@/features/source/services/SourceMetadata.ts';
import { import {
@@ -29,7 +30,6 @@ import {
} from '@/features/settings/services/ServerSettingsMetadata.ts'; } from '@/features/settings/services/ServerSettingsMetadata.ts';
import { makeToast } from '@/base/utils/Toast.ts'; import { makeToast } from '@/base/utils/Toast.ts';
import { getErrorMessage } from '@/lib/HelperFunctions.ts'; import { getErrorMessage } from '@/lib/HelperFunctions.ts';
import { toUniqueISOLanguageCodes } from '@/lib/ISOLanguageUtil.ts';
export class Sources { export class Sources {
static readonly LOCAL_SOURCE_ID = '0'; static readonly LOCAL_SOURCE_ID = '0';
@@ -98,7 +98,7 @@ export class Sources {
enabled?: boolean; enabled?: boolean;
} = {}, } = {},
): Source[] { ): Source[] {
const normalizedLanguages = toComparableLanguages(toUniqueISOLanguageCodes(languages ?? [])); const normalizedLanguages = toComparableLanguages(toUniqueLanguageCodes(languages ?? []));
return sources return sources
.filter( .filter(

View File

@@ -101,7 +101,7 @@ export function getISOLanguage(code: string): LanguageObject | null {
); );
} }
export const toUniqueISOLanguageCodes = (codes: string[]): string[] => { const toUniqueISOLanguageCodes = (codes: string[]): string[] => {
const languages = codes.map((code) => getISOLanguage(code)).filter((code) => code !== null); const languages = codes.map((code) => getISOLanguage(code)).filter((code) => code !== null);
const languagesByIsoCode = Object.groupBy(languages, (language) => language.isoCode); const languagesByIsoCode = Object.groupBy(languages, (language) => language.isoCode);