在延迟加载的应用程序部件之间共享行为

Sharing behavior between lazy loaded app parts

正如 Polymer Starter Kit 或 Polymer Shop 所展示的那样,我们在 Polymer 应用程序中使用了延迟加载。这意味着我们有一个基于抽屉的布局,应用程序 shell 导入抽屉内容以及主页内容。

现在我们介绍一种行为,并在自定义元素 A 和 B 中使用它,其中 A 显示在抽屉中,B 显示在主页中。现在是我们收到浏览器 (Chrome) 警告,flattenBehaviorsList 找不到行为。

我们假设发生这种情况是因为主页的 Polymer.importHref 调用(选项 asynctrue)识别行为(在自定义元素 B 中)并将其导入添加到HTML导入地图。但是在导入内容之前,抽屉的 Polymer.importHref(选项 asynctrue)调用想要导入自定义元素 A 的行为并从 HTML 导入地图。但由于导入未完成,行为是 null.

这个假设是真的吗?如果是的话,这是 Chrome 中的一个错误——只是一个想法,因为 Firefox 似乎可以处理这个问题?还是设计不好,我们不应该在不同的延迟加载应用程序部件中共享相同的行为?

你怎么看?

提前致谢

延迟加载是加载您不需要的资源的首选方式。但是你必须做对,我稍后会解释。

在单独的文件中有一个行为并在多个自定义元素中重复使用它也是很正常的,甚至是鼓励的。但是,自定义组件需要的所有资源 必须 作为 正常 rel="import" 加载,这意味着 async defer 标志必须不能设置。

例如,看看下面的演示元素,摘自 Polymer's devguide pages:

<link rel="import" href="highlight-behavior.html">

<script>
  Polymer({
    is: 'my-element',
    behaviors: [HighlightBehavior]
  });
</script>

如您所见,该行为已作为依赖项导入。没有它,很可能会出现错误,就像您的情况一样。

现在是有趣的部分 - 延迟加载。在这里,您实际上 加载组件使用的所有内容。所以你必须非常清楚哪些资源可以延迟加载,哪些不能延迟加载。根据经验,您必须 use/instantiate 直接在组件中加载所有内容。

延迟加载的一些常见示例:

  • 如果您有一个 iron-pages 元素并且所有页面都是自定义元素,那么您应该只加载默认(第一个)页面,因为不会立即使用其他页面。
  • 您可以将非必要的 GUI 元素(例如滑出式侧边栏)放在 dom-if 中,并在延迟加载所有组件后呈现 dom-if。最简单的方法是使用 importHref.

延迟加载元素的一个很好的例子是 Polymer 的商店应用程序:source code, online demo

总结:不要懒加载自定义元素的必备依赖,而是懒加载元素本身。

我想我今天遇到了同样的问题。使用 importHref async 时出现 [paper-radio-button::_flattenBehaviorsList]: behavior is null, check for missing or 404 import 之类的错误,但是当我更改为 async = false 时,错误消息消失了。

这似乎是 Polymer 的一个已知错误,或者可能是 Chrome https://github.com/Polymer/polymer/issues/2522