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

Node.js使用Highland对接MongoDB>=4.0查询流时无限输出undefined问题

问题原因
  • 该问题和你使用的MongoDB服务端镜像版本(mongo:4.2.10)无关,故障出在npm包mongodb4.x版本的接口破坏性变更与Highland流的适配逻辑上。
  • mongodb 4.0.0及以上版本中,collection.find()返回的Cursor对象不再默认实现Node.js标准Readable流接口,也不兼容旧版同步迭代协议。Highland接收到不符合流/可迭代协议的对象时,会将其当作普通值反复推送,最终导致无限输出undefined、堆内存耗尽。
  • 额外注意:原代码存在变量名笔误,定义的客户端实例名为client,查询时误用了mongoClient;同时4.x版本驱动要求必须显式调用connect()建立连接,不支持旧版的隐式连接逻辑。
修复方案

二选一即可,优先选方案1,改动最小。

方案1:显式转换为标准Node.js流(最小改动)

4.x版本的Cursor提供了stream()方法,调用后返回标准Readable流,可直接被Highland正常消费,修改后代码如下:

const connectionString = ...
const client = new MongoClient(connectionString);
await client.connect(); // 4.x驱动必须显式建立连接
const records = client
  .db('mydb')
  .collection('acollection')
  .find({})
  .stream(); // 关键:显式获取可读流实例
const res = await hi(records).tap(_log).collect().toPromise(Promise);

function _log(record) {
  console.log(record);
  return record;
}

方案2:基于异步迭代器手动构造Highland流

如果不想使用Node.js原生流,也可以利用4.x Cursor原生支持的AsyncIterable协议,手动构造Highland流:

const connectionString = ...
const client = new MongoClient(connectionString);
await client.connect();
const cursor = client
  .db('mydb')
  .collection('acollection')
  .find({});
// 遍历异步迭代器向Highland推送数据
const records = hi(async (push, next) => {
  for await (const doc of cursor) {
    push(null, doc);
  }
  push(null, hi.nil); // 遍历完成后推送结束标记
});
const res = await records.tap(_log).collect().toPromise(Promise);

function _log(record) {
  console.log(record);
  return record;
}

内容的提问来源于stack exchange,提问作者Dotan

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.26 12:54:15