为什么 Akita statestore return 是一个空实体而不是更新后的实体?

Why does Akita statestore return an empty entity rather than updated entity?

我正在使用 Akita 作为我的 Angular 应用程序的状态存储。

我成功地从后端服务器获取数据并填充我的商店(数据显示在组件中)但是当我尝试更新商店中的实体时它发出一个空对象。

我怀疑这是我对秋田犬的理解所缺少的一些基本知识,但我希望调用以下内容

  1. 更新具有给定 ID 的实体
  2. 触发 myQuery.select(id).subscribe() 与更新的实体
     myStore.setActive(idOfThingToUpdate)
     myStore.updateActive({someProperty: newPropertyValue})
     myStore.removeActive(idOfThingToUpdate)

我也在服务中尝试过这种语法:

        this.myStore.update(entityId, {propertyName: newPropertyValue});

上面显示的订阅函数是 returning 一个空对象。 如果我在我的实体 class 中创建一个构造函数并设置几个默认值,则只有在构造函数中定义的属性才会在 query.select() 调用中被 return 编辑。这些属性的值是默认值(在构造函数中定义)而不是商店中存在的值。

所以似乎以下一项或两项为真:

希望一切都有意义....

一些代码:

服务:

this.contestStore.setActive(contestId);
// attempt set a single property 'winningLicence' on the active entity
this.contestStore.updateActive({
      winningLicence: newWinningLicence
  }
);
this.contestStore.removeActive(contestId);

我是要将新构造的实体传递到 updateActive() 函数还是只是传递我想要更新的道具?

export interface ContestState {
  loading: boolean;
  contests: Contest[];
}

export function createInitialState(): ContestState {
  return {
    loading: false,
    contests: []
  };
}

@StoreConfig({ name: 'contestStore', resettable: true})
export class ContestStore extends EntityStore<ContestState> {
  constructor() {
    super(createInitialState());
  }
}

查询 - 当我在组件中调用 selectAll 时,这会 return 有意义的数据:

@Injectable()
export class ContestsQuery extends QueryEntity<ContestState> {
  constructor(protected contestStore: ContestStore) {
    super(contestStore);
  }
}

来自组件...

  ngOnInit(): void {
    // contest is @Input and may be a new unsaved/no id contest, hence check
    if (this.contest.id) { 
      this.contestsQuery.selectEntity(this.contest.id).subscribe((contest: Contest) => {
        // this comes back as empty object after calling my update code in service shown above
        console.log(contest); 
      });
    }
  }

好吧,我找到了一个解决方案,不确定我是否完全理解它,但它是...

在我的服务中,我有一个功能可以通过 HTTP 从后端获取数据来刷新缓存,然后迭代响应对象并调用 store.set() 来设置存储....

        const contests = [];
        contestData.forEach((json) => {
          const contest = Object.assign(new Contest(), json);
          contests.push(contest);
        });
        this.contestStore.set(contests);

我改为使用 upsert 而不是尝试使用 set() 函数一次性设置集合:

        contestData.forEach((json) => {
          const contest = Object.assign(new Contest(), json);
          this.contestStore.upsert(contest.id, contest);
        });

现在这似乎像我最初预期的那样工作并且查询。select/get 函数 return 在我使用 update(id, object) 更新对象后更新数据。

我大概可以使用 upsertMany([]),但我不确定这与 set([]) 在功能上有何不同。实际上,使用 upsertMany 并传递 Contest 数组会以与 set([]) 相同的方式失败。所以现在我会依次为每个人坚持 upsert(id, entity)。

也许我在告诉 Akita 应该提取 Contest 对象中的 id 字段并将其用作 ID 时错过了一步?

https://datorama.github.io/akita/docs/entities/entity-store