返回

gt-react@10.18.0

Ernest McCarter avatarErnest McCarter
gt-reactderivecontexti18n

概述

此次发布为 gt-react 新增了对可派生上下文值的支持。翻译内容时,源文本与译文之间并不总是一对一映射——同一个英文短语在另一种语言中可能需要多种译法。上下文派生通过允许你从单个源字符串生成多个翻译条目来解决这个问题。

背景:GT 翻译的工作原理

在 GT 的翻译系统中,您需要用 gt() 包裹可翻译的字符串:

import { useGT } from 'gt-react';

function Greeting() {
  const gt = useGT();
  return <p>{gt("Hello, world!")}</p>;
}

每次调用 gt() 都会创建一个源条目——也就是一段待翻译的文本。通常,一个源条目会为每种语言生成一个对应的译文。

什么是 derive?

derive() 函数会通知 GT CLI:根据不同的 runtime 值,从一次 gt() 调用中注册多个翻译条目。你不需要为每种变体分别编写单独的 gt() 调用,而是可以用 derive() 在一处表达所有变体,然后由 CLI 在构建时生成相应的源条目。

例如,英语在“The boy/girl is playing”中不区分性别,但西班牙语会区分 (“El niño está jugando”和“La niña está jugando”) 。借助 derive(),你可以在一次 gt() 调用中处理这种情况:

const subject = isBoy ? "boy" : "girl";
gt(`The ${derive(subject)} is playing.`);

CLI 会识别 derive() 调用,并注册两个源条目——一个对应 "The boy is playing.",另一个对应 "The girl is playing."——每个条目都会有各自的译文,并保持正确的西班牙语一致性。

问题:一对多映射关系

考虑源条目到翻译条目的三种映射情况:

情况 1:一对一映射

每个源条目恰好对应一个翻译条目。这是最直接的情况。

源条目翻译条目
这个男孩很漂亮。El niño es hermoso.
这个女孩很漂亮。La niña es hermosa.

情况 2:多对一映射

多个源条目会对应同一个翻译。例如,英语有复数形式,而普通话没有:

源条目翻译条目
I have {n} cat.我有{n}只猫。
I have {n} cats.

案例 3:一对多映射

单个源条目需要 多个 翻译。例如,西班牙语中的形容词需要与性别保持一致性,而英语没有这种变化:

源条目翻译条目
我很累Estoy cansado
Estoy cansada

这是在本次发布之前尚不支持的情况。GT 之前假定源条目与译文之间是一对一映射关系。

解决方案:derive 与 $context 搭配使用

GT 的 $context 选项可让你区分同一源文本对应的不同翻译条目。结合 derive() 后,你可以在调用处表达这一点:

import { useGT, derive } from 'gt-react';

function StatusMessage({ isMasculine }) {
  const gt = useGT();

  return (
    <p>
      {gt("I am tired", {
        $context: derive(
          isMasculine ? "inflect as masculine" : "inflect as feminine"
        )
      })}
    </p>
  );
}

在构建时,CLI 会识别 derive() 调用,并注册两个独立的源条目,每个条目都会生成各自的翻译:

"I am tired" ($context: "inflect as masculine") → "Estoy cansado"
"I am tired" ($context: "inflect as feminine")  → "Estoy cansada"

在 runtime 阶段,会根据 isMasculine 的值选择正确的翻译。

如果不使用 derive(),你就需要把它写成两个独立的调用:

// 不使用 derive — 代码更冗长,源文本重复
const message = isMasculine
  ? gt("I am tired", { $context: "inflect as masculine" })
  : gt("I am tired", { $context: "inflect as feminine" });

derive() 能以更少的重复代码达到相同效果,也让意图更清晰。

为什么不直接用条件判断?

和内容字符串一样,$context 的值也必须是静态的——CLI 需要在构建时解析它们。你不能把 runtime 表达式直接传给 $context,因为 CLI 无法预先知道它可能有哪些取值。derive() 通过沿调用栈追踪,解析出所有可能传入的静态字符串,从而解决了这个问题,让 CLI 能为每一种情况注册一条源条目。

总结

上下文派生弥补了翻译模型中的一个根本性缺口:它无法表示源条目与翻译条目之间的一对多映射关系。通过将 derive()$context`` 结合使用,单个 gt()` 调用就能生成多个可在 runtime 完成消歧的译文。

相关链接