lobe-chat

Форк
0
/
translation.test.ts 
137 строк · 4.1 Кб
1
// @vitest-environment node
2
import { cookies } from 'next/headers';
3
import * as fs from 'node:fs';
4
import * as path from 'node:path';
5
import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest';
6

7
import { DEFAULT_LANG, LOBE_LOCALE_COOKIE } from '@/const/locale';
8
import { normalizeLocale } from '@/locales/resources';
9
import * as env from '@/utils/env';
10

11
import { getLocale, translation } from './translation';
12

13
// Mock external dependencies
14
vi.mock('next/headers', () => ({
15
  cookies: vi.fn(),
16
}));
17

18
vi.mock('node:fs', () => ({
19
  existsSync: vi.fn(),
20
  readFileSync: vi.fn(),
21
}));
22

23
vi.mock('node:path', () => ({
24
  join: vi.fn(),
25
}));
26

27
vi.mock('@/const/locale', () => ({
28
  DEFAULT_LANG: 'en-US',
29
  LOBE_LOCALE_COOKIE: 'LOBE_LOCALE',
30
}));
31

32
vi.mock('@/locales/resources', () => ({
33
  normalizeLocale: vi.fn((locale) => locale),
34
}));
35

36
vi.mock('@/utils/env', () => ({
37
  isDev: false,
38
}));
39

40
describe('getLocale', () => {
41
  const mockCookieStore = {
42
    get: vi.fn(),
43
  };
44

45
  beforeEach(() => {
46
    vi.clearAllMocks();
47
    (cookies as any).mockReturnValue(mockCookieStore);
48
  });
49

50
  it('should return the provided locale if hl is specified', async () => {
51
    const result = await getLocale('fr-FR');
52
    expect(result).toBe('fr-FR');
53
    expect(normalizeLocale).toHaveBeenCalledWith('fr-FR');
54
  });
55

56
  it('should return the locale from cookie if available', async () => {
57
    mockCookieStore.get.mockReturnValue({ value: 'de-DE' });
58
    const result = await getLocale();
59
    expect(result).toBe('de-DE');
60
    expect(mockCookieStore.get).toHaveBeenCalledWith(LOBE_LOCALE_COOKIE);
61
  });
62

63
  it('should return DEFAULT_LANG if no cookie is set', async () => {
64
    mockCookieStore.get.mockReturnValue(undefined);
65
    const result = await getLocale();
66
    expect(result).toBe(DEFAULT_LANG);
67
  });
68
});
69

70
describe('translation', () => {
71
  const mockTranslations = {
72
    key1: 'Value 1',
73
    key2: 'Value 2 with {{param}}',
74
    nested: { key: 'Nested value' },
75
  };
76

77
  beforeEach(() => {
78
    vi.clearAllMocks();
79
    (fs.existsSync as any).mockReturnValue(true);
80
    (fs.readFileSync as any).mockReturnValue(JSON.stringify(mockTranslations));
81
    (path.join as any).mockImplementation((...args: any) => args.join('/'));
82
  });
83

84
  it('should return correct translation object', async () => {
85
    const result = await translation('common', 'en-US');
86
    expect(result).toHaveProperty('locale', 'en-US');
87
    expect(result).toHaveProperty('t');
88
    expect(typeof result.t).toBe('function');
89
  });
90

91
  it('should translate keys correctly', async () => {
92
    const { t } = await translation('common', 'en-US');
93
    expect(t('key1')).toBe('Value 1');
94
    expect(t('key2', { param: 'test' })).toBe('Value 2 with test');
95
    expect(t('nested.key')).toBe('Nested value');
96
  });
97

98
  it('should return key if translation is not found', async () => {
99
    const { t } = await translation('common', 'en-US');
100
    expect(t('nonexistent.key')).toBe('nonexistent.key');
101
  });
102

103
  it('should use fallback language if specified locale file does not exist', async () => {
104
    (fs.existsSync as any).mockReturnValueOnce(false);
105
    await translation('common', 'nonexistent-LANG');
106
    expect(fs.readFileSync).toHaveBeenCalledWith(
107
      expect.stringContaining(`/${DEFAULT_LANG}/common.json`),
108
      'utf8',
109
    );
110
  });
111

112
  it('should use zh-CN in dev mode when fallback is needed', async () => {
113
    (fs.existsSync as any).mockReturnValueOnce(false);
114
    (env.isDev as unknown as boolean) = true;
115
    await translation('common', 'nonexistent-LANG');
116
    expect(fs.readFileSync).toHaveBeenCalledWith(
117
      expect.stringContaining('/zh-CN/common.json'),
118
      'utf8',
119
    );
120
  });
121

122
  it('should handle file reading errors', async () => {
123
    const consoleErrorSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
124
    (fs.readFileSync as any).mockImplementation(() => {
125
      throw new Error('File read error');
126
    });
127

128
    const result = await translation('common', 'en-US');
129
    expect(result.t('any.key')).toBe('any.key');
130
    expect(consoleErrorSpy).toHaveBeenCalledWith(
131
      'Error while reading translation file',
132
      expect.any(Error),
133
    );
134

135
    consoleErrorSpy.mockRestore();
136
  });
137
});
138

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.