Elasticsearch數組內時間范圍篩選:如何高效查找change_records數組中指定時間范圍內元素個數達到N的文檔?

高效篩選elasticsearch數組內時間范圍數據

本文介紹如何高效地從Elasticsearch文檔中篩選出change_records數組內,change_time字段值位于特定時間范圍且元素個數達到指定數量的文檔。 我們面臨的挑戰是如何在不引發no field found錯誤的情況下,對數組內元素進行時間范圍篩選和計數。

問題:我們需要查詢change_records數組中,change_time字段值在指定時間范圍(例如,一年)內,元素個數不少于指定數量(例如,10個)的文檔。直接使用腳本查詢會導致字段未找到的錯誤。

解決方案:采用script_score查詢,結合自定義Painless腳本實現高效篩選。此方法避免了在Filter中直接使用腳本帶來的字段訪問問題。

查詢結構:

{   "query": {     "script_score": {       "query": {         "match_all": {}  // 可根據實際需求添加其他查詢條件       },       "script": {         "source": """           int count = 0;           for (Map record : doc['change_records']) {             long changeTime = record['change_time'];             if (changeTime >= params.start && changeTime <= params.end) {               count++;             }           }           return count >= params.n ? 1 : 0;         """,         "lang": "painless",         "params": {           "start": 1609459200000, // 2021年1月1日0時0分0秒的毫秒數           "end": 1704067200000,   // 2024年1月1日0時0分0秒的毫秒數           "n": 10                // 至少需要10個change_time在指定時間范圍內         }       }     }   } }

Elasticsearch數組內時間范圍篩選:如何高效查找change_records數組中指定時間范圍內元素個數達到N的文檔?

代碼解釋:

  • script_score:使用腳本評分來篩選文檔。
  • query:可以添加其他查詢條件,此處使用match_all匹配所有文檔。
  • script:Painless腳本,遍歷change_records數組。
    • count:計數器,統計滿足時間范圍條件的元素個數。
    • 循環體:獲取每個change_record的change_time,并判斷是否在指定范圍內。
    • return:如果count大于等于n,返回1(匹配),否則返回0(不匹配)。
  • params:腳本參數,包含時間范圍的起始和結束時間戳(毫秒),以及所需的最小匹配數量n。

此方法通過腳本評分,有效地解決了直接使用腳本查詢時遇到的字段訪問問題,并實現了對數組內元素的時間范圍篩選和計數功能,從而高效地查找滿足條件的文檔。 請確保您的change_records字段映射正確,并且change_time字段為數值類型(例如long)。

? 版權聲明
THE END
喜歡就支持一下吧
點贊5 分享