Skip to content

Commit ed447f5

Browse files
committed
fix: complete i18n configuration and translations
Normalize locale detection, sync document language direction, complete locale keys, and add i18n regression coverage. Refs rustfs/rustfs#2735
1 parent 92e0213 commit ed447f5

21 files changed

Lines changed: 1923 additions & 159 deletions

components/providers/i18n-provider.tsx

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
"use client"
22

33
import { useEffect, useRef, useState } from "react"
4-
import { initI18n, RTL_LOCALES } from "@/lib/i18n"
4+
import { DEFAULT_LOCALE, initI18n, isRtlLocale, normalizeLocale } from "@/lib/i18n"
55
import { DirectionProvider } from "@/components/ui/direction"
66
import i18n from "i18next"
77

88
type Dir = "ltr" | "rtl"
99

1010
function getDir(lang: string): Dir {
11-
return RTL_LOCALES.has(lang.split("-")[0]) ? "rtl" : "ltr"
11+
return isRtlLocale(lang) ? "rtl" : "ltr"
1212
}
1313

1414
export function I18nProvider({ children }: { children: React.ReactNode }) {
@@ -17,7 +17,9 @@ export function I18nProvider({ children }: { children: React.ReactNode }) {
1717
const mountedRef = useRef(true)
1818

1919
const applyDir = (lang: string) => {
20+
const locale = normalizeLocale(lang)
2021
const d = getDir(lang)
22+
document.documentElement.lang = locale
2123
document.documentElement.dir = d
2224
setDir(d)
2325
}
@@ -27,12 +29,15 @@ export function I18nProvider({ children }: { children: React.ReactNode }) {
2729
initI18n()
2830
.then(() => {
2931
if (mountedRef.current) {
30-
applyDir(i18n.language ?? "en")
32+
applyDir(i18n.resolvedLanguage ?? i18n.language ?? DEFAULT_LOCALE)
3133
setReady(true)
3234
}
3335
})
3436
.catch(() => {
35-
if (mountedRef.current) setReady(true)
37+
if (mountedRef.current) {
38+
applyDir(DEFAULT_LOCALE)
39+
setReady(true)
40+
}
3641
})
3742

3843
const handler = (lng: string) => applyDir(lng)

i18n/locales/ar-MA.json

Lines changed: 127 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -708,8 +708,6 @@
708708
"Send events via MQTT broker": "إرسال الأحداث عبر وسيط MQTT",
709709
"Send events via NATS": "إرسال الأحداث عبر NATS",
710710
"Send events via Pulsar": "إرسال الأحداث عبر Pulsar",
711-
"Send events via NATS": "إرسال الأحداث عبر NATS",
712-
"Send events via Pulsar": "إرسال الأحداث عبر Pulsar",
713711
"Server Address": "عنوان الخادم",
714712
"Server Configuration": "إعداد الخادم",
715713
"Server Host": "مضيف الخادم",
@@ -1098,8 +1096,8 @@
10981096
"Failed to save OIDC provider": "فشل حفظ موفر OIDC",
10991097
"Failed to validate OIDC configuration": "فشل التحقق من إعدادات OIDC",
11001098
"Groups Claim": "مطالبة المجموعات",
1101-
"Roles Claim": "Roles Claim",
1102-
"Optional. Separate claim for role values (e.g. roles). Leave empty to use groups claim only.": "Optional. Separate claim for role values (e.g. roles). Leave empty to use groups claim only.",
1099+
"Roles Claim": "مطالبة الأدوار",
1100+
"Optional. Separate claim for role values (e.g. roles). Leave empty to use groups claim only.": "اختياري. مطالبة منفصلة لقيم الأدوار (مثل roles). اتركه فارغًا لاستخدام مطالبة المجموعات فقط.",
11031101
"Issuer": "الجهة المصدّرة",
11041102
"Leave empty to keep current secret": "اتركه فارغًا للاحتفاظ بالسر الحالي",
11051103
"Loading...": "جارٍ التحميل...",
@@ -1136,5 +1134,129 @@
11361134
"Validate": "تحقق",
11371135
"Validating...": "جارٍ التحقق...",
11381136
"View and manage persisted OIDC providers.": "اعرض وأدر موفري OIDC المحفوظين.",
1139-
"You have unsaved OIDC changes. Do you want to discard them?": "لديك تغييرات OIDC غير محفوظة. هل تريد تجاهلها؟"
1137+
"You have unsaved OIDC changes. Do you want to discard them?": "لديك تغييرات OIDC غير محفوظة. هل تريد تجاهلها؟",
1138+
"a": "a",
1139+
"Add {type} Audit Target": "إضافة هدف تدقيق {type}",
1140+
"Add Audit Target": "إضافة هدف تدقيق",
1141+
"API not ready": "واجهة API غير جاهزة",
1142+
"Are you sure you want to delete this audit target?": "هل أنت متأكد من حذف هدف التدقيق هذا؟",
1143+
"Are you sure you want to delete this tag?": "هل أنت متأكد من حذف هذه العلامة؟",
1144+
"Are you sure you want to delete this user?": "هل أنت متأكد من حذف هذا المستخدم؟",
1145+
"ARN": "ARN",
1146+
"Audit is disabled": "التدقيق معطل",
1147+
"Audit is disabled. Enable audit before managing audit targets.": "التدقيق معطل. فعّل التدقيق قبل إدارة أهداف التدقيق.",
1148+
"Audit target created successfully": "تم إنشاء هدف التدقيق بنجاح",
1149+
"Audit Targets": "أهداف التدقيق",
1150+
"AWS S3": "AWS S3",
1151+
"Back to Login": "العودة إلى تسجيل الدخول",
1152+
"Bucket name is required": "اسم الحاوية مطلوب",
1153+
"Bucket names must be 3-63 characters long": "يجب أن يتراوح طول أسماء الحاويات بين 3 و63 حرفًا",
1154+
"Bucket names must not contain uppercase letters": "يجب ألا تحتوي أسماء الحاويات على أحرف كبيرة",
1155+
"Bucket not found": "لم يتم العثور على الحاوية",
1156+
"Cancel Deletion": "إلغاء الحذف",
1157+
"Cancel Key Deletion": "إلغاء حذف المفتاح",
1158+
"Client ID is required": "معرف العميل مطلوب",
1159+
"Collecting files": "جارٍ جمع الملفات",
1160+
"Collects and displays key performance indicators (such as CPU, memory, disk I/O, etc.) through visualized charts to help users understand system operation status and performance bottlenecks": "يجمع ويعرض مؤشرات الأداء الرئيسية مثل المعالج والذاكرة وإدخال/إخراج القرص عبر مخططات مرئية لمساعدة المستخدمين على فهم حالة تشغيل النظام واختناقات الأداء",
1161+
"Comma-separated audience IDs.": "معرفات الجمهور مفصولة بفواصل.",
1162+
"Console": "Console",
1163+
"Content Type": "نوع المحتوى",
1164+
"Controlled by {envKey}": "يتحكم فيه {envKey}",
1165+
"Copy Path": "نسخ المسار",
1166+
"Create an audit target to forward audit logs.": "أنشئ هدف تدقيق لإعادة توجيه سجلات التدقيق.",
1167+
"Current backend status for replicated buckets, users, groups, policies, and lifecycle expiry rules.": "حالة الخلفية الحالية للحاويات والمستخدمين والمجموعات والسياسات وقواعد انتهاء دورة الحياة المنسوخة.",
1168+
"Default": "افتراضي",
1169+
"Delete Tag": "حذف العلامة",
1170+
"Delete task created": "تم إنشاء مهمة الحذف",
1171+
"Deletion Date": "تاريخ الحذف",
1172+
"Detailed site replication status is not available on this server yet. Basic peer information is still shown below.": "حالة نسخ الموقع التفصيلية غير متاحة بعد على هذا الخادم. لا تزال معلومات النظراء الأساسية معروضة أدناه.",
1173+
"div": "div",
1174+
"Download Failed": "فشل التنزيل",
1175+
"Download ready": "التنزيل جاهز",
1176+
"Downloading files": "جارٍ تنزيل الملفات",
1177+
"e.g., app-default": "e.g., app-default",
1178+
"e.g., https://vault.example.com:8200": "e.g., https://vault.example.com:8200",
1179+
"Each remote site needs an endpoint and administrator credentials so the cluster can complete the join handshake.": "يحتاج كل موقع بعيد إلى نقطة نهاية وبيانات اعتماد مسؤول حتى يتمكن العنقود من إكمال مصافحة الانضمام.",
1180+
"Each remote site uses its administrator credentials to complete the initial replication handshake.": "يستخدم كل موقع بعيد بيانات اعتماد المسؤول الخاصة به لإكمال مصافحة النسخ الأولية.",
1181+
"Enable audit in Settings before managing audit targets.": "فعّل التدقيق في الإعدادات قبل إدارة أهداف التدقيق.",
1182+
"Enable notify in Settings before managing bucket event subscriptions.": "فعّل الإشعارات في الإعدادات قبل إدارة اشتراكات أحداث الحاوية.",
1183+
"Enable notify in Settings before managing event destinations.": "فعّل الإشعارات في الإعدادات قبل إدارة وجهات الأحداث.",
1184+
"Enter prefix...": "أدخل البادئة...",
1185+
"ENV": "ENV",
1186+
"Environment variables are controlling some switches": "تتحكم متغيرات البيئة في بعض المفاتيح",
1187+
"Example: http://localhost:9000 or https://your-domain.com": "Example: http://localhost:9000 or https://your-domain.com",
1188+
"Exit Fullscreen": "الخروج من وضع ملء الشاشة",
1189+
"Failed to create audit target": "فشل إنشاء هدف التدقيق",
1190+
"Failed to generate secure random keys": "فشل إنشاء مفاتيح عشوائية آمنة",
1191+
"Failed to load key details": "فشل تحميل تفاصيل المفتاح",
1192+
"Failed to load module switches": "فشل تحميل مفاتيح الوحدات",
1193+
"File Permissions": "أذونات الملف",
1194+
"Formatted": "منسق",
1195+
"Fullscreen": "ملء الشاشة",
1196+
"Getting URL": "جارٍ الحصول على URL",
1197+
"HashiCorp Vault KV2": "HashiCorp Vault KV2",
1198+
"Health": "الصحة",
1199+
"Healthy": "سليم",
1200+
"Key Manager": "مدير المفاتيح",
1201+
"Leave blank to keep the stored Vault token.": "اتركه فارغًا للاحتفاظ برمز Vault المخزن.",
1202+
"Max Cached Keys": "الحد الأقصى للمفاتيح المخزنة مؤقتًا",
1203+
"Metadata": "البيانات الوصفية",
1204+
"Minio": "Minio",
1205+
"Module switch is managed by environment variables": "يُدار مفتاح الوحدة بواسطة متغيرات البيئة",
1206+
"Module switches saved": "تم حفظ مفاتيح الوحدات",
1207+
"New access key has been created": "تم إنشاء مفتاح وصول جديد",
1208+
"No Audit Targets": "لا توجد أهداف تدقيق",
1209+
"No files to download": "لا توجد ملفات للتنزيل",
1210+
"No options available": "لا توجد خيارات متاحة",
1211+
"No tags": "لا توجد علامات",
1212+
"Notify": "الإشعارات",
1213+
"Notify is disabled": "الإشعارات معطلة",
1214+
"Notify is disabled. Enable notify before managing bucket event subscriptions.": "الإشعارات معطلة. فعّل الإشعارات قبل إدارة اشتراكات أحداث الحاوية.",
1215+
"Notify is disabled. Enable notify before managing event destinations.": "الإشعارات معطلة. فعّل الإشعارات قبل إدارة وجهات الأحداث.",
1216+
"Origin": "الأصل",
1217+
"Other Audiences": "جماهير أخرى",
1218+
"password length cannot be less than 8 characters and greater than 40 characters": "يجب أن يتراوح طول كلمة المرور بين 8 و40 حرفًا",
1219+
"Peer membership and editable replication controls, aligned with the RustFS backend site replication API and MinIO-style site management flow.": "عضوية النظراء وعناصر تحكم النسخ القابلة للتحرير، المتوافقة مع واجهة API لنسخ المواقع في خلفية RustFS وتدفق إدارة المواقع بأسلوب MinIO.",
1220+
"Please enter GCS credentials JSON": "يرجى إدخال JSON بيانات اعتماد GCS",
1221+
"Please remove members first": "يرجى إزالة الأعضاء أولًا",
1222+
"Please select audit target type": "يرجى تحديد نوع هدف التدقيق",
1223+
"Previous": "السابق",
1224+
"Provides detailed performance monitoring and alerting mechanisms to help administrators understand system status in real-time and ensure system stability and reliability": "يوفر آليات مفصلة لمراقبة الأداء والتنبيه لمساعدة المسؤولين على فهم حالة النظام في الوقت الفعلي وضمان استقراره وموثوقيته",
1225+
"Quota Save Failed": "فشل حفظ الحصة",
1226+
"Raw": "خام",
1227+
"Read-only OIDC settings": "إعدادات OIDC للقراءة فقط",
1228+
"Read-only settings": "إعدادات للقراءة فقط",
1229+
"Request failed": "فشل الطلب",
1230+
"s3fs": "s3fs",
1231+
"Select backend type": "حدد نوع الخلفية",
1232+
"sha256": "sha256",
1233+
"State": "الحالة",
1234+
"Stored token is hidden. Enter a new token only to replace it.": "الرمز المخزن مخفي. أدخل رمزًا جديدًا فقط لاستبداله.",
1235+
"The current site is detected automatically by the server. Add one or more remote sites to join the replication group.": "يكتشف الخادم الموقع الحالي تلقائيًا. أضف موقعًا بعيدًا واحدًا أو أكثر للانضمام إلى مجموعة النسخ.",
1236+
"This key is used as the platform default for SSE-KMS and SSE-S3.": "يُستخدم هذا المفتاح كافتراضي للمنصة لكل من SSE-KMS وSSE-S3.",
1237+
"This server has not exposed the site replication API yet, so the page now shows a friendly fallback instead of a raw NotImplemented error.": "لم يعرّض هذا الخادم واجهة API لنسخ المواقع بعد، لذلك تعرض الصفحة رسالة بديلة واضحة بدلًا من خطأ NotImplemented الخام.",
1238+
"This user already exists": "هذا المستخدم موجود بالفعل",
1239+
"transit": "transit",
1240+
"Unable to reach RustFS server health endpoint": "تعذر الوصول إلى نقطة نهاية صحة خادم RustFS",
1241+
"Unhealthy": "غير سليم",
1242+
"Update license": "تحديث الترخيص",
1243+
"Update the deployment environment first before changing ENV-managed module switches.": "حدّث بيئة النشر أولًا قبل تغيير مفاتيح الوحدات المُدارة بواسطة ENV.",
1244+
"Update the peer details that RustFS uses for site replication management. Fields not shown here are preserved from the current configuration.": "حدّث تفاصيل النظراء التي يستخدمها RustFS لإدارة نسخ المواقع. سيتم الاحتفاظ بالحقول غير المعروضة هنا من التكوين الحالي.",
1245+
"update:name": "update:name",
1246+
"update:show": "update:show",
1247+
"update:visible": "update:visible",
1248+
"Usage": "الاستخدام",
1249+
"Webhook": "Webhook",
1250+
"When the backend implements the site replication info endpoint, this page will automatically show peer sites, status summaries, and management actions.": "عندما تنفذ الخلفية نقطة نهاية معلومات نسخ المواقع، ستعرض هذه الصفحة تلقائيًا مواقع النظراء وملخصات الحالة وإجراءات الإدارة.",
1251+
"X-Amz-Algorithm": "X-Amz-Algorithm",
1252+
"X-Amz-Content-Sha256": "X-Amz-Content-Sha256",
1253+
"X-Amz-Credential": "X-Amz-Credential",
1254+
"X-Amz-Date": "X-Amz-Date",
1255+
"X-Amz-Expires": "X-Amz-Expires",
1256+
"X-Amz-Security-Token": "X-Amz-Security-Token",
1257+
"X-Amz-Signature": "X-Amz-Signature",
1258+
"X-Amz-SignedHeaders": "X-Amz-SignedHeaders",
1259+
"X-Amz-Target": "X-Amz-Target",
1260+
"You do not have permission to update module switches.": "ليست لديك صلاحية تحديث مفاتيح الوحدات.",
1261+
"You do not have permission to update OIDC providers.": "ليست لديك صلاحية تحديث موفري OIDC."
11401262
}

0 commit comments

Comments
 (0)