| | import { cookies, headers } from 'next/headers' |
| | import Negotiator from 'negotiator' |
| | import { match } from '@formatjs/intl-localematcher' |
| |
|
| | import { createInstance } from 'i18next' |
| | import resourcesToBackend from 'i18next-resources-to-backend' |
| | import { initReactI18next } from 'react-i18next/initReactI18next' |
| | import { i18n } from '.' |
| | import type { Locale } from '.' |
| |
|
| | |
| | const initI18next = async (lng: Locale, ns: string) => { |
| | const i18nInstance = createInstance() |
| | await i18nInstance |
| | .use(initReactI18next) |
| | .use(resourcesToBackend((language: string, namespace: string) => import(`./${language}/${namespace}.ts`))) |
| | .init({ |
| | lng: lng === 'zh-Hans' ? 'zh-Hans' : lng, |
| | ns, |
| | fallbackLng: 'en-US', |
| | }) |
| | return i18nInstance |
| | } |
| |
|
| | export async function useTranslation(lng: Locale, ns = '', options: Record<string, any> = {}) { |
| | const i18nextInstance = await initI18next(lng, ns) |
| | return { |
| | t: i18nextInstance.getFixedT(lng, ns, options.keyPrefix), |
| | i18n: i18nextInstance, |
| | } |
| | } |
| |
|
| | export const getLocaleOnServer = (): Locale => { |
| | const locales: string[] = i18n.locales |
| |
|
| | let languages: string[] | undefined |
| | |
| | const localeCookie = cookies().get('locale') |
| | languages = localeCookie?.value ? [localeCookie.value] : [] |
| |
|
| | if (!languages.length) { |
| | |
| | const negotiatorHeaders: Record<string, string> = {} |
| | headers().forEach((value, key) => (negotiatorHeaders[key] = value)) |
| | |
| | languages = new Negotiator({ headers: negotiatorHeaders }).languages() |
| | } |
| |
|
| | |
| | if (!Array.isArray(languages) || languages.length === 0 || !languages.every(lang => typeof lang === 'string' && /^[\w-]+$/.test(lang))) |
| | languages = [i18n.defaultLocale] |
| |
|
| | |
| | const matchedLocale = match(languages, locales, i18n.defaultLocale) as Locale |
| | return matchedLocale |
| | } |
| |
|