feat(i18n): add the Slovak (sk-SK) panel locale (#6889)

Adds a complete Slovak translation of every panel and bot string, registers
sk-SK in the language picker (a browser set to sk now lands on it instead of
English) and loads Ant Design's Slovak locale. The locale count in the READMEs,
docs and contributor guides moves from 13 to 14.
This commit is contained in:
VAIO73
2026-10-24 07:35:28 +02:00
committed by MHSanaei
parent e0d2a0c58c
commit 052b11d2bc
20 changed files with 2843 additions and 33 deletions
+1
View File
@@ -12,6 +12,7 @@ const antdLocaleLoaders: Record<string, () => Promise<{ default: Locale }>> = {
'ja-JP': () => import('antd/es/locale/ja_JP'),
'pt-BR': () => import('antd/es/locale/pt_BR'),
'ru-RU': () => import('antd/es/locale/ru_RU'),
'sk-SK': () => import('antd/es/locale/sk_SK'),
'tr-TR': () => import('antd/es/locale/tr_TR'),
'uk-UA': () => import('antd/es/locale/uk_UA'),
'vi-VN': () => import('antd/es/locale/vi_VN'),
+2 -2
View File
@@ -5,7 +5,7 @@ import { join, resolve } from 'node:path';
import { describe, expect, it } from 'vitest';
/*
* Guards the 13-locale translation set two ways: every key in en-US must be
* Guards the 14-locale translation set two ways: every key in en-US must be
* referenced somewhere in the frontend or Go sources (dead keys accumulate
* silently — this test deleted over two hundred of them when it was
* introduced), and every locale must carry exactly the en-US key set
@@ -77,7 +77,7 @@ describe('i18n keys', () => {
const dead = enKeys.filter(
(key) => !tokens.has(key) && !prefixes.some((p) => key.startsWith(p)),
);
expect(dead, `dead i18n keys (delete from all 13 locales):\n ${dead.join('\n ')}`).toEqual(
expect(dead, `dead i18n keys (delete from all 14 locales):\n ${dead.join('\n ')}`).toEqual(
[],
);
});
+18
View File
@@ -41,6 +41,24 @@ describe('subscription language scope', () => {
expect(dateTimeFormat).toHaveBeenLastCalledWith('fa-IR', expect.any(Object));
});
it('maps a Slovak browser to the Slovak panel locale instead of resetting to English', async () => {
vi.resetModules();
const utils = await import('@/utils');
const cookies = new Map<string, string>();
vi.spyOn(utils.CookieManager, 'getCookie').mockImplementation(
(name) => cookies.get(name) ?? '',
);
vi.spyOn(utils.CookieManager, 'setCookie').mockImplementation((name, value) => {
cookies.set(name, value);
});
const reload = vi.fn();
vi.stubGlobal('window', { navigator: { language: 'sk' }, location: { reload } });
expect(utils.LanguageManager.getLanguage()).toBe('sk-SK');
expect(cookies.get('lang')).toBe('sk-SK');
expect(reload).not.toHaveBeenCalled();
});
it('does not resolve the language for empty or invalid dates', async () => {
const utils = await import('@/utils');
const getLanguage = vi.spyOn(utils.LanguageManager, 'getLanguage').mockReturnValue('en-US');
+2
View File
@@ -901,6 +901,7 @@ export class LanguageManager {
{ name: 'Український', value: 'uk-UA', icon: '🇺🇦' },
{ name: 'Türkçe', value: 'tr-TR', icon: '🇹🇷' },
{ name: 'Português', value: 'pt-BR', icon: '🇧🇷' },
{ name: 'Slovenčina', value: 'sk-SK', icon: '🇸🇰' },
];
static getLanguage(scope: LanguageScope = 'panel'): string {
@@ -931,6 +932,7 @@ export class LanguageManager {
['uk', LanguageManager.supportedLanguages[10].value],
['tr', LanguageManager.supportedLanguages[11].value],
['pt', LanguageManager.supportedLanguages[12].value],
['sk', LanguageManager.supportedLanguages[13].value],
];
simularLangs.forEach((pair) => {