You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Discord.js结合MongoDB查询匹配question字段多结果实现问题

MongoDB查询匹配问题解决方案

原嵌套数组结构(questionAdd为数组)的修复方案

你之前的代码返回全部内容的原因是:$elemMatch 在查询条件里的作用是筛选符合条件的文档,不会过滤返回的questionAdd数组内容,所以只要文档里有一个匹配的问答项,就会返回整个文档的全部内容。
如果要只返回匹配的数组项,需要在投影参数里也加上$elemMatch过滤,修改后的代码如下:

var test2 = "What fast food chain has the most locations globally?";
await Data.findOne(
  // 查询条件:筛选包含匹配问答项的文档
  {
    questionAdd: {
      $elemMatch: {
        question: {$regex: test2, $options: 'i'}
      }
    }
  },
  // 投影:只返回匹配的questionAdd数组项,其他字段按需保留
  {
    _id: 0,
    questionAdd: {
      $elemMatch: {
        question: {$regex: test2, $options: 'i'}
      }
    }
  },
  (err, data)=>{
    if(data){
      var getData = JSON.stringify(data); // 替换toString为JSON序列化更清晰
      console.log(getData);
    }
  }
)

如果需要返回同一个文档里所有匹配的数组项,把投影里的$elemMatch换成$filter聚合操作符即可。

调整后扁平化结构的说明与修复

这个结构每个文档对应一条问答,可以正常返回多个匹配结果,你的原有代码存在3个可优化问题:

  1. 空结果判断错误:Data.find 没有匹配结果时返回的是空数组[],空数组的布尔值为true,所以!data永远不会触发,要改成data.length === 0判断
  2. 存在await和回调函数混用的问题,统一用async/await写法逻辑更清晰
  3. 正则可以加上i选项实现不区分大小写匹配,省去提前转小写的冗余操作

修改后的参考代码:

let messageArgs1 = args.join(' ');
let outString = messageArgs1.replace(/[`~!@#$%^&()_|+\-=?;'",.<>\{\}\[\]\\\/]/gi, '');
let messageArgs = outString.trim();
if(messageArgs === "") return message.channel.send("Please type your question!");

try {
  const data = await Data.find(
    { question: { $regex: messageArgs, $options: 'i' } },
    { question: 1, answer: 1, _id: 0 }
  ).limit(9);
  if(data.length === 0) {
    console.log('无匹配结果');
    return message.channel.send(`Nope!`);
  }
  // 这里处理匹配结果,data就是包含最多9条匹配问答的数组
} catch (err) {
  console.error('查询错误:', err);
}

内容的提问来源于stack exchange,提问作者Và Thi Thi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.14 12:36:08