【问题标题】:Vuex4 state populated with api call is undefined in component使用 api 调用填充的 Vuex4 状态在组件中未定义
【发布时间】:2022-01-06 18:10:13
【问题描述】:

请告诉我我对使用 Vuex 还是很陌生,还不太了解它。 我正在为 IndexedDB 使用带有 localforage 包的 Vuex4。

我的Vuex商店如下:

import { createStore } from 'vuex'
import localforage from 'localforage'
import axios from 'axios'

const store = createStore({
  state: {
    tenantLocale: {}
  },
  getters: {},
  mutations: {
    setLocale(state, value) {
      state.tenantLocale = value
    }
  },
  actions: {
    getTenant(context) {
      axios.get('/api/tenant-data/locale').then((response) => {
        context.commit('setLocale', response.data)
        localforage.setItem('tenantLocale', response.data)
      })
    }
  }
})

export default store

我像这样在我的 App.vue 中调度操作:

import { useStore } from 'vuex'

export default {
  setup() {
    const store = useStore()

    //get default information about tenant from api
    store.dispatch('getTenant')

    return {}
  }
}

现在的问题是,如果我在模板部分的 Login.vue 组件中呈现状态,如下所示:

<h1>{{ store.state.tenantLocale.timezone }}</h1>

它显示了正确的数据,但是如果我尝试在我的组件的脚本部分对它做一些事情,比如说尝试打印出来:

console.log(store.state.tenantLocale.timezone)

我收到未定义的消息。

我在这里缺少什么?这里最好的方法是什么?我需要为它创建吸气剂吗?创建一个承诺?我的大脑被炸了......任何帮助至少将我指向正确的方向表示感谢!

【问题讨论】:

  • “但是如果我尝试在我的组件的脚本部分用它做一些事情” - 究竟在哪里?该操作是异步的。您无法同步获得结果。将异步副作用仅放入 setup 是错误的,应该在 onMounted 内部,或者整个组件需要异步。
  • 我明白你的意思,但我试着把它放在 onMounted 里面我仍然得到未定义的结果,这就是我这么困惑的原因
  • 您在 onMounted 中究竟做了什么?在异步操作完成之前,您不能期望它被定义。如果它是通过 getTenant 操作完成的,那么通常你必须等待一个承诺。 “创建一个承诺?” - 已经有一个来自 dispatch 的承诺,你忽略了它。如果您不确定那里发生了什么,您也可以查看stackoverflow.com/questions/14220321/…
  • 例如,如果我想创建一个基于tenantLocale 对象取值的日期:date = new Date().toLocaleString(store.state.tenantLocale.localization, { timeZone: `${store.state.tenantLocale.timezone}` })
  • 正如答案所暗示的, date 应该是一个计算值。如果在您访问date 时该值未定义,这意味着您需要以某种方式推迟其访问,直到所有相关数据都可用。在 Vue 中有几种统一的方法可以做到这一点。这取决于您的情况,哪个更可取。您可以将 dispatch('getTenant') 移动到父级并且在数据可用之前不渲染子级,或者使用 Vue 3 的 Suspense

标签: javascript vue.js vuex vuejs3 vuex4


【解决方案1】:

在 setup 函数中,您可以使用 computed 访问 state 或 getter:

computed(() => store.state.tenantLocale.timezone)

【讨论】:

  • 您能详细说明一下吗?也无法让它以这种方式工作。
【解决方案2】:

你可以这样做

import { computed } from 'vue'
import { useStore } from 'vuex'

export default {
  setup () {
    const store = useStore()

    return {
      // access a state in computed function
      timezone: computed(() => store.state.tenantLocale.timezone),

    }
  }
}

【讨论】:

  • 我正在使用组合 API,所以我不能使用这个关键字。
  • 在这种情况下这样做 import { computed } from 'vue' import { useStore } from 'vuex' export default { setup () { const store = useStore() return { // 访问一个状态在计算函数时区:computed(() => store.state.tenantLocale.timezone), } } }
猜你喜欢
  • 1970-01-01
  • 2021-11-28
  • 2016-05-24
  • 2020-09-10
  • 2020-03-14
  • 2020-02-06
  • 1970-01-01
  • 2021-04-16
  • 2023-04-06
相关资源
最近更新 更多