使用’ObjectId’查询MongoDB

我已经将document插入MongoDB而没有id 。 我想通过搜索默认分配的MongoDB ObjectId来检索它们。

这是我的尝试 –

 var query_id = Query.EQ("_id", "50ed4e7d5baffd13a44d0153"); var entity = dbCollection.FindOne(query_id); return entity.ToString(); 

我得到以下错误 –

发生了’System.NullReferenceException’类型的第一次机会exception

问题是什么?

您需要创建ObjectId的实例,然后使用该实例进行查询,否则您的查询会将ObjectId与String进行比较,并且无法找到匹配的文档。

这应该工作:

 var query_id = Query.EQ("_id", ObjectId.Parse("50ed4e7d5baffd13a44d0153")); var entity = dbCollection.FindOne(query_id); return entity.ToString(); 

C#最新官方MongoDB.Driver写这个 –

 var filter_id = Builders.Filter.Eq("id", ObjectId.Parse("50ed4e7d5baffd13a44d0153")); var entity = dbCollection.Find(filter).FirstOrDefault(); return entity.ToString(); 

我们可以在不将id从string转换为ObjectId情况下完成相同的结果。 但是,我们必须在模型类中的id属性之前添加[BsonRepresentation(BsonType.ObjectId)]

使用lambda表达式甚至可以进一步简化代码 –

 var entity = dbCollection.Find(document => document.id == "50ed4e7d5baffd13a44d0153").FirstOrDefault(); return entity.ToString(); 

所选答案是正确的。 对于任何被Query.EQ混淆的人,这是另一种编写基本更新的方法(更新整个mongodb文档):

 string mongoDocumentID = "123455666767778"; var query = new QueryDocument("_id", ObjectId.Parse(mongoDocumentID)); var update = new UpdateDocument { { "$set", documentToSave } }; mongoCollection.Update(query, update, UpdateFlags.Multi); 

当您想要按对象ID实际搜索时,需要ObjectId对象,否则它将字符串与objectid类型进行比较,并且它将不匹配。 无论字段名称是否正确,Mongo都以这种方式非常严格。

如果你在2018年在这里,并希望复制/粘贴代码仍然有效或纯字符串语法;

  [Fact] public async Task QueryUsingObjectId() { var filter = Builders.Filter.Eq("_id", new ObjectId("5b57516fd16cb04bfc35fcc6")); var entity = stocksCollection.Find(filter); var stock = await entity.SingleOrDefaultAsync(); Assert.NotNull(stock); var idString = "5b57516fd16cb04bfc35fcc6"; var stringFilter = "{ _id: ObjectId('" + idString + "') }"; var entityStringFiltered = stocksCollection.Find(stringFilter); var stockStringFiltered = await entityStringFiltered.SingleOrDefaultAsync(); Assert.NotNull(stockStringFiltered); } 

你也可以这样做,它

 public static ObjectId GetInternalId(string id) { if (!ObjectId.TryParse(id, out ObjectId internalId)) internalId = ObjectId.Empty; return internalId; } 

然后在你的方法中你可以做这样的事情

 ObjectId internalId = GetMongoId.GetInternalId(id); return await YourContext.YourTable.Find(c => c.InternalId == internalId).FirstOrDefaultAsync(); 

注意:GetInternalId中的id参数是该方法的参数。 万一你需要这样:

 public async Task Find(string id) { ObjectId internalId = GetMongoId.GetInternalId(id); return await YourContext.YourTable.Find(c => c.InternalId == internalId).FirstOrDefaultAsync(); } 

希望它也有帮助。