fix: Fix languages

This commit is contained in:
Myzel394 2023-03-05 15:19:21 +01:00
parent a6c80cda0c
commit 067e99926a
No known key found for this signature in database
GPG Key ID: 79CC92F37B3E1A2B
11 changed files with 54 additions and 53 deletions

View File

@ -66,7 +66,7 @@
}, },
"proxyUserAgent": { "proxyUserAgent": {
"label": "Weiterleitungs-User-Agent", "label": "Weiterleitungs-User-Agent",
"helperText": "Ein User Agent ist ein Identifikator, den jeder Browser und E-Mail-Client beim Abrufen von Dateien, wie z.B. Bildern, sendet. Du kannst hier angeben, welcher User Agent verwendet werden soll, wenn wir deine Bilder weiterleiten. User Agents werden auf dem neuesten Stand gehalten." "helperText": "Ein User Agent ist ein Identifikator, den jeder Browser und E-Mail-Client beim Abrufen von Dateien, wie z.B. Bildern, sendet. Du kannst hier angeben, welcher User Agent verwendet werden soll, wenn wir deine Bilder weiterleiten. User Agents werden auf dem neuesten Stand gehalten.",
"values": { "values": {
"apple-mail": "Apple Mail", "apple-mail": "Apple Mail",
"google-mail": "Google Mail", "google-mail": "Google Mail",

View File

@ -15,7 +15,7 @@
"code": { "code": {
"label": "Anmelde-Code", "label": "Anmelde-Code",
"errors": { "errors": {
"invalidChars": "Der Anmelde-Code ist ungültig", "invalidChars": "Der Anmelde-Code ist ungültig"
} }
} }
} }

View File

@ -2,6 +2,6 @@
"title": "Einstellungen", "title": "Einstellungen",
"actions": { "actions": {
"enable2fa": "Zwei-Faktor-Authentifizierung", "enable2fa": "Zwei-Faktor-Authentifizierung",
"aliasPreferences": "Alias Präferenzen" "aliasPreferences": "Alias-Präferenzen"
} }
} }

View File

@ -16,14 +16,17 @@ export const ALIAS_TYPE_ICON_MAP: Record<AliasType, ReactElement> = {
[AliasType.CUSTOM]: <FaHashtag />, [AliasType.CUSTOM]: <FaHashtag />,
} }
const ALIAS_TYPE_TOOLTIP_MAP = createEnumMapFromTranslation("aliasTypeExplanation", AliasType)
export default function AliasTypeIndicator({type}: AliasTypeIndicatorProps): ReactElement { export default function AliasTypeIndicator({type}: AliasTypeIndicatorProps): ReactElement {
const {t} = useTranslation("aliases") const {t} = useTranslation("aliases")
const aliasTypeTooltipMap = createEnumMapFromTranslation(
"aliasTypeExplanation",
AliasType,
)(key => t(key))
return ( return (
// @ts-ignore // @ts-ignore
<Tooltip title={t(ALIAS_TYPE_TOOLTIP_MAP[type] as string)} arrow> <Tooltip title={t(aliasTypeTooltipMap[type] as string)} arrow>
<Box display="flex" justifyContent="center" alignItems="center"> <Box display="flex" justifyContent="center" alignItems="center">
{ALIAS_TYPE_ICON_MAP[type]} {ALIAS_TYPE_ICON_MAP[type]}
</Box> </Box>

View File

@ -1,11 +0,0 @@
import {ImageProxyFormatType, ProxyUserAgentType} from "~/server-types"
import {createEnumMapFromTranslation} from "~/utils"
export const IMAGE_PROXY_FORMAT_TYPE_NAME_MAP = createEnumMapFromTranslation(
"settings.fields.imageProxyFormat.values",
ImageProxyFormatType,
)
export const PROXY_USER_AGENT_TYPE_NAME_MAP = createEnumMapFromTranslation(
"settings.fields.proxyUserAgent.values",
ProxyUserAgentType,
)

View File

@ -13,11 +13,7 @@ import {QueryKey, useMutation} from "@tanstack/react-query"
import {Alias, DecryptedAlias, ImageProxyFormatType, ProxyUserAgentType} from "~/server-types" import {Alias, DecryptedAlias, ImageProxyFormatType, ProxyUserAgentType} from "~/server-types"
import {UpdateAliasData, updateAlias} from "~/apis" import {UpdateAliasData, updateAlias} from "~/apis"
import {parseFastAPIError} from "~/utils" import {createEnumMapFromTranslation, parseFastAPIError} from "~/utils"
import {
IMAGE_PROXY_FORMAT_TYPE_NAME_MAP,
PROXY_USER_AGENT_TYPE_NAME_MAP,
} from "~/constants/enum-mappings"
import {useErrorSuccessSnacks} from "~/hooks" import {useErrorSuccessSnacks} from "~/hooks"
import {queryClient} from "~/constants/react-query" import {queryClient} from "~/constants/react-query"
import {AuthContext, FormikAutoLockNavigation} from "~/components" import {AuthContext, FormikAutoLockNavigation} from "~/components"
@ -48,6 +44,15 @@ export default function AliasPreferencesForm({
const {showSuccess, showError} = useErrorSuccessSnacks() const {showSuccess, showError} = useErrorSuccessSnacks()
const {_decryptUsingMasterPassword} = useContext(AuthContext) const {_decryptUsingMasterPassword} = useContext(AuthContext)
const imageProxyMap = createEnumMapFromTranslation(
"settings.fields.imageProxyFormat.values",
ImageProxyFormatType,
)(key => t(key))
const imageProxyUserAgentMap = createEnumMapFromTranslation(
"settings.fields.proxyUserAgent.values",
ProxyUserAgentType,
)(key => t(key))
const schema = yup.object().shape({ const schema = yup.object().shape({
removeTrackers: yup removeTrackers: yup
.mixed<boolean | null>() .mixed<boolean | null>()
@ -164,9 +169,7 @@ export default function AliasPreferencesForm({
formik={formik} formik={formik}
icon={<FaFile />} icon={<FaFile />}
name="imageProxyFormat" name="imageProxyFormat"
valueTextMap={ valueTextMap={imageProxyMap}
IMAGE_PROXY_FORMAT_TYPE_NAME_MAP
}
/> />
</Grid> </Grid>
<Grid item xs={12} sm={6}> <Grid item xs={12} sm={6}>
@ -176,9 +179,7 @@ export default function AliasPreferencesForm({
)} )}
formik={formik} formik={formik}
name="proxyUserAgent" name="proxyUserAgent"
valueTextMap={ valueTextMap={imageProxyUserAgentMap}
PROXY_USER_AGENT_TYPE_NAME_MAP
}
/> />
</Grid> </Grid>
</Grid> </Grid>

View File

@ -30,17 +30,17 @@ export default function SelectField({
valueTextMap: parentValueTextMap, valueTextMap: parentValueTextMap,
}: SelectFieldProps): ReactElement { }: SelectFieldProps): ReactElement {
const user = useUser() const user = useUser()
const {t} = useTranslation("components") const {t} = useTranslation(["components", "aliases"])
const BOOLEAN_SELECT_TEXT_MAP: Record<string, string> = { const BOOLEAN_SELECT_TEXT_MAP: Record<string, string> = {
true: "SelectField.values.true", true: t("SelectField.values.true"),
false: "SelectField.values.false", false: t("SelectField.values.false"),
} }
const valueTextMap = parentValueTextMap ?? BOOLEAN_SELECT_TEXT_MAP const valueTextMap = parentValueTextMap ?? BOOLEAN_SELECT_TEXT_MAP
const labelId = `${name}-label` const labelId = `${name}-label`
const preferenceName = `alias${name.charAt(0).toUpperCase() + name.slice(1)}` const preferenceName = `alias${name.charAt(0).toUpperCase() + name.slice(1)}`
const value = user.preferences[preferenceName as keyof User["preferences"]] const value = user.preferences[preferenceName as keyof User["preferences"]]
const defaultValueText = t(valueTextMap[value.toString()]) const defaultValueText = valueTextMap[value.toString()]
return ( return (
<FormControl fullWidth> <FormControl fullWidth>
@ -81,7 +81,7 @@ export default function SelectField({
})} })}
</i> </i>
) : ( ) : (
t(valueTextMap[value.toString()]) valueTextMap[value.toString()]
) )
} }
> >
@ -95,7 +95,7 @@ export default function SelectField({
{valueTextMap && {valueTextMap &&
Object.entries(valueTextMap).map(([value, translationString]) => ( Object.entries(valueTextMap).map(([value, translationString]) => (
<MenuItem key={value} value={value}> <MenuItem key={value} value={value}>
{t(translationString)} {translationString}
</MenuItem> </MenuItem>
))} ))}
</Select> </Select>

View File

@ -36,7 +36,7 @@ function ReportDetailRoute(): ReactElement {
<DeleteButton <DeleteButton
onDelete={() => deleteReport(params.id!)} onDelete={() => deleteReport(params.id!)}
label={t("actions.delete.label")} label={t("actions.delete.label")}
description={t("delete.description")} description={t("actions.delete.description")}
continueLabel={t("actions.delete.continueActionLabel")} continueLabel={t("actions.delete.continueActionLabel")}
navigateTo={"/reports"} navigateTo={"/reports"}
successMessage={t("messages.report.deleted", {ns: "common"})} successMessage={t("messages.report.deleted", {ns: "common"})}

View File

@ -26,14 +26,15 @@ const SORTING_VIEW_ICON_MAP: Record<SortingView, ReactElement> = {
[SortingView.List]: <MdList />, [SortingView.List]: <MdList />,
[SortingView.GroupByAlias]: <FaMask />, [SortingView.GroupByAlias]: <FaMask />,
} }
const SORTING_VIEW_NAME_MAP: Record<SortingView, string> = createEnumMapFromTranslation(
"pageActions.sort.values",
SortingView,
)
function ReportsRoute(): ReactElement { function ReportsRoute(): ReactElement {
const {t} = useTranslation("reports") const {t} = useTranslation("reports")
const sortingViewNameMap = createEnumMapFromTranslation(
"pageActions.sort.values",
SortingView,
)(key => t(key))
const query = useQuery<PaginationResult<Report>, AxiosError>(["get_reports"], getReports) const query = useQuery<PaginationResult<Report>, AxiosError>(["get_reports"], getReports)
const [sortingView, setSortingView] = useState<SortingView>(SortingView.List) const [sortingView, setSortingView] = useState<SortingView>(SortingView.List)
@ -57,9 +58,9 @@ function ReportsRoute(): ReactElement {
}} }}
select select
> >
{Object.keys(SORTING_VIEW_NAME_MAP).map(name => ( {Object.keys(sortingViewNameMap).map(name => (
<MenuItem key={name} value={name}> <MenuItem key={name} value={name}>
{t(SORTING_VIEW_NAME_MAP[name as SortingView])} {t(sortingViewNameMap[name as SortingView])}
</MenuItem> </MenuItem>
))} ))}
</TextField> </TextField>

View File

@ -25,11 +25,7 @@ import {LoadingButton} from "@mui/lab"
import {ImageProxyFormatType, ProxyUserAgentType, SimpleDetailResponse} from "~/server-types" import {ImageProxyFormatType, ProxyUserAgentType, SimpleDetailResponse} from "~/server-types"
import {UpdatePreferencesData, updatePreferences} from "~/apis" import {UpdatePreferencesData, updatePreferences} from "~/apis"
import {useErrorSuccessSnacks, useUser} from "~/hooks" import {useErrorSuccessSnacks, useUser} from "~/hooks"
import {parseFastAPIError} from "~/utils" import {createEnumMapFromTranslation, parseFastAPIError} from "~/utils"
import {
IMAGE_PROXY_FORMAT_TYPE_NAME_MAP,
PROXY_USER_AGENT_TYPE_NAME_MAP,
} from "~/constants/enum-mappings"
import {AuthContext, SimplePageBuilder} from "~/components" import {AuthContext, SimplePageBuilder} from "~/components"
interface Form { interface Form {
@ -49,6 +45,15 @@ export default function SettingsAliasPreferencesRoute(): ReactElement {
const user = useUser() const user = useUser()
const {showError, showSuccess} = useErrorSuccessSnacks() const {showError, showSuccess} = useErrorSuccessSnacks()
const imageProxyMap = createEnumMapFromTranslation(
"settings.fields.imageProxyFormat.values",
ImageProxyFormatType,
)(key => t(key))
const imageProxyUserAgentMap = createEnumMapFromTranslation(
"settings.fields.proxyUserAgent.values",
ProxyUserAgentType,
)(key => t(key))
const schema = yup.object().shape({ const schema = yup.object().shape({
removeTrackers: yup.boolean().label(t("settings.fields.removeTrackers.label")), removeTrackers: yup.boolean().label(t("settings.fields.removeTrackers.label")),
createMailReport: yup.boolean().label(t("settings.fields.createMailReport.label")), createMailReport: yup.boolean().label(t("settings.fields.createMailReport.label")),
@ -251,7 +256,7 @@ export default function SettingsAliasPreferencesRoute(): ReactElement {
formik.errors.imageProxyFormat formik.errors.imageProxyFormat
} }
> >
{Object.entries(IMAGE_PROXY_FORMAT_TYPE_NAME_MAP).map( {Object.entries(imageProxyMap).map(
([value, translationString]) => ( ([value, translationString]) => (
<MenuItem key={value} value={value}> <MenuItem key={value} value={value}>
{t(translationString)} {t(translationString)}
@ -292,7 +297,7 @@ export default function SettingsAliasPreferencesRoute(): ReactElement {
formik.touched.proxyUserAgent && formik.errors.proxyUserAgent formik.touched.proxyUserAgent && formik.errors.proxyUserAgent
} }
> >
{Object.entries(PROXY_USER_AGENT_TYPE_NAME_MAP).map( {Object.entries(imageProxyUserAgentMap).map(
([value, translationString]) => ( ([value, translationString]) => (
<MenuItem key={value} value={value}> <MenuItem key={value} value={value}>
{t(translationString)} {t(translationString)}

View File

@ -1,9 +1,11 @@
type TranslationFunction = (key: string) => string
export default function createEnumMapFromTranslation<T extends Record<string, string>>( export default function createEnumMapFromTranslation<T extends Record<string, string>>(
prefix: string, prefix: string,
TEnum: T, TEnum: T,
): Record<keyof T, string> { ): (callback: TranslationFunction) => Record<keyof T, string> {
return Object.fromEntries(Object.values(TEnum).map(key => [key, `${prefix}.${key}`])) as Record< return callback =>
keyof T, Object.fromEntries(
string Object.values(TEnum).map(key => [key, callback(`${prefix}.${key}`)]),
> ) as Record<keyof T, string>
} }