Skip to content

Commit

Permalink
Use i18next plurals
Browse files Browse the repository at this point in the history
  • Loading branch information
tassoevan committed Jan 11, 2024
1 parent 7d9a2c4 commit 6bef693
Show file tree
Hide file tree
Showing 40 changed files with 306 additions and 338 deletions.
2 changes: 1 addition & 1 deletion apps/meteor/.scripts/translation-check.ts
Original file line number Diff line number Diff line change
Expand Up @@ -237,8 +237,8 @@ const checkFiles = async (sourceDirPath: string, sourceLng: string, fix = false)

for await (const { path, json, lng } of translations) {
await checkPlaceholdersFormat({ json, path, fix });
await checkMissingPlurals({ json, path, lng, fix });
await checkExceedingKeys({ json, path, lng, sourceJson, sourceLng, fix });
await checkMissingPlurals({ json, path, lng, fix });
}
};

Expand Down
20 changes: 1 addition & 19 deletions apps/meteor/app/utils/lib/i18n.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,31 +6,13 @@ import { isObject } from '../../../lib/utils/isObject';

export const i18n = i18next.use(sprintf);

type HasCounter = {
counter?: number;
};

const hasCounterProperty = (obj: any): obj is HasCounter => obj?.hasOwnProperty('counter') && typeof obj.counter === 'number';

export const addSprinfToI18n = function (t: (typeof i18n)['t'], i18nInstance?: typeof i18n) {
export const addSprinfToI18n = function (t: (typeof i18n)['t']) {
return function (key: string, ...replaces: any): string {
if (replaces[0] === undefined) {
return t(key, ...replaces);
}

if (isObject(replaces[0]) && !Array.isArray(replaces[0])) {
if (!hasCounterProperty(replaces[0])) {
return t(key, ...replaces);
}

const pluralKey = `${key}_plural`;
const pluralKeyExists = i18nInstance?.exists(pluralKey);
const counter = replaces[0]?.counter;

if (counter !== undefined && pluralKeyExists) {
return counter === 1 ? t(key, ...replaces) : t(pluralKey, ...replaces);
}

return t(key, ...replaces);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { Icon } from '@rocket.chat/fuselage';
import { useConnectionStatus, useTranslation } from '@rocket.chat/ui-contexts';
import type { MouseEventHandler, FC } from 'react';
import type { MouseEventHandler } from 'react';
import React, { useEffect, useRef, useState } from 'react';

import './ConnectionStatusBar.styles.css';
Expand Down Expand Up @@ -45,7 +45,7 @@ const useReconnectCountdown = (
return reconnectCountdown;
};

const ConnectionStatusBar: FC = function ConnectionStatusBar() {
function ConnectionStatusBar() {
const { connected, retryTime, status, reconnect } = useConnectionStatus();
const reconnectCountdown = useReconnectCountdown(retryTime, status);
const t = useTranslation();
Expand All @@ -65,12 +65,7 @@ const ConnectionStatusBar: FC = function ConnectionStatusBar() {
<Icon name='warning' /> {t('meteor_status' as Parameters<typeof t>[0], { context: status })}
</strong>

{status === 'waiting' && (
<>
{' '}
{t(reconnectCountdown === 1 ? 'meteor_status_reconnect_in' : 'meteor_status_reconnect_in_plural', { count: reconnectCountdown })}
</>
)}
{status === 'waiting' && <> {t('meteor_status_reconnect_in', { count: reconnectCountdown })}</>}

{['waiting', 'offline'].includes(status) && (
<>
Expand All @@ -82,6 +77,6 @@ const ConnectionStatusBar: FC = function ConnectionStatusBar() {
)}
</div>
);
};
}

export default ConnectionStatusBar;
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ const DiscussionMetrics = ({ lm, count, rid, drid }: DiscussionMetricsProps): Re
<MessageBlock>
<MessageMetrics>
<MessageMetricsReply data-rid={rid} data-drid={drid} onClick={() => goToRoom(drid)}>
{count ? t('message_counter', { counter: count, count }) : t('Reply')}
{count ? t('message_counter', { count }) : t('Reply')}
</MessageMetricsReply>
<MessageMetricsItem title={lm?.toLocaleString()}>
<MessageMetricsItem.Icon name='clock' />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,17 +42,17 @@ const getBadgeTitle = (
) => {
const title = [] as string[];
if (userMentions) {
title.push(t('mentions_counter', { counter: userMentions }));
title.push(t('mentions_counter', { count: userMentions }));
}
if (threadUnread) {
title.push(t('threads_counter', { counter: threadUnread }));
title.push(t('threads_counter', { count: threadUnread }));
}
if (groupMentions) {
title.push(t('group_mentions_counter', { counter: groupMentions }));
title.push(t('group_mentions_counter', { count: groupMentions }));
}
const count = unread - userMentions - groupMentions;
if (count > 0) {
title.push(t('unread_messages_counter', { counter: count }));
title.push(t('unread_messages_counter', { count }));
}
return title.join(', ');
};
Expand Down
16 changes: 2 additions & 14 deletions apps/meteor/client/sidebar/footer/voip/index.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import type { VoIpCallerInfo } from '@rocket.chat/core-typings';
import { useEndpoint, useTranslation } from '@rocket.chat/ui-contexts';
import type { ReactElement } from 'react';
import React, { useCallback, useMemo, useState } from 'react';
import React, { useCallback, useState } from 'react';

import { useVoipFooterMenu } from '../../../../ee/client/hooks/useVoipFooterMenu';
import {
Expand Down Expand Up @@ -62,18 +62,6 @@ export const VoipFooter = (): ReactElement | null => {
return subtitles[state] || '';
};

const getCallsInQueueText = useMemo((): string => {
if (queueCounter === 0) {
return t('Calls_in_queue_empty');
}

if (queueCounter === 1) {
return t('Calls_in_queue', { calls: queueCounter });
}

return t('Calls_in_queue_plural', { calls: queueCounter });
}, [queueCounter, t]);

if (!('caller' in callerInfo)) {
return <SidebarFooterDefault />;
}
Expand All @@ -91,7 +79,7 @@ export const VoipFooter = (): ReactElement | null => {
togglePause={togglePause}
createRoom={createRoom}
openRoom={openRoom}
callsInQueue={getCallsInQueueText}
callsInQueue={t('Calls_in_queue', { count: queueCounter })}
dispatchEvent={dispatchEvent}
openedRoomInfo={openedRoomInfo}
isEnterprise={isEnterprise}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import { Pagination, Field, FieldLabel, FieldRow } from '@rocket.chat/fuselage';
import { useDebouncedValue, useMediaQuery, useMutableCallback } from '@rocket.chat/fuselage-hooks';
import { useEndpoint, useToastMessageDispatch, useRoute, useTranslation } from '@rocket.chat/ui-contexts';
import { useEndpoint, useToastMessageDispatch, useRoute } from '@rocket.chat/ui-contexts';
import { useQuery } from '@tanstack/react-query';
import type { FC } from 'react';
import React, { useMemo, useState } from 'react';
import { useTranslation } from 'react-i18next';

import FilterByText from '../../../components/FilterByText';
import GenericNoResults from '../../../components/GenericNoResults';
Expand All @@ -23,7 +24,7 @@ import DateRangePicker from './helpers/DateRangePicker';
const ModerationConsoleTable: FC = () => {
const [text, setText] = useState('');
const moderationRoute = useRoute('moderation-console');
const t = useTranslation();
const { t } = useTranslation();
const isDesktopOrLarger = useMediaQuery('(min-width: 1024px)');

const { sortBy, sortDirection, setSort } = useSort<'reports.ts' | 'reports.message.u.username' | 'reports.description' | 'count'>(
Expand Down Expand Up @@ -110,7 +111,7 @@ const ModerationConsoleTable: FC = () => {
{t('Moderation_Report_date')}
</GenericTableHeaderCell>,
<GenericTableHeaderCell key='reports' direction={sortDirection} active={sortBy === 'count'} onClick={setSort} sort='count'>
{t('Moderation_Report_plural')}
{t('Moderation_Report_reports')}
</GenericTableHeaderCell>,
<GenericTableHeaderCell key='actions' width='x48' />,
],
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
import { useEndpoint, useRouter, useSetModal, useToastMessageDispatch, useTranslation } from '@rocket.chat/ui-contexts';
import { useEndpoint, useRouter, useSetModal, useToastMessageDispatch } from '@rocket.chat/ui-contexts';
import { useMutation, useQueryClient } from '@tanstack/react-query';
import React from 'react';
import { useTranslation } from 'react-i18next';

import type { GenericMenuItemProps } from '../../../../components/GenericMenu/GenericMenuItem';
import GenericModal from '../../../../components/GenericModal';

const useDismissUserAction = (userId: string): GenericMenuItemProps => {
const t = useTranslation();
const { t } = useTranslation();
const setModal = useSetModal();
const dispatchToastMessage = useToastMessageDispatch();
const moderationRoute = useRouter();
Expand All @@ -20,7 +21,7 @@ const useDismissUserAction = (userId: string): GenericMenuItemProps => {
dispatchToastMessage({ type: 'error', message: error });
},
onSuccess: () => {
dispatchToastMessage({ type: 'success', message: t('Moderation_Reports_dismissed_plural') });
dispatchToastMessage({ type: 'success', message: t('Moderation_Reports_all_dismissed') });
},
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,12 +19,9 @@ const EnabledAppsCount = ({
}): ReactElement | null => {
const t = useTranslation();

const privateAppsCountText: string = t('Private_Apps_Count_Enabled', { counter: enabled });
const marketplaceAppsCountText: string = t('Apps_Count_Enabled', { counter: enabled });

return (
<GenericResourceUsage
title={context === 'private' ? privateAppsCountText : marketplaceAppsCountText}
title={context === 'private' ? t('Private_Apps_Count_Enabled', { count: enabled }) : t('Apps_Count_Enabled', { count: enabled })}
value={enabled}
max={limit}
percentage={percentage}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ const PruneMessagesWithData = (): ReactElement => {
throw new Error(t('No_messages_found_to_prune'));
}

dispatchToastMessage({ type: 'success', message: t('__count__message_pruned', { counter: count }) });
dispatchToastMessage({ type: 'success', message: t('__count__message_pruned', { count }) });
methods.reset();
} catch (error: unknown) {
dispatchToastMessage({ type: 'error', message: error });
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ const VideoConfListItem = ({
</Avatar.Stack>
<Box mis={4}>
{joinedUsers.length > VIDEOCONF_STACK_MAX_USERS
? t('__usersCount__member_joined', { counter: joinedUsers.length - VIDEOCONF_STACK_MAX_USERS })
? t('__usersCount__member_joined', { count: joinedUsers.length - VIDEOCONF_STACK_MAX_USERS })
: t('joined')}
</Box>
</Box>
Expand Down
29 changes: 19 additions & 10 deletions apps/meteor/packages/rocketchat-i18n/i18n/ar.i18n.json
Original file line number Diff line number Diff line change
Expand Up @@ -706,9 +706,12 @@
"Call": "مكالمة",
"Calling": "يتم الآن الاتصال",
"Call_Center": "مركز الاتصال",
"Calls_in_queue": "{{calls}} من المكالمات الانتظار",
"Calls_in_queue_plural": "{{calls}} من المكالمات الانتظار",
"Calls_in_queue_empty": "قائمة الانتظار فارغة",
"Calls_in_queue_zero": "قائمة الانتظار فارغة",
"Calls_in_queue_one": "{{count}} من المكالمات الانتظار",
"Calls_in_queue_two": "{{count}} من المكالمات الانتظار",
"Calls_in_queue_few": "{{count}} من المكالمات الانتظار",
"Calls_in_queue_many": "{{count}} من المكالمات الانتظار",
"Calls_in_queue_other": "{{count}} من المكالمات الانتظار",
"Call_declined": "تم رفض المكالمة!",
"Call_Information": "معلومات المكالمة",
"Call_provider": "مزود المكالمة",
Expand Down Expand Up @@ -2847,8 +2850,12 @@
"Message_Characther_Limit": "حد أحرف الرسالة",
"Message_Code_highlight": "رمز تمييز قائمة اللغات",
"Message_Code_highlight_Description": "قائمة اللغات المفصولة بفواصل (كل اللغات المدعومة على [highlight.js](https://github.com/highlightjs/highlight.js/tree/11.6.0#supported-languages)) التي سيتم استخدامها لتمييز الكتل البرمجية للتعليمات البرمجية",
"message_counter": "{{counter}} رسالة",
"message_counter_plural": "{{counter}} رسائل",
"message_counter_zero": "{{count}} رسائل",
"message_counter_one": "{{count}} رسالة",
"message_counter_two": "{{count}} رسائل",
"message_counter_few": "{{count}} رسائل",
"message_counter_many": "{{count}} رسائل",
"message_counter_other": "{{count}} رسائل",
"Message_DateFormat": "تنسيق التاريخ",
"Message_DateFormat_Description": "انظر أيضًا: [Moment.js](http://momentjs.com/docs/#/displaying/format/)",
"Message_deleting_blocked": "لا يمكن حذف هذه الرسالة بعد الآن",
Expand Down Expand Up @@ -2941,8 +2948,12 @@
"meteor_status_connecting": "يتم الاتصال الآن...",
"meteor_status_failed": "فشل الاتصال بالخادم",
"meteor_status_offline": "وضع عدم الاتصال.",
"meteor_status_reconnect_in": "المحاولة مرة أخرى خلال ثانية واحدة...",
"meteor_status_reconnect_in_plural": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_reconnect_in_zero": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_reconnect_in_one": "المحاولة مرة أخرى خلال ثانية واحدة...",
"meteor_status_reconnect_in_two": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_reconnect_in_few": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_reconnect_in_many": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_reconnect_in_other": "المحاولة مرة أخرى خلال {{count}} من الثواني...",
"meteor_status_try_now_offline": "الاتصال مرة أخرى",
"meteor_status_try_now_waiting": "المحاولة الآن",
"meteor_status_waiting": "في انتظار اتصال الخادم،",
Expand Down Expand Up @@ -3494,8 +3505,6 @@
"Replied_on": "تم الرد على",
"Replies": "الردود",
"Reply": "رد",
"reply_counter": "{{counter}} رد",
"reply_counter_plural": "{{counter}} ردود",
"Reply_in_direct_message": "الرد في رسالة مباشرة",
"Reply_in_thread": "الرد في موضوع",
"Reply_via_Email": "الرد عبر البريد الإلكتروني",
Expand Down Expand Up @@ -4886,4 +4895,4 @@
"Enterprise": "مؤسسة",
"UpgradeToGetMore_engagement-dashboard_Title": "التحليلات",
"UpgradeToGetMore_auditing_Title": "تدقيق الرسائل"
}
}
18 changes: 8 additions & 10 deletions apps/meteor/packages/rocketchat-i18n/i18n/ca.i18n.json
Original file line number Diff line number Diff line change
Expand Up @@ -704,9 +704,9 @@
"Call": "Trucada",
"Calling": "Trucant",
"Call_Center": "Centre de trucades",
"Calls_in_queue": "{{calls}} Trucada a la cua",
"Calls_in_queue_plural": "{{calls}} Trucades a la cua",
"Calls_in_queue_empty": "La cua és buida",
"Calls_in_queue_zero": "La cua és buida",
"Calls_in_queue_one": "{{count}} Trucada a la cua",
"Calls_in_queue_other": "{{count}} Trucades a la cua",
"Call_declined": "Trucada rebutjada!",
"Call_Information": "Informació de la trucada",
"Call_provider": "Proveïdor de trucades",
Expand Down Expand Up @@ -2820,8 +2820,8 @@
"Message_Characther_Limit": "Límit de caràcters del missatge",
"Message_Code_highlight": "Llista d'idiomes de ressaltat de codi",
"Message_Code_highlight_Description": "Llista d'idiomes separats per comes (tots els idiomes admesos en [highlight.js](https://github.com/highlightjs/highlight.js/tree/11.6.0#supported-languages)) que s'utilitzarà per a ressaltar blocs de codi",
"message_counter": "missatge {{counter}}",
"message_counter_plural": "{{counter}} missatges",
"message_counter_one": "missatge {{count}}",
"message_counter_other": "{{count}} missatges",
"Message_DateFormat": "Format de data",
"Message_DateFormat_Description": "Veure: [Moment.js](http://momentjs.com/docs/#/displaying/format/)",
"Message_deleting_blocked": "Aquest missatge ja no es pot eliminar",
Expand Down Expand Up @@ -2913,8 +2913,8 @@
"meteor_status_connecting": "Connectant...",
"meteor_status_failed": "La connexió del servidor ha fallat",
"meteor_status_offline": "Mode fora de línia",
"meteor_status_reconnect_in": "intentant de nou en un segon ...",
"meteor_status_reconnect_in_plural": "provant de nou d'aquí a {{count}} segons ...",
"meteor_status_reconnect_in_one": "intentant de nou en un segon ...",
"meteor_status_reconnect_in_other": "provant de nou d'aquí a {{count}} segons ...",
"meteor_status_try_now_offline": "Connectar de nou",
"meteor_status_try_now_waiting": "Prova-ho ara",
"meteor_status_waiting": "Esperant la connexió de servidor,",
Expand Down Expand Up @@ -3441,8 +3441,6 @@
"Replied_on": "Va respondre a",
"Replies": "Respostes",
"Reply": "Resposta",
"reply_counter": "{{counter}} resposta",
"reply_counter_plural": "{{counter}} respostes",
"Reply_in_direct_message": "Respondre en missatge directe",
"Reply_in_thread": "Respon en fil",
"Reply_via_Email": "Respondre per correu electrònic",
Expand Down Expand Up @@ -4690,4 +4688,4 @@
"Enterprise": "Empresa",
"UpgradeToGetMore_engagement-dashboard_Title": "Analítiques",
"UpgradeToGetMore_auditing_Title": "Auditoria de missatges"
}
}
16 changes: 9 additions & 7 deletions apps/meteor/packages/rocketchat-i18n/i18n/cs.i18n.json
Original file line number Diff line number Diff line change
Expand Up @@ -2392,8 +2392,10 @@
"Message_BadWordsFilterList": "Přidat sprostá slova na černou listinu",
"Message_BadWordsFilterListDescription": "Zadejte čárkou oddělený seznam sprostých slov k odfiltrování",
"Message_Characther_Limit": "Maximální délka zprávy",
"message_counter": "{{counter}} zpráva",
"message_counter_plural": "{{counter}} zpráv(y)",
"message_counter_one": "{{count}} zpráva",
"message_counter_few": "{{count}} zpráv(y)",
"message_counter_many": "{{count}} zpráv(y)",
"message_counter_other": "{{count}} zpráv(y)",
"Message_DateFormat": "Formát datumu",
"Message_DateFormat_Description": "Viz také: [Moment.js](http://momentjs.com/docs/#/displaying/format/)",
"Message_deleting_blocked": "Tuto zprávu již nelze smazat",
Expand Down Expand Up @@ -2466,8 +2468,10 @@
"meteor_status_connecting": "Připojuji k serveru...",
"meteor_status_failed": "Připojení k serveru selhalo",
"meteor_status_offline": "Offline režim.",
"meteor_status_reconnect_in": "zkusím znovu za sekundu...",
"meteor_status_reconnect_in_plural": "zkusím znovu za {{count}} sekund...",
"meteor_status_reconnect_in_one": "zkusím znovu za sekundu...",
"meteor_status_reconnect_in_few": "zkusím znovu za {{count}} sekund...",
"meteor_status_reconnect_in_many": "zkusím znovu za {{count}} sekund...",
"meteor_status_reconnect_in_other": "zkusím znovu za {{count}} sekund...",
"meteor_status_try_now_offline": "Znovu připojit",
"meteor_status_try_now_waiting": "Zkusit nyní",
"meteor_status_waiting": "Čekám na připojení k serveru,",
Expand Down Expand Up @@ -2926,8 +2930,6 @@
"Replied_on": "Zodpovězeno",
"Replies": "Odpovědi",
"Reply": "Odpověď",
"reply_counter": "{{counter}} odpověď",
"reply_counter_plural": "{{counter}} odpovědí",
"Reply_in_direct_message": "Odpovědět v přímé zprávě",
"Reply_in_thread": "Odpovědět ve vlákně",
"ReplyTo": "Odpovědět na",
Expand Down Expand Up @@ -3965,4 +3967,4 @@
"Enterprise": "Korporace",
"UpgradeToGetMore_engagement-dashboard_Title": "Analytika",
"UpgradeToGetMore_auditing_Title": "Audit zpráv"
}
}
Loading

0 comments on commit 6bef693

Please sign in to comment.