Svelte即时加载数据:@const失效后的替代实践方案问询
Svelte中替代@const实现可变数据加载的简洁方案
在Svelte里用@const实现即时数据加载确实很优雅,不用在脚本里额外声明变量,但它定义的变量不可变,导致后续没法修改数据属性(比如示例中修改行的open状态)。这里有两种简洁的解决方案,既能保持模板内声明的简洁性,又支持数据修改:
方案一:用{#let}声明块级可变状态
如果只是需要给列表项添加临时交互状态(比如open),可以直接在each块内部用{#let}声明块级可变变量,完全不需要在脚本里加状态:
<script> let a = false; </script> <button on:click={() => a = !a}>Toggle</button> {#if a} {#await axios.get(...)} <Spinner /> {:then rawTable} {#each rawTable as item} {#let open = false} <button on:click={() => open = true}>Open row!</button> {#if open} <!-- 展开内容 --> {/if} {/let} {/each} {/await} {/if}
{#let}是Svelte 3.47+支持的语法,它会在块级作用域内创建可变变量,状态只作用于当前列表项,不会污染全局脚本。
方案二:用{#let}包装可变数据副本
如果需要修改的是数据本身的属性(而非临时交互状态),可以在await的then块里,用{#let}声明一个可变的数据副本,通过映射给原始数据添加可写属性:
<script> let a = false; </script> <button on:click={() => a = !a}>Toggle</button> {#if a} {#await axios.get(...)} <Spinner /> {:then rawTable} {#let table = rawTable.map(item => ({ ...item, open: false }))} {#each table as x} <button on:click={() => x.open = true}>Open row!</button> {#if x.open} <!-- 展开内容 --> {/if} {/each} {/let} {/await} {/if}
这种方式既保留了@const那种在模板内即时声明的优雅,又让数据变成了可变的对象,后续修改属性完全没问题,同时脚本里也不用额外添加多余的状态变量。
内容的提问来源于stack exchange,提问作者Drun555
相关产品推荐
相关产品推荐

