1

我想知道是否有人知道您是否可以在 MongoDB 上过度使用嵌入。不是说像 100 层那样深,在我的应用程序中,我的平均文档大小会变得非常大,简单的测试显示文档为 177kb。

该应用程序用于日志记录,例如,我获取 Apache 访问日志并从中获取很多信息,例如所有被调用页面的列表、所有 IP 地址的点亮等等。这些都是按分钟完成的。

我不太可能拥有一个处于 MongoDB 文档大小限制的文档,但想知道我是否将每个子列表保留为自己的文档,这是否会提高性能,返回子集信息(查询对于发生在 5 分钟内的所有 IP 地址)。

当我运行查询时,我过滤以仅显示 IP 地址,如果我将每一分钟分组到一个文档中,我是否会浪费数据库性能,或者如果我将每个列表拆分为自己的文档,我是否会浪费它?

4

1 回答 1

2

您希望以反映您打算如何使用数据的方式来构建您的集合和文档。如果您要执行大量复杂查询,尤其是子文档,您可能会发现将文档拆分为单独的集合更容易。这方面的一个例子是从博客文章中拆分评论。

您的评论可以存储为子文档数组:

# Example post document with comment subdocuments
{
    title: 'How to Mongo!'
    content: 'So I want to talk about MongoDB.',
    comments: [
        {
            author: 'Renold',
            content: 'This post, it's amazing.'
        },
        ...
    ]
}

但是,如果您只想对评论进行复杂查询(例如,从所有帖子中选择最新评论或获取一位作者的所有评论),这可能会导致问题。如果您打算进行这些复杂查询,那么您会更好关闭创建两个集合:一个用于评论,另一个用于帖子。

# Example post document with "ForeignKeys" to comment documents
{
    _id: ObjectId("50c21579c5f2c80000000000"),
    title: 'How to Mongo!',
    content: 'So I want to talk about MongoDB.',
    comments: [
        ObjectId("50c21579c5f2c80000000001"),
        ObjectId("50c21579c5f2c80000000002"),
        ...
    ]
}

# Example comment document with a "ForeignKey" to a post document
{
    _id: ObjectId("50c21579c5f2c80000000001"),
    post_id: ObjectId("50c21579c5f2c80000000000"),
    title: 'Renold',
    content: 'This post, it's amazing.'
}

这类似于您在关系数据库中存储“外键”的方式。像这样规范化您的文档可以轻松查询评论和帖子。此外,由于您正在拆分文档,因此每个文档将占用更少的内存。但是,权衡是,ObjectId只要任一文档发生更改(例如,当您插入/更新/删除评论或帖子时),您都必须维护引用。而且由于 Mongo 中没有事件挂钩,因此您必须这样做您的应用程序中的所有这些维护。

另一方面,如果您不打算对文档的子文档进行任何复杂的查询,您可能会从存储单体对象中受益。例如,用户的偏好不是您可能会查询的内容:

# Example user document with address subdocument
{
    ObjectId("50c21579c5f2c800000000421"),
    name: 'Howard',
    password: 'naughtysecret',
    address: {
        state: 'FL',
        city: 'Gainesville',
        zip: 32608
    }
}
于 2012-12-10T03:20:51.927 回答