如何使用动态过滤器过滤苗条的商店

时间:2020-05-15 11:40:16

标签: observable reactive-programming svelte

我有一个派生商店,该商店必须使用HTML选择器来过滤条目对象。现在,我引入了一个额外的过滤器存储(可观察),以强制在过滤器存储发生更改时运行派生的存储回调。

但是当过滤器更改时,是否有可能在没有过滤器存储的情况下触发以下派生存储中的回调?我需要这家额外的商店吗? 下面的代码工作正常。我很好奇。

import { writable, derived } from 'svelte/store';
import { entries } from './../stores/entries.js';

export const filter = writable({
  // to update filter use: $filter.kind = ... 
  // or: filter.update(o => Object.assign(o, {kind: .., batchId: ...}));
  batchId: 'all',
  kind: 'all',
});

let list, total;

export const view = derived(
  [filter, entries], 
  ([$filter, $entries], set) => {

    total = 0;

    if ($entries) {
      // filter by HTML selects: kind, batchId
      list = Object.keys($entries.map).sort().reduce((a, key) => {
        if ((['all', $entries.map[key].description.kind].includes($filter.kind))
          && (['all', $entries.map[key].parentId].includes($filter.batchId))) {
            total += $entries.map[key].grossValue;
            a.push($entries.map[key]);
        };
        return a;  
      }, []);
      set({list, total});
    };

    return () => {
      set(null);
    };
  }, null
);

1 个答案:

答案 0 :(得分:2)

您可以从派生存储中提取逻辑到您自己控制的函数/对象中,并使用API​​手动触发更新...但这不是一个好主意。那将破坏某些封装而毫无益处。

您的writable + derived解决方案是IMO,最简单,最优雅的解决方案。它明确概述了数据依赖关系,并明确地分离了关注点,而没有涉及任何奥秘代码。它还提供Svelte监视更改所需的内容,并以最精细的粒度自动为您管理订阅。

这是一个不错的模式,非常适合您的用例。我会这样保留它。