【问题标题】:Can I get entire i18n labels of specific dictionary我可以获得特定字典的整个 i18n 标签吗
【发布时间】:2017-07-26 14:41:24
【问题描述】:

我遇到了 i18n 标签的问题。

我的应用程序使用 Granite.I18n.get('') 函数在 js 前端读取了几个 i18n 标签。整个字典被下载为“/libs/cq/i18n/dict.{+locale}.json”,如“/etc/clientlibs/foundation/shared/source/init.js”中所述。

现在 en 字典只返回自定义标签并且尺寸很小。 但是像fr这样的其他语言,字典文件是所有/libs字典的集合,非常庞大。我在其他几个网站上也注意到了这一点。

tennantco.com

en dictionary - 118 KB

fr dictionary - 1.4 MB

Timewarnercable.com

en dictionary - 1.1 KB

fr dictionary - 1.2 MB

热鱼

en dictionary - 3 KB

fr dictionary - 695 KB

我们的痛点是,在 CDN 上缓存这个大文件的成本会增加,并试图找到降低 CDN 成本的方法。

我知道标签本身就是关键。但是 ExportServlet 只能过滤掉 en 的呈现自定义字典。我们的字典类似于 /libs 下的 otb 字典。那么ExportServlet是如何处理en export下的otb标签的呢?

此错误在所有 CMS 产品中都很常见还是特定于 Adob​​e?还需要一个解决方案或解决方法来获取仅适用于其他语言的自定义词典。

【问题讨论】:

    标签: internationalization aem


    【解决方案1】:

    英语词典很小,因为英语条目是关键而不是翻译。法语(和其他语言)很大,因为它们包含英语的关键和进一步的翻译。此外,许多密钥仅在翻译语言中可用,因为密钥用作默认翻译。

    所以对于法语,如果你使用Granite.I18n.get('Hello world!'),它会在找到它时返回法语翻译,否则它会简单地返回“Hello World”,如果语言上下文是英语则不需要翻译。

    由于 JS 在客户端进行评估的性质,该产品旨在下载完整的字典,包括产品本身的 OOTB 翻译,因为 i18n 实现不了解上下文并且无法过滤掉不需要的翻译。

    虽然方便,但不幸的是,这是使用 Granite.I18n.get('') 的限制和副作用。

    可能的解决方法

    • Granite.I18n.* 可以通过使用服务器端 i18n 库并仅在服务器上呈现所需的翻译并用作部分 HTML 来避免。这可能对 SPA 不起作用
    • 如果您使用像 Angular(x) 这样的 SPA 框架,那么它们支持 i18n 工厂初始化,可以挂接到自定义 servlet 响应,下载过滤后的 i18n。这可能需要大量工作,而且如果翻译的术语过多且字典变大,大小仍然会成为问题。
    • 压缩、最小化和缓存字典。您可以使用 Apache 模块或输出过滤器来完成。这将减少流量的大小和负载,但同样不能保证随着翻译的增长整个字典的大小会很小。

    通常,页面只能呈现所需的内容。使用 JS 进行后期翻译会强制下载字典​​,而 Granite.i18n 不适合优化的下载体验。

    【讨论】:

    • 感谢您的解释。我编辑了这个问题。我需要一个解决方案或解决方法来解决这个问题。我知道这是产品错误,但如何解决?
    【解决方案2】:

    我最终编写了一个自定义实现,因为我在这个问题上也没有从 Adob​​e 票证中获得太多帮助。

    • OTB 字典 json 由 ResourceBundleExportServlet 渲染
    • 我创建了一个自定义的 sling servlet,它将准备和返回类似于 ResourceBundleExportServlet 的 json
    • 修改 /etc/clientlibs/granite/utils/source/I18n.js 以调用自定义 servlet 而不是 otb servlet。
    • 自定义 servlet 被编码为仅返回特定数据字典而不是所有字典。

    这解决了我的问题。尽管我不相信这是正确的解决方案。需要一种 otb 方式来呈现这种干净。

    【讨论】:

    • 我认为现在的路径是/libs/cq/i18n
    • 我想在单独的路径上注册 ResourceBundleExportServlet,我该怎么做?
    【解决方案3】:

    我们遇到了类似的要求,即使用 Granite.i18n 库在客户端获取 I18n 值 这就是我所做的。

    1. 创建了一个自定义 servlet,它返回类似于
      的 JSON 响应 ResourceBundleExportServlet。
    2. 使用 basename 和 locale 参数加载包 - ResourceBundle resourceBundle = req.getResourceBundle(basename,
      pageLocale);
    3. 在 /apps/project-name/i18n 文件夹中特定语言的 i18n xml 文件中添加了 sling:basename="basename_constant"'。在我的 情况下,我正在设置语言环境本身的值,例如:“zh_cn”。

    4.在clientlibs javascript文件中设置Granite.I18n.setUrlPrefix("/bin/custom/i18n/dict.");从
    获取 自定义 servlet URL。这不需要修改 OOTB I18n.js

    【讨论】:

      【解决方案4】:

      当您尝试获取特定词典时,这里有一个可以帮助您的答案:https://stackoverflow.com/a/55656153/14465431

      查看提及 sling:basename

      的部分

      这也适用于一个网站

      示例:

      [sling:Language] > mix:language
      mixin
      - sling:basename (string)
      - sling:basename (string) multiple
      
      

      http://localhost:4502/libs/cq/i18n/dict.es.[sling:basename-value].json

      OTB 解决方案 :)

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2019-09-23
        • 2018-03-22
        • 1970-01-01
        • 2011-01-31
        • 1970-01-01
        • 2012-04-12
        • 2023-01-11
        相关资源
        最近更新 更多