React+NodeJS中MongoDB返回指定用户投诉时出现不可序列化错误
解决Redux存储用户投诉数据的不可序列化问题
问题根源
后端用Complaint.find({ userId })返回的是Mongoose文档对象,这类对象包含Mongoose内置的方法和额外属性(比如__v、save()等),不是纯JSON格式的普通JavaScript对象,而Redux和localStorage只支持序列化纯JS对象,所以会触发Non-serializable错误。
解决方案
1. 后端修改查询逻辑,返回纯JS对象
在查询时添加.lean()方法,让Mongoose直接返回普通JS对象,而非文档实例:
// 后端接口代码 const userComplaints = await Complaint.find({ userId }).lean(); res.status(200).json(userComplaints);
.lean()会剥离Mongoose文档的所有额外属性和方法,返回的就是可直接序列化的纯数据,前端拿到后就能正常存入Redux和localStorage。
2. 排查findById请求失败的原因
findById是根据文档自身的_id字段查询,而你要查询的是关联的userId外键,所以用findById本身就不符合需求。如果误把userId当成了Complaint集合的_id,才会导致Postman请求失败——确认数据库中Complaint文档的_id和你传入的userId是否一致,若不一致,就不该用findById,继续用find({ userId })配合.lean()即可。
3. 前端Redux序列化/反序列化处理
确保在reducer中正确处理localStorage的存储:
// 初始化状态 const initialState = { userComplaints: localStorage.getItem('userComplaints') ? JSON.parse(localStorage.getItem('userComplaints')) : null }; // Reducer逻辑 const complaintReducer = (state = initialState, action) => { switch(action.type) { case 'SET_USER_COMPLAINTS': const newState = { ...state, userComplaints: action.payload }; // 存入localStorage前先转成字符串 localStorage.setItem('userComplaints', JSON.stringify(newState.userComplaints)); return newState; default: return state; } };
内容的提问来源于stack exchange,提问作者Eudeamonism
相关产品推荐
相关产品推荐

