xref: /expo/apps/test-suite/tests/Localization.js (revision 4a05dfd5)
1import * as Localization from 'expo-localization';
2import { Platform } from 'react-native';
3import i18n from 'i18n-js';
4
5const en = {
6  good: 'good',
7  morning: 'morning',
8};
9
10const fr = {
11  good: 'bien',
12  morning: 'matin',
13};
14
15const pl = {
16  good: 'dobry',
17  morning: 'rano',
18};
19
20export const name = 'Localization';
21
22export function test(t) {
23  t.describe(`Localization methods`, () => {
24    t.it('expect async to return locale', async () => {
25      function validateString(result) {
26        t.expect(result).toBeDefined();
27        t.expect(typeof result).toBe('string');
28        t.expect(result.length > 0).toBe(true);
29      }
30
31      function validateStringArray(result) {
32        t.expect(result).toBeDefined();
33        t.expect(Array.isArray(result)).toBe(true);
34      }
35
36      const {
37        locale,
38        locales,
39        timezone,
40        isoCurrencyCodes,
41        region,
42        isRTL,
43      } = await Localization.getLocalizationAsync();
44
45      validateString(locale);
46      validateString(timezone);
47      if (Platform.OS === 'ios') {
48        validateString(region);
49      }
50      validateStringArray(isoCurrencyCodes);
51      validateStringArray(locales);
52      t.expect(locales[0]).toBe(Localization.locale);
53      t.expect(typeof isRTL).toBe('boolean');
54    });
55  });
56
57  t.describe(`Localization defines constants`, () => {
58    if (Platform.OS === 'ios') {
59      t.it('Gets the current device country', async () => {
60        const result = Localization.region;
61
62        t.expect(result).toBeDefined();
63        t.expect(typeof result).toBe('string');
64        t.expect(result.length > 0).toBe(true);
65      });
66    }
67    t.it('Gets the current locale', async () => {
68      const result = Localization.locale;
69
70      t.expect(result).toBeDefined();
71      t.expect(typeof result).toBe('string');
72      t.expect(result.length > 0).toBe(true);
73    });
74    t.it('Gets the preferred locales', async () => {
75      const result = Localization.locales;
76
77      t.expect(result).toBeDefined();
78      t.expect(Array.isArray(result)).toBe(true);
79      t.expect(result.length > 0).toBe(true);
80      t.expect(result[0]).toBe(Localization.locale);
81    });
82    t.it('Gets ISO currency codes', async () => {
83      const result = Localization.isoCurrencyCodes;
84      t.expect(result).toBeDefined();
85      t.expect(Array.isArray(result)).toBe(true);
86      for (let iso of result) {
87        t.expect(typeof iso).toBe('string');
88        t.expect(iso.length > 0).toBe(true);
89      }
90    });
91    if (Platform.OS !== 'web') {
92      t.it('Gets the current timezone', async () => {
93        const result = Localization.timezone;
94        t.expect(result).toBeDefined();
95        t.expect(typeof result).toBe('string');
96        t.expect(result.length > 0).toBe(true);
97        // Format: expect something like America/Los_Angeles or America/Chihuahua
98        t.expect(result.split('/').length > 1).toBe(true);
99      });
100    }
101
102    t.it('Gets the current layout direction (ltr only)', async () => {
103      const result = Localization.isRTL;
104      t.expect(result).toBeDefined();
105      t.expect(result).toBe(false);
106    });
107  });
108
109  t.describe(`Localization works with i18n-js`, () => {
110    i18n.locale = Localization.locale;
111    i18n.translations = { en, fr, pl };
112    i18n.missingTranslationPrefix = 'EE: ';
113    i18n.fallbacks = true;
114
115    t.it('expect language to match strings (en, pl, fr supported)', async () => {
116      const target = 'good';
117
118      i18n.locale = Localization.locale;
119
120      const expoPredictedLangTag = Localization.locale.split('-')[0];
121      const translation = i18n.translations[expoPredictedLangTag];
122
123      t.expect(translation[target]).toBe(i18n.t(target));
124    });
125  });
126}
127