Express中如何实现多可选查询参数查询MongoDB的challenges集合
实现方案
核心修改逻辑是动态构造MongoDB查询条件,不要把可选参数写死在查询对象中,同时修复原代码的逻辑漏洞即可。
修改要点
- 先校验必填参数
section是否传入,避免无参数时返回整个集合的全量数据 - 仅当
challenge参数存在时,才将其加入查询条件 - 修复原查询结果判断逻辑:
Model.find()方法永远返回数组,空数组属于真值,原if(!challenge)判断永远不会触发
修改后完整代码
// @route GET api/challenge?section=_&challenge=_ // @description Get challenge(s) by section number (and optional challenge number) // @access Private router.get('/', auth, async (req, res) => { try { // 校验必填参数section if (!req.query.section) { return res.status(400).json({ msg: '缺少必填参数section' }); } // 动态构造查询条件 const query = { section_no: req.query.section }; // 仅当传入challenge参数时才加入查询条件 if (req.query.challenge) { query.challenge_no = req.query.challenge; } const challenges = await Challenge.find(query); // 结果为空时返回提示 if (challenges.length === 0) { return res.status(400).json({ msg: '未找到对应的挑战数据' }); } return res.json(challenges); } catch (err) { console.error(err.message); res.status(500).send('Server Error'); } });
可选优化
如果希望传入challenge参数时直接返回对象而非数组,可以拆分查询逻辑:
let result; if (req.query.challenge) { result = await Challenge.findOne(query); if (!result) return res.status(400).json({ msg: '未找到对应的挑战数据' }); } else { result = await Challenge.find(query); if (result.length === 0) return res.status(400).json({ msg: '未找到对应的挑战数据' }); } return res.json(result);
修改后请求api/challenge?section=1&challenge=1会直接返回单个对象,请求api/challenge?section=1返回数组,更符合常规接口设计习惯。
内容的提问来源于stack exchange,提问作者seshkebab
相关产品推荐
相关产品推荐

