Vue中watchEffect监听Store值异常:为何获取值为undefined?
问题原因与修复方案
核心问题:Ref的访问方式错误
你用ref()包裹了整个store对象,但在<script>中直接访问mystore.myVariable是错误的——ref的响应式值存储在.value属性中。模板里Vue会自动为ref解包,所以模板中mystore.myVariable能正常显示,但脚本里必须通过.value访问。
同时你的watchEffect只触发一次,是因为它没有追踪到有效的响应式依赖(你访问的mystore.myVariable不是响应式的,只是一个undefined值)。
具体修复步骤
1. 优化Store的写法(解决this指向问题)
当前setMyVariable方法里的this指向存在不确定性,建议把方法抽离出来,操作更清晰:
// stores/mystore.js import { ref } from "vue"; export const mystore = ref({ myVariable: false, }); // 独立方法,避免this指向问题 export function setMyVariable(value) { mystore.value.myVariable = value; }
2. 修正组件脚本中的Ref访问
在foo.vue的<script>中,所有访问store属性的地方都要加上.value,这样才能追踪到响应式变化:
<script setup> import { watchEffect, reactive } from "vue"; import { mystore, setMyVariable } from "../../../stores/mystore.js"; const { data: thedata, refresh } = await useFetch( "http://api.test/foo", { transform(data) { return JSON.parse(data); }, pick: ["data"], } ); const headers = reactive([ { title: "ID", key: "id" }, { title: "Name", key: "name" } ]); watchEffect(() => { console.log("test"); console.log(mystore.value.myVariable); // 这里添加.value // 触发fetch刷新 if (mystore.value.myVariable) { refresh(); // 重置变量,避免重复触发 mystore.value.myVariable = false; } }); </script>
3. 修正触发按钮的调用
如果采用了抽离后的独立方法,index.vue里也要对应修改:
<script setup> import { setMyVariable } from "../stores/mystore.js"; </script> <template> <v-btn @click="setMyVariable(true)">Refresh</v-btn> </template>
为什么模板里能正常显示?
Vue3的模板会自动为顶层ref进行解包,所以mystore.myVariable在模板中等价于mystore.value.myVariable,但这个自动解包仅在模板中生效,<script>里必须手动使用.value。
内容的提问来源于stack exchange,提问作者DevonDahon
相关产品推荐
相关产品推荐

