Vue3 Pinia问题:API获取的值无法设为非响应式常量
解决方案
要获取完全独立于state.data的非响应式副本,核心是对API返回的数据做深拷贝,而非浅拷贝。
问题根源
你当前使用的对象解构({ ...res.data })或Object.assign({}, res.data)都属于浅拷贝:它们仅复制对象的顶层属性,而内部的fruits、owners数组是引用类型,依然和state.data中的数组指向同一个内存地址。当后续修改state.data里的数组元素时,data_copy的对应数组也会同步变化,看起来像是“响应式副本”,但本质是引用共享导致的联动变更。
具体实现
对于API返回的普通JSON数据(无特殊类型如Date、函数),最简便的深拷贝方式是通过JSON序列化:
export const useShopStore = defineStore( "shop", () => { const state = reactive({ data: { fruits: [], owners: [], }, }); let data_copy = { fruits: [], owners: [], }; async function fetchData() { const URL = `${API_URL}/shops`; try { const res = await axios.get(URL); // 给响应式状态赋值(浅拷贝足够,需保持响应式关联) state.data = { ...res.data }; // 深拷贝生成完全独立的非响应式副本 data_copy = JSON.parse(JSON.stringify(res.data)); } catch (err) { if (err.response) { console.log(err.response); } } } return { data: state.data, data_copy, fetchData }; }, { persist: true, } );
其他可选方案
如果数据包含JSON无法序列化的类型(如Date对象),可以使用:
- 浏览器原生API:
data_copy = structuredClone(res.data); - 第三方工具库(如lodash):引入
cloneDeep后执行data_copy = cloneDeep(res.data);
效果验证
修改后,data_copy会固定为API返回的初始数据状态,无论后续如何修改state.data的内容,data_copy都不会同步变化,完全满足你对比初始值与修改值的需求。
内容的提问来源于stack exchange,提问作者Lucien Chardon
相关产品推荐
相关产品推荐

