4

一些背景:

我通过 mongo-elasticsearch 河将 MongoDB 与 ElasticSearch 结合使用。在 Elasticsearch 中,我希望我的文档结构如下所示:

{
    "_id": "SomeId-AnotherId",

    ... // all the other lovely denormalized data
}

SomeId-AnotherId 是我在非规范化数据时创建的。我需要这种结构的原因是我需要能够说http://elasticsearch/index/type/SomeId-AnotherId检索文档。

我将我的数据(一个 C# 应用程序)非规范化,然后插入到 MongoDB 中(这些数据然后通过上述河流进入 ES)。当我插入 MongoDB 时,我目前的印象是我需要在我的模型上设置一个 BsonId,Mongo 使用它来索引文档。这可以是 ObjectId 或任何其他类型,例如 string 或 int 等,只要我添加 [BsonId] 属性即可。

我的模型如下所示:

public class Model {
    [BsonId]
    public string Id {get;set;}
}

我这样设置:

model.Id = string.format("{0}-{1}", someId, anotherId);

问题

目前,我看到约 1,500 个文档从约 10,000 个插入中进入 Mongo。我查看了为模型对象生成的 id,肯定有很多超过 12 个字节。mongo会拒绝那些而不写它们吗?

Bson Id 是 12 字节 - 这是否意味着如果我创建自己的 ID(格式:“SomeId-AnotherId”)也应该只有 12 字节长?无论如何围绕这个?

我不想对这些文档使用 mongos 默认 objectId,因为如上所述,一旦文档在 elasticsearch 中,我希望能够以特定方式获取文档(在 URI 中使用“SomeId-AnotherId”)。

最后说明:

我知道我可以将另一个 ID 属性添加到我的模型中,称为 ElasticId 之类的东西,然后配置 Elasticsearch 以查找此属性并将其用作 elasticsearch 文档的 _id。如果我这样做了,那么我可以使用 Mongos 默认 ID,一切都会好起来的。但是,我会牺牲弹性搜索性能,并且我还需要在弹性搜索中存储一个我不想要的额外字段。

对不起,顺便说一句,大量的大脑转储!:)

4

2 回答 2

9

_idMongoDB 文档的字段可以是 12 字节的 UUID,但不是必须的。根据文档,您可以使用任何非数组值作为_id,只要您可以确保它是唯一的。

于 2012-11-27T15:33:48.613 回答
4

好的,我现在已经解决了。回想起来,这有点明显,对我来说是一个巨大的疏忽。

我分批插入 10,000 条,但记录总数超过 4000 万条。我的 id 保证在每批的基础上都是唯一的 - 所以在其他批次中可能会有重复。

我打开了安全模式并开始看到我得到的异常——它们来自 mongo,它们是重复的关键异常。我发现 mongo csharp 客户端在收到重复键错误后会立即删除批处理中的所有剩余数据。所以我看到一批的前 1500 个进入,然后我收到一个重复的密钥错误,然后批次的其余部分没有被插入。这完全有道理。

所以现在我正在做单次插入,实际上几乎和批量插入一样快。当我收到重复键错误时,我会记录它,但会继续进行,因为我不关心我的场景中的重复项。

感谢@Philipp 的帮助。

于 2012-11-28T13:31:13.290 回答