如何用MERN栈的insertMany方法将TXT文件数据上传至Mongoose
问题
我想把10道MCQ题目从mcq.txt文件批量保存到Mongoose中,现在后端返回201状态码,但数据库里找不到数据。打印req.body是空对象,用create单条插入正常,但用insertMany时只会生成一个空条目,没法像文件里那样生成10条独立数据。请问怎么用insertMany把文件数据传到Mongoose?
相关代码片段
React组件(AddMultipleMCQ.js)
export default function AddMultipleMCQ() { const [multipleMCQ, setMultipleMCQ] = useState([]); const buttonClickHandler = async () => { const postRequestOptions = { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify(multipleMCQ), }; try { const res = await fetch("/add-multiple-mcq", postRequestOptions); const resData = await res.json(); } catch (error) { console.log(error); } }; return ( <div> <input type="file" onChange={(e) => setMultipleMCQ(e.target.files[0])} /> <button onClick={() => buttonClickHandler()}>Add Multiple MCQs</button> </div> ); }
后端批量插入代码
router.post("/add-multiple-mcq", async (req, res) => { try { const multipleMCQ = await MCQ.insertMany(req.body) res.status(201).json({ success: true, data: multipleMCQ }) } catch (error) { res.status(401).json({ success: false }) console.log("server error: ", error) } })
mcq.txt文件内容
[ { "question": "question 1", "options": ["option 1", "option 2", "option 3", "option 4"], "answer": "option 2", "tags": "question 1" }, ..... ..... { "question": "question 10", "options": ["option 1", "option 2", "option 3", "option 4"], "answer": "option 2", "tags": "question 10" } ]
解决方案
问题核心是前端没有正确读取文件内容,直接将File对象传给后端,导致req.body格式错误或为空。
1. 前端修改:正确读取并解析文件内容
需要用FileReader读取上传的txt文件内容,解析成JSON数组后再发送请求:
export default function AddMultipleMCQ() { const [multipleMCQ, setMultipleMCQ] = useState([]); // 处理文件上传,读取内容并解析为JSON const handleFileChange = (e) => { const file = e.target.files[0]; if (!file) return; const reader = new FileReader(); reader.onload = (event) => { try { // 解析文件内容为JSON数组 const mcqData = JSON.parse(event.target.result); setMultipleMCQ(mcqData); } catch (err) { console.error("文件格式错误,请确保是JSON格式", err); } }; reader.readAsText(file); }; const buttonClickHandler = async () => { if (multipleMCQ.length === 0) { console.log("请先选择正确的MCQ文件"); return; } const postRequestOptions = { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify(multipleMCQ), }; try { const res = await fetch("/add-multiple-mcq", postRequestOptions); const resData = await res.json(); console.log("批量插入成功", resData); } catch (error) { console.log("请求失败", error); } }; return ( <div> <input type="file" onChange={handleFileChange} accept=".txt,.json" /> <button onClick={buttonClickHandler}>Add Multiple MCQs</button> </div> ); }
2. 后端增强验证(可选)
在后端校验req.body是否为有效数组,提前拦截无效请求:
router.post("/add-multiple-mcq", async (req, res) => { try { if (!Array.isArray(req.body) || req.body.length === 0) { return res.status(400).json({ success: false, message: "请提供有效的MCQ数组数据" }); } const multipleMCQ = await MCQ.insertMany(req.body); res.status(201).json({ success: true, data: multipleMCQ }); } catch (error) { res.status(500).json({ success: false, message: error.message }); console.log("server error: ", error); } });
关键修改说明
- 原代码直接将
e.target.files[0](File对象)存入状态,JSON.stringify后会得到空结构,后端无法解析有效数据。 - 新增
handleFileChange方法,通过FileReader读取文件文本内容并解析为JSON数组,确保传给后端的是正确的MCQ数据集合。 - 增加
accept=".txt,.json"限制文件类型,引导用户选择格式正确的文件。 - 后端新增数组校验,避免空数据插入,同时返回更明确的错误信息。
内容的提问来源于stack exchange,提问作者Nasem
相关产品推荐
相关产品推荐

