【问题标题】:MongoDB aggregation with a wildcard in the group组中带有通配符的 MongoDB 聚合
【发布时间】:2014-03-22 02:40:34
【问题描述】:

我在 MongoDB 中有一组构建统计信息,我想知道是否可以对其中一个字段进行通配符聚合查询。

这是一个示例文档:

    {
            "_id" : ObjectId("52deab2fe4b0a491abb54108"),
            "type" : "build",
            "time" : ISODate("2014-01-21T17:15:27.471Z"),
            "data" : {
                    "buildNumber" : 43,
                    "buildDuration" : 997308,
                    "buildProjectName" : "Mobile_February",
                    "branch" : "FEB"
                    "buildResult" : "SUCCESS"
            }
    }

我有这个查询,它将按日期和分支为我提供平均构建持续时间:

    db.builds.aggregate([
        { $group: { 
            _id: { 
                month: { $month: "$time" },
                day: { $dayOfMonth: "$time" },
                year: { $year: "$time" }, 
                branch: "$data.branch", 
            },
            buildDuration: { $avg: "$data.buildDuration" } 
        } },
        { $sort: { "_id.year": 1, "_id.month": 1, "_id.day": 1, "_id.branch": 1 } }
    ])

我们有几个相同类型的构建作业 - 每个月一个。有 Mobile_February、Mobile_March 等。我们对其他工作也有相同的标准...OtherJob_February、OtherJob_March 等。

我想知道是否有某种特定类型的工作运行时间更长或更短。这意味着我不会在分支上分组,而是在 buildProjectName 上分组,但它必须是通配符搜索才能带回 Mobile_* 和 OtherJob_* 的分组

这对 MongoDB 可行吗?一种解决方案是添加一个新的元素名称——比如“jobType”:“Mobile”,但如果 MongoDB 有办法使用现有数据来做这件事,这似乎很浪费。

谢谢!

【问题讨论】:

    标签: mongodb


    【解决方案1】:

    MongoDB 聚合框架具有$substr-operator,它返回字符串的固定长度部分。这有点小技巧,但它允许您根据值的前 x 个字符进行分组。

    db.builds.aggregate([
        { $group: { 
            _id: { 
                month: { $month: "$time" },
                day: { $dayOfMonth: "$time" },
                year: { $year: "$time" }, 
                branch: "$data.branch", 
                jobType: { $substr: [ "$data.buildProjectName", 0, 6] } // <--
            },
            buildDuration: { $avg: "$data.buildDuration" } 
        } },
        { $sort: { "_id.year": 1, "_id.month": 1, "_id.day": 1, "_id.branch": 1 } }
    ])
    

    这将创建两个额外的分组“JobType”,在本例中为“Mobile”和“OtherJ”

    【讨论】:

    • 我认为如果我们的工作名称的第一部分相似或大小相同,这将起作用,但不幸的是它们的长度差异很大。
    • 可以用子字符串和正则表达式做点什么吗?即:stackoverflow.com/questions/6538884/…
    【解决方案2】:

    假设您的所有工作类型至少有 6 个字符长,您可以使用 $substr 运算符提取前 6 个字符并按该字段分组。示例:

    > db.test.aggregate([{$project:{type:{$substr:["$data.buildProjectName", 0, 6]}}}])
    {
            "result" : [
                    {
                            "_id" : ObjectId("52deab2fe4b0a491abb54108"),
                            "type" : "Mobile"
                    },
                    {
                            "_id" : ObjectId("52deab2fe4b0a491abb54109"),
                            "type" : "OtherJ"
                    }
            ],
            "ok" : 1
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-02-06
      • 2020-08-20
      • 2019-07-17
      • 2013-07-12
      • 1970-01-01
      • 1970-01-01
      • 2021-08-25
      相关资源
      最近更新 更多