将字符串索引更改为大型 MongoDB 实例中的 ObjectID

Change string indexes to be ObjectID ones in large MongoDB instance

所以,我 git 一个大型生产数据库转储,其中 _id 字段为 strings。不同的集合使这些字符串的长度不同。那里有很多关系。我需要一种将字符串 _ids 更改为 ObjectId 的方法。

我已经尝试过的:

1) 查看 mongoose/mongodb 文档以了解执行此操作失败的单个命令

2) node.js 获取一个集合中的所有条目并将 string id 包装到 ObjectId 中的迁移脚本只是因为堆栈溢出 FATAL ERROR: CALL_AND_RETRY_LAST Allocation failed - JavaScript heap out of memory 而失败,如果我们正在尝试删除并重新创建方法,或者出现关于错误字符串长度和无法从该字符串创建 ObjectId 的错误。

稍后将附加数据示例 and/or mongoose 架构。

避免JavaScript堆内存不足的一种简单而低效的游标解决方案是序列化所有内容。当然,要编辑 _id,您必须创建一个新文档并删除旧文档。

const cursor = Model.find().lean().cursor();
let doc;
while ((doc = await cursor.next())) {
  // The string must be a valid ObjectId, otherwhise it won't work
  if (typeof doc._id === 'string') {
    let newId = new mongoose.Types.ObjectId(doc._id);
    let newDoc = new Model(Object.assign({}, doc, {_id: newId}));
    await newDoc.save();
    await Model.remove({_id: doc._id});
  }
}

但是,如果您有错误 ID 的错误,可能是因为字符串 ID 实际上不是 mongo ObjectId 的字符串化版本。在这种情况下,关系无法保留。