有没有一种方法可以在使用elasticsearch或opensearch API的过滤器上使用脚本filelds计算?

pxiryf3j  于 7个月前  发布在  ElasticSearch
关注(0)|答案(1)|浏览(50)

我有一个使用脚本字段计算价格的elasticsearch查询。然而,我想使用计算值进行过滤,但我无法在脚本查询中访问它。有没有方法可以在过滤器中使用脚本字段?
我在Ruby on Rails应用程序上使用Searchkick gem。我有以下搜索查询

{
  script_fields: {
    total_stay_fee: {
      script: {
        source: "
          def totalStay = params.total_stay;
          def defaultRate = params['_source']['default_rate'];

          return totalStay * defaultRate;
        ",
        params: {
          total_stay: 12
        }
      }
    }
  },
  _source: ["*"],
  query: {
    function_score: {
      query: {
        bool: {
          filter: {
            range: {
              total_stay_fee: {
                gte: 12,
                lte: 100
              }
            }
          },
        }
      },
      boost_mode: "replace",
      score_mode: "first"
    }
  }
}

字符串
我已经计算了total_stay_fee的值,但是我想根据它的值过滤结果。我如何实现这一点?
另外,值得注意的是defaultRate是动态的,所以我也不能真正索引和使用它。

yduiuuwa

yduiuuwa1#

我认为最有效的方法是将gtelte中的值除以12,然后与defaultRate进行比较。
然而,假设你有一个更复杂的方程,你可以使用script查询。你不能在脚本查询中使用_source,因为它会对大型数据集的性能产生负面影响,但你可以使用doc值。

DELETE test
PUT test
{
  "mappings": {
    "properties": {
      "default_rate": {
        "type": "double"
      }
    }
  }
}

POST test/_bulk?refresh
{"index":{}}
{"default_rate":0.5}
{"index":{}}
{"default_rate":1}
{"index":{}}
{"default_rate":5}
{"index":{}}
{"default_rate":7}
{"index":{}}
{"default_rate":10}

POST test/_search
{
  "script_fields": {
    "total_stay_fee": {
      "script": {
        "source": """
          def totalStay = params.total_stay;
          def defaultRate = params['_source']['default_rate'];

          return totalStay * defaultRate;
        """,
        "params": {
          "total_stay": 12
        }
      }
    }
  },
  "_source": [
    "*"
  ],
  "query": {
    "bool": {
      "filter": [
        {
          "script": {
            "script": {
              "source": """
                 def totalStay = params.total_stay;
                 def defaultRate = doc['default_rate'].value;
                 def total_stay_fee = totalStay * defaultRate;
                 return total_stay_fee >=  params.gte && total_stay_fee <=  params.lte;
              """,
              "params": {
                "total_stay": 12,
                "gte": 12,
                "lte": 100
              }
            }
          }
        }
      ]
    }
  }
}

字符串

相关问题