小能豆

根据字段上的自定义比较函数对 ElasticSearch 结果进行排序

py

如果我想从按评级排序的弹性中获取驱动程序数据,其中评级可能是["good", "ok", "bad"],如何编写查询以帮助我按好 > 正常 > 差的顺序获取数据

排序后的响应列表:

[{
    "name": "driver1",
    "rating": "good"
},
{
    "name": "driver3",
    "rating": "good"
},
{
    "name": "driver2",
    "rating": "ok"
},
{
    "name": "driver4",
    "rating": "bad"
}]

阅读 19

收藏
2025-01-01

共1个答案

小能豆

要从 Elasticsearch 中按 ["good", "ok", "bad"] 的自定义顺序排序驱动程序数据,可以使用一种称为 脚本排序 的方法。以下是一个示例查询,它通过 script_score 设置自定义排序顺序:

查询

GET /drivers/_search
{
  "query": {
    "function_score": {
      "query": {
        "match_all": {}
      },
      "functions": [
        {
          "script_score": {
            "script": {
              "source": """
                def rating_order = ['good': 3, 'ok': 2, 'bad': 1];
                return rating_order.containsKey(doc['rating.keyword'].value) 
                  ? rating_order[doc['rating.keyword'].value] : 0;
              """
            }
          }
        }
      ],
      "boost_mode": "replace"
    }
  },
  "sort": [
    {
      "_score": {
        "order": "desc"
      }
    }
  ]
}

响应解释

  1. 查询中的逻辑:
  2. 使用 rating_order 作为映射,将 good 评分分配为 3,ok 分配为 2,bad 分配为 1。
  3. 使用 doc['rating.keyword'].value 获取文档的 rating 值并映射到上述权重。如果值不存在,则默认权重为 0

  4. 排序方式:

  5. 通过 script_score,计算分数并用作排序依据。
  6. sort 部分按 _score 值降序排列。

  7. 示例结果:
    响应将按 good > ok > bad 的顺序排序。

前提条件

  1. 确保 rating 字段是一个 keyword 类型,或者在查询中使用 .keyword
  2. 将评分值设置为可以映射的固定字符串。

其他优化

如果数据规模较大,建议在索引时添加自定义字段,例如 rating_score,直接将数值存储为 321,并在查询时按该字段排序以提高性能。

2025-01-01