我正在使用一个静态网站生成器,希望能够同时支持反应性JavaScript交互和标准的“将页面加载到浏览器中”超链接。在我看来,像斯维尔特这样的东西可能更适合这个;我可以使用服务器端渲染支持为所有页面生成HTML,然后可以使用hydratable: true
编译和发布JavaScript组件以支持动态功能。
我用这种方法想到的一个问题是,我项目的大多数组件都是完全静态的内容:只是HTML和超链接,没有任何状态或事件处理程序,除非生成新的,否则我不会更改道具。不同页面的HTML文件。如果天真地生成JavaScript以在页面加载时合并所有这些组件,那么我最终可能会得到比实际需要的捆绑包大得多(并且在运行时完成了更多的工作)。
斯维尔特(Svelte)提供任何方法来优化这种情况吗?我能以某种方式检查某个组件是否纯粹是其道具的功能,以便在不需要时避免为其补水吗?还是编译器足够聪明才能为我做到这一点?
答案 0 :(得分:1)
这是一个很好的问题,我们目前没有一个简单的答案。
可以确定单个组件是否具有可以更改的值-svelte.compile(...)
返回具有vars
属性的对象,该属性是所有值的数组在组件内部。检查此数组将告诉您哪些值永远不会重新分配或更改。 (它不会告诉您组件是否具有事件处理程序,这些事件处理程序具有副作用,但是不影响状态,这对于确定组件是否完全静态也是必要的。我们可以在将来的3.x版本中添加。)
但这只是故事的一半。考虑一个声明name
属性的组件...
<script>
export let name;
</script>
<h1>Hello {name}!</h1>
...,并且在您的应用中使用的方式如下:
<Greeting name="world"/>
就编译器在编译<Greeting>
组件时所关心的问题而言,name
值随时可能更改,因此将其视为完全静态是不安全的。但是,如果它可以更全面地了解您的应用,则可以将{name}
替换为world
,这会带来很多好处。
在补水时,Svelte假定现有DOM与应该存在的内容之间可能存在差异。在许多情况下,可以安全地做出其他假设,并跳过检查已知为静态的子树的工作,这样就无需在生成的JS中包括它们。
作为编译器,Svelte位置优越,可以利用这些技术,但是我们尚未进行这项工作。理想情况下,我们将能够以无需更改任何内容即可缩小应用程序的方式来升级编译器。如果您热衷于尝试同时进行各种尝试,那么从vars
返回的svelte.compile(...)
属性(我想也是ast
属性)就可以开始了。