You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在Next.js中无需外部库实现i18n locale全局化调用

在Next.js中全局获取翻译变量t(无需外部库)

问题背景

我希望在应用的任意组件中获取locale作为全局变量,且不使用任何外部库。目前已完成以下配置:

  • 翻译文件es.js:
export default {
  home: 'Inicio',
  signin: 'Iniciar Sesion',
  welcome: 'Bienvenido',
};

(en.js为对应英文翻译,结构一致)

  • next.config.js的i18n配置:
i18n: {
    locales: ['en', 'es'],
    defaultLocale: 'es',
  },

现在可以通过router.locale在组件中手动判断加载对应翻译,但每个组件都要重复这段逻辑,希望能简化成直接调用t变量的形式,比如:

import t from "../lib/i18n/t";

const HomePage = () => {
  return (
    <div>{t.home}</div>
  )
}

解决方案

方案一:用React Context全局共享(推荐)

通过React Context把翻译对象全局注入,所有组件都能直接获取,适合大型应用。

1. 创建Context和Provider

新建lib/i18n/TranslationContext.js:

import { createContext, useContext, useMemo } from 'react';
import { useRouter } from 'next/router';
import en from './en';
import es from './es';

// 创建翻译上下文
const TranslationContext = createContext();

// 全局Provider组件,包裹整个应用
export const TranslationProvider = ({ children }) => {
  const router = useRouter();
  const { locale } = router;
  
  // 根据当前语言缓存翻译对象
  const t = useMemo(() => {
    switch(locale) {
      case 'en':
        return en;
      case 'es':
        return es;
      default:
        return es; // 兜底用默认语言
    }
  }, [locale]);

  return (
    <TranslationContext.Provider value={t}>
      {children}
    </TranslationContext.Provider>
  );
};

// 自定义Hook,简化上下文调用
export const useTranslation = () => {
  return useContext(TranslationContext);
};

2. 在_app.js中全局注入

修改pages/_app.js,让所有页面都能访问上下文:

import { TranslationProvider } from '../lib/i18n/TranslationContext';

function MyApp({ Component, pageProps }) {
  return (
    <TranslationProvider>
      <Component {...pageProps} />
    </TranslationProvider>
  );
}

export default MyApp;

3. 组件中使用

现在任何组件都能通过自定义Hook快速获取t:

import { useTranslation } from "../lib/i18n/TranslationContext";

const HomePage = () => {
  const t = useTranslation();
  return (
    <div>{t.home}</div>
  );
};

export default HomePage;

方案二:自定义Hook(轻量版)

如果不想用Context,直接写一个Hook封装逻辑,每次调用自动获取当前语言的翻译:

新建lib/i18n/useTranslation.js:

import { useRouter } from 'next/router';
import { useMemo } from 'react';
import en from './en';
import es from './es';

export default function useTranslation() {
  const router = useRouter();
  const { locale } = router;

  // 缓存翻译对象,避免重复计算
  const t = useMemo(() => {
    return locale === 'en' ? en : es;
  }, [locale]);

  return t;
}

组件中使用:

import useTranslation from "../lib/i18n/useTranslation";

const HomePage = () => {
  const t = useTranslation();
  return (
    <div>{t.home}</div>
  );
};

export default HomePage;

关于直接import t的说明

如果一定要实现直接import t的形式,由于Next.js的服务端渲染特性,全局变量无法动态匹配每个请求的locale,会导致服务端和客户端渲染内容不一致(出现闪烁),因此不推荐。如果是纯客户端渲染场景,可以尝试,但存在局限性,建议优先选择上面两种方案。


内容的提问来源于stack exchange,提问作者Jesus Aguas

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.02 16:20:23