gt-react@10.12.0
概述
gt-react 现在导出了一个 t() 函数,用于在浏览器中以同步方式进行模块级字符串翻译。
此前,在 gt-react 中翻译字符串需要使用基于 React 上下文的 Hook,例如 useGT。Hook 在组件内部效果很好,但无法覆盖一种常见场景:在模块级别翻译字符串——也就是在 React 组件之外、渲染前,或在普通工具文件中。
t() 正好填补了这一空白。它是一个同步函数,你可以在浏览器代码中的任何位置调用它:
import { t } from 'gt-react/browser';
const greeting = t('Hello, world!');无需 Hooks、无需异步,也无需组件树。
为什么采用这种方式
这个 PR 的核心思路,是尝试脱离基于 React 上下文 的翻译方案。t() 在组件树之外运行,因此能支持一些更灵活的模式——尤其是模块级翻译。字符串可以在定义时就完成翻译,而不是等到渲染时再处理。
这也带来了一些权衡:
- 仅限客户端。
t()只适用于客户端 React 应用。它依赖浏览器执行模块,在应用渲染前加载翻译。 - 切换语言需要整页重新加载。 由于翻译是在模块加载时解析的,切换区域设置需要重新执行这些模块——也就意味着必须整页刷新。无法在会话中途热切换语言。
不过,开发体验有了明显提升。无需用 hook 包装字符串,无需处理组件层面的样板代码,也没有异步边界——只需要一次函数调用。
现有的 React 上下文 方案 (useGT、<T> 等) 不会消失。这只是为那些适合接受这些权衡的项目提供的一个额外选项。
工作原理
t() 会从预先加载的翻译中同步获取译文。这些翻译由 bootstrap() 注入;`bootstrap()`` 是一个新的异步初始化函数,会在应用渲染前加载当前区域设置的所有翻译。
你需要修改应用的入口点,先运行 bootstrap()。通常是 main.tsx,不过你也可以在 index.html 中更改入口点。
// bootstrap.tsx(新入口点)
import gtConfig from '../gt.config.json';
import { bootstrap } from 'gt-react/browser';
async function getTranslations(locale: string) {
return import(`./_gt/${locale}.json`);
}
await bootstrap({
...gtConfig,
getTranslations,
});
await import('./main.tsx');getTranslations 函数是异步的——它会先加载翻译,再导入并执行 React 应用。这就是 t() 能在模块级访问翻译的原因:当任意模块调用 t() 时,翻译已经准备就绪。
这只适用于纯客户端 React 应用,因为模块级代码在浏览器中加载时会重新执行。而且由于要更新翻译后的内容,我们必须重新执行模块,所以切换区域设置时需要整页刷新。
**实验性:**此功能目前仅支持纯客户端 React 应用。
变量
t() 支持变量插值,用法与 msg() 相同:
import { t } from 'gt-react/browser';
t('Hello, {name}!', { name: 'John' }); // → "Hola, John!"适用位置
当你需要在 React 组件树之外使用翻译时,t() 是合适的选择——比如常量文件、工具函数、配置对象、路由定义,或者任何在浏览器中运行于模块作用域的内容。
请注意:
- 它目前还不能与
gt-react系统的其余部分集成。 你需要按上文所述完成 bootstrap 设置。这是一种独立方案。 - 仅支持客户端。 服务端翻译应使用基于 React 上下文的 Hook,例如
useGT。
设计说明
t() 仅可在浏览器中使用。如果在服务器端调用 (此时 window 未定义) ,它会记录一条警告,并回退到源字符串。这是有意的——服务端翻译应使用现有的基于 React 上下文的 Hook。
API 参考
有关参数、返回类型和设置详细信息,请参阅完整的 t() API 参考。