vuex - 在动态注册的模块中覆盖数据

vuex - data overwritten in dynamically registed modules

我有一个模块,我们称它为 providers。我使用 id 为各个提供者动态注册模块。像这样:

[1, 2, 3].forEach((id) => {
  this.registerModule(['providers', id.toString()], ProviderModule);  
})

这些 ProviderModule 中的每一个都有一个名为 availabilities 的模块。所以这个模块的名称 space 看起来像这样:`providers/${id}/availabilities`

我进行了一次 api 调用以获取有关每个提供商的数据。 api 调用 returns 通过 id 映射到每个提供者的对象数组(可用性)。对于数组中的每个对象,我在相应的模块中分派一个动作。像这样:

response.data.forEach((providerAvailabilities) => {
  dispatch(`provider/${providerAvailabilities.id}/availabilities/load`, providerAvailabilities);
})

load 操作中,我们提交变更中的属性并记录一些信息:

[types.SET_AVAILABILITIES](state, payload) {
  console.log(payload);
  state.firstAvailable = payload.firstAvailable;
  state.id = payload.id;
  state.timeslots = payload.timeslots;
  console.log('state: ', state.timeslots);
}

上面代码中的日志准确地显示了我想要的每个提供程序模块循环响应数据时的数据。

问题来了。每次循环响应数据时,它都会设置每个提供者的 availabilties' 属性,而不仅仅是循环当前所在的提供者。因此,呈现的 availabilities 始终是最后一个提供者的 availabilities

为了验证是否是这种情况,我将日志放入一个 getter 中,它获取了我所有的提供者:

list: (state) => { 
  if (state.provider) {
    const providers = Object.keys(state.providers).map(key => state.providers[key]);
    console.log('current providers: ', providers.map(provider => provider.availabilities.timeslots));
    return providers;
  }
}

这会在提供程序发生更改时注销,每次触发 load 操作时,它都会将所有提供程序的 availabilities 重置为它所在的循环迭代。

这就是我所能解决的问题。

我的问题:

  1. 是什么导致 load 操作为所有 providers 设置值?

  2. 如何确保为相应的动态注册模块设置正确的数据?

问题出在此处和 ProviderModule 的定义中:

[1, 2, 3].forEach((id) => {
  this.registerModule(['providers', id.toString()], ProviderModule);  
})

您正在使用不同的名称注册同一个模块 ProviderModule,但底层对象是相同的。

简而言之,在您的模块定义中,您应该以与在组件定义中定义数据相同的方式定义您的状态,并使用返回对象而不是静态对象的函数:

state () {
    return {
      foo: 'bar'
    }
  },

问题记录在此处 https://vuex.vuejs.org/en/modules.html(请参阅模块重用部分)