如何使用静态值和其他字段值降序对MongoDB集合进行排序

mw3dktmi  于 2023-05-28  发布在  Go
关注(0)|答案(2)|浏览(111)

我的集合是一个具有以下结构的产品列表

{
      _id
      name
      status  // enum ['active','sold','reserved','pending']
      .
      .
      createdAt
    }

我需要的是一个排序特性沿着传递给系统的状态值,下面我将给予一个例子
case:如果status = 'active',则结果应按以下方式排序
所有产品的状态活动应首先(活动列表本身应在createdAt desc顺序)
剩余产品应按描述顺序列出createdAt
所有其他状态值也是如此。
如果状态为空,则按描述顺序列出所有内容
我尝试的是下面给出的

db.products.aggregate([
         {
            $project: {
            "_id":1,
            "name":1,
            "status":1,
            "createdAt":1
            }
         },
         {$sort:{status:"active", createdAt:-1}}, // Error
         {$sort:{status:1, createdAt:-1}}, // Result work but not as expected
    ])

任何帮助将不胜感激

flseospp

flseospp1#

我设法得到一个解决方案,这是下面列出的,但我愿意接受任何更好的解决方案,如果存在

db.products.aggregate([
         {
            $project: {
            "_id":1,
            "name":1,
            "status":1,
            "createdAt":1,
            "timeStamp": {
             "$switch": {
                "branches": [
                    { "case": { "$eq": [ "$status", "pending" ] }, "then": 99999999999999 },
                ],
                "default": {"$toLong": "$createdAt"}
                 }
              },
                "createdTime": {
                             "$toLong": "$createdAt"
                           }
              }
         },
         {$sort:{timeStamp:-1, createdTime:-1}}
    ])
jljoyd4f

jljoyd4f2#

另一种选择是创建一个单独的字段,指定哪个状态值最先出现
1.添加一个字段sortBy,如果它的状态值应该首先出现,则分配0,否则分配1
1.执行通常的排序sortBy升序和createdAt降序
1.使用project从输出结果中删除新添加的字段

const status = 'active'

db.products.aggregate([
  { $addFields: { sortBy: { $cond: [ { $eq: [ "$status", status ] }, 0, 1 ] } } },
  { $sort: { sortBy: 1, createdAt: -1 } },
  { $project: { sortBy: 0 } }
])

playground

相关问题