云端基础设施
语系与本地化
在单一网站中支持多种语系,包含主要语系、无需额外点数的机器翻译、语系感知传递与 SEO,并为托管与无头前端提供相同的合约。
网站设有一个主要语系,并可新增更多语系。每个文字字段皆保留其主要语系的数值;翻译内容则存储于旁边的资料表中,每一笔记录与语系各占一行。新增语系时,系统会在后台翻译整个网站,并于完成后发布。托管网站与您构建的任何前端,皆通过相同的 locale 参数读取相同的资料。
核心对象
- 语系集 (Locale set)。 网站的语系包含一个主要语系、状态(
draft、translating、published、disabled)、每个次要语系的网址前缀(en、ja或拥有者自选的前缀)以及自动翻译开关。GET /api/v1/site会在locales[]中列出这些信息。 - 翻译 (Translations)。 每一笔记录与语系各占一行,包含草稿与已发布的字段资料、专属的网址别名(单一区段)以及翻译时来源记录的
sourceHash。哈希值用于检测过时的翻译,并防止外部工具覆盖较新的来源文字。 - 可翻译字段 (Translatable fields)。 根据各内容类型架构衍生的注册表,定义哪些路径可进行翻译:标题、RTF 文字、区块文字、SEO 字段、产品描述、长篇详情、常见问题与购买备注、产品选项与变体描述、课程单元(包含文字课程与测验问题,但不包含答案)、全站处理时间与购买备注、表单及法律页面。集合字段需通过
localized: true启用。价格、库存、订单、顾客与评论皆不进行翻译。 - 网址别名 (URL slugs)。 页面、文章、分类、标签、作者、产品、产品分类与集合项目,每个语系皆可拥有自己的别名。首次机器翻译至某语系时,会从翻译后的标题产生别名(拉丁语系语言会产生 ASCII 别名;其他语言若主要别名为 ASCII 则保留该别名),之后不会自动变更。页面仅翻译其自身的区段,因此某语系中的页面路径是根据该语系中各层级的别名所构建。固定的永久链接区段(如
/blog与/product)不会被翻译。 - 翻译任务 (Translation jobs)。 新增语系或重试失败批次时,会执行全站任务;后续对主要语系的编辑会以增量方式重新翻译。任务与单笔记录翻译不消耗 AI 点数;每日调用上限会将工作排入隔日,而非直接失败。
设置之间的关联
语系、货币、商业市场与时区是四个独立的设置。彼此互不依赖,因此网站可以使用英文撰写、以欧元销售,并采用东京时间运行。顾客的语系(Contact.locale)会在结账、登录与提交表单时记录,并决定其电子邮件、顾客账号与证书的语系。
API 的运作方式
- 使用 Content Delivery API 读取。 每次读取皆接受
locale(代码或网址前缀)。未翻译的字段会回退至主要文字,响应内容会在resolvedLocale中说明服务语系,并在availableLocales中列出已翻译的语系。通过别名读取时,接受任何语系的别名并返回该请求语系的slug;页面与产品会新增localePaths(在每个在线语系中的路径),集合项目则新增localeSlugs。若网站不存在该语系,则返回400 UNSUPPORTED_LOCALE。/seo/*、/feed与搜索功能皆遵循相同的参数。请参阅 读取内容。 - 使用 Management API 管理。
localization.locales.*可新增、更新、重新排序、移除及设置主要语系;localization.translations.*可列出、读取、写入(使用sourceHash进行upsert,以及设置或清除语系的网址别名)、发布与删除翻译,并通过translate按需执行翻译;localization.jobs.*可读取进度与重试。新增或移除语系会变更该语系的所有网址,并要求confirm: true。语系代码为自然键:新增已存在的语系会返回ALREADY_ADDED,移除不存在的语系会返回NOT_FOUND,因此重试调用不会创建第二个语系,且无需幂等键。 - 监听 Webhooks。
content.translation.published与deleted会针对每笔记录与语系触发;localization.locale.published、unpublished与updated则在语系集变更时触发;localization.job.completed与failed则针对全站任务触发。每个内容事件上的cacheTags带有@<locale>,因此翻译上线时仅会刷新该语系。请参阅 Webhooks。 - 在前端进行路由与标签。
createKanorioMiddleware({ features: { locales: true } })会将主要语系的前缀重定向至根目录,提供/<prefix>/llms.txt与/<prefix>/rss.xml,匹配不含前缀的共享重定向,并针对完整路径匹配语系重定向(locale设置)。requestLocaleOf、buildAlternates与languageSwitcher(传入localePaths)可让您取得语系、标准网址 (canonical)、hreflang 以及与托管网站规则相同的语言菜单。请参阅 Next.js 与 SDK 参考。 - 顾客端文字。 Customer API 与
@kanorio/elements接受locale;若未提供,则使用顾客记录的语系。课程与单元标题、订单项目名称与完成证书皆遵循此设置。请参阅 课程与成员。 - 自动化电子邮件。 订单、付款、运送、退款、登录与表单确认邮件会以顾客记录的语系发送(若网站提供该语系),否则使用主要语系。若拥有者未自订电子邮件,则使用内置措辞(每个网站语言皆有对应版本)。自订电子邮件的翻译方式与其他内容相同:其翻译为
message_template记录类型(自订模板的 ID),通过localization.translations.*针对各语系修正并于写入时生效。在语系拥有自订电子邮件的翻译前,该邮件会以主要语系发送。模板变量(如订单编号等三括号占位符)必须与来源完全一致;新增变量的翻译将被拒绝。 - 导出。 网站导出内容包含主要语系内容旁边的
localization/locales.json与localization/translations.json。
应遵循的行为
- 主要语系于根目录提供;其他所有语系皆位于其前缀之下。主要语系本身的代码作为前缀时,会以
301重定向至根目录。 - 仍在翻译中的语系对访客或 Delivery API 而言不存在。当任务完成时,该语系会一次性发布。
- 移除已上线的语系会将其前缀重定向至主要语系的页面。其翻译内容至少保留 30 天;重新新增该语系会重复使用这些翻译,并仅翻译缺失的部分。使用相同的前缀即可恢复旧网址。
- 以回退方式提供的页面(该语系尚未有翻译)会取得主要语系的标准网址 (canonical) 且不含 hreflang,因此搜索引擎不会索引重复内容。
- 具有草稿与发布生命周期的记录(页面、全局区块、网站设置、文章与集合项目)会将编辑过的翻译保留为草稿。发布记录会使每个语系的草稿上线;
localization.translations.publish可单独发布一个语系,并需要记录的发布权限(site:publish、blog:publish或collections:publish)。编辑翻译不会将主要语系标记为已变更。 - 使用其他语系别名的网址,或在语系已有专属别名时使用主要别名,皆会重定向至该语系的别名。变更已上线的别名会从该语系的旧网址新增 301;清除别名则会使该语系再次遵循主要别名。
- 网站仅有一个语系时可变更主要语系。在多语系网站上变更主要语系会重写所有网址,目前尚未开放此功能。
- 相同的规则适用于托管网站与无头 (headless) 前端;
npx @kanorio/cli doctor可检查您的前端是否在每个语系前缀下提供翻译后的标题、列出每个在线语系的 hreflang,并提供各语系的llms.txt。
API 开放的范围
- Locale set & translations (add a locale, full-site machine translation, review)可用
- API
- Management API
localization.locales.*(list,add,update,reorder,remove,set_primary),localization.translations.*(list,get,upsertwithsourceHash,publish,delete,translate),localization.jobs.*; REST/sites/:id/locales,/sites/:id/translations - 托管网站
/settingslocale list (status, progress, URL prefix, auto-translate) and the editor's locale switcher for corrections- Webhooks
content.translation.published/deleted,localization.locale.published/unpublished/updated,localization.job.completed/failed
- Locale-aware delivery, SEO files and customer-facing text可用
- API
- Delivery
?locale=(code or URL prefix) on/site,/pages,/globals,/collections,/catalog,/forms,/search,/seo/*and/feedwithresolvedLocale/availableLocales/localePaths(collection items:localeSlugs), any locale's slug resolves to the record;/redirectsrules carrylocale; Customer APIlocaleon deliverables, orders and unit open; SDKcreateKanorioMiddleware({ features: { locales } }),buildAlternates,requestLocaleOf,languageSwitcher, locale-scopedrevalidate; CLIdoctori18n rules - Elements
localeon<KanorioProvider>(forms, login, curriculum and unit load the visitor's locale)- 托管网站
- Primary locale at the root, other locales under their prefix (
/en/…), header language menu, per-localellms.txt/rss.xml, one sitemap withxhtml:link, hreflang andx-default - Webhooks
cacheTagson every content event carry@<locale>so a translation going live refreshes only that locale
API 参考
Webhook 事件
- content.translation.published · Fired when one record's translation in one locale goes live on its own (editor correction, Management API write, incremental or on-demand machine translation). cacheTags carry only that locale's tags. Not fired per record during a full-site translation job; see localization.job.completed.
- content.translation.deleted · Fired when a live translation of one record in one locale is deleted; visitors see the primary-locale text until it is translated again.
- localization.locale.published · Fired when a locale goes live for visitors and the Content Delivery API (a full-site translation job finished, or the owner published it). cacheTags is site:<id>: rebuild the language switcher and hreflang on every page.
- localization.locale.unpublished · Fired when a live locale is taken offline or removed (removed: true); its URL prefix now 301-redirects to the primary locale.
- localization.locale.updated · Fired when a live locale's URL prefix (change: path_prefix, previous holds the old prefix), its position in the language switcher (order) or the site's primary locale (primary) changes.
- localization.job.completed · Fired when a full-site translation job finishes. cacheTags is locale:<code>: every response of that locale may have changed. A locale going live for the first time also fires localization.locale.published.
- localization.job.failed · Fired when a full-site translation job fails (the model provider stayed unavailable or retries ran out; the daily limit only pauses a job). Retry it with localization.jobs.retry.
近期变更
- 2026-11-04 Localization: automated emails follow the customer's language
- 2026-11-04 Localization: publishing one locale needs the record's publish permission
- 2026-11-04 Localization: more translatable fields (product details, variants, lessons, quizzes, store notes)
- 2026-11-04 Localization: each locale can have its own URL slug
- 2026-11-03 Localization is generally available; site export includes locales and translations
给网站所有者
如何在后台使用这项产品,请参阅帮助中心。
打开帮助中心