From d933e296bc0c7970eb881b0bc715f8915d5c40ca Mon Sep 17 00:00:00 2001 From: "Gerry.tan" Date: Tue, 8 Jul 2025 11:17:51 +0800 Subject: [PATCH] perf: ES command log supports fuzzy search --- apps/audits/backends/es.py | 3 ++- apps/common/plugins/es.py | 19 +++++++++++++++++-- apps/terminal/backends/command/es.py | 5 +++-- 3 files changed, 22 insertions(+), 5 deletions(-) diff --git a/apps/audits/backends/es.py b/apps/audits/backends/es.py index 7947b8f04..eba1b0d29 100644 --- a/apps/audits/backends/es.py +++ b/apps/audits/backends/es.py @@ -35,6 +35,7 @@ class OperateLogStore(ES, metaclass=Singleton): } } exact_fields = {} + fuzzy_fields = {} match_fields = { 'id', 'user', 'action', 'resource_type', 'resource', 'remote_addr', 'org_id' @@ -44,7 +45,7 @@ class OperateLogStore(ES, metaclass=Singleton): } if not config.get('INDEX'): config['INDEX'] = 'jumpserver_operate_log' - super().__init__(config, properties, keyword_fields, exact_fields, match_fields) + super().__init__(config, properties, keyword_fields, exact_fields, fuzzy_fields, match_fields) self.pre_use_check() @staticmethod diff --git a/apps/common/plugins/es.py b/apps/common/plugins/es.py index 902b9d8db..1f77b3be7 100644 --- a/apps/common/plugins/es.py +++ b/apps/common/plugins/es.py @@ -123,7 +123,7 @@ def get_es_client_version(**kwargs): class ES(object): - def __init__(self, config, properties, keyword_fields, exact_fields=None, match_fields=None): + def __init__(self, config, properties, keyword_fields, exact_fields=None, fuzzy_fields=None, match_fields=None, **kwargs): self.version = 7 self.config = config hosts = self.config.get('HOSTS') @@ -140,7 +140,7 @@ class ES(object): self.index = None self.query_index = None self.properties = properties - self.exact_fields, self.match_fields, self.keyword_fields = set(), set(), set() + self.exact_fields, self.match_fields, self.keyword_fields, self.fuzzy_fields = set(), set(), set(), set() if isinstance(keyword_fields, Iterable): self.keyword_fields.update(keyword_fields) @@ -148,6 +148,8 @@ class ES(object): self.exact_fields.update(exact_fields) if isinstance(match_fields, Iterable): self.match_fields.update(match_fields) + if isinstance(fuzzy_fields, Iterable): + self.fuzzy_fields.update(fuzzy_fields) self.init_index() self.doc_type = self.config.get("DOC_TYPE") or '_doc' @@ -314,6 +316,13 @@ class ES(object): query: {k: v} }) return _filter + + @staticmethod + def handle_fuzzy_fields(exact): + _filter = [] + for k, v in exact.items(): + _filter.append({ 'wildcard': { k: f'*{v}*' } }) + return _filter @staticmethod def is_keyword(props: dict, field: str) -> bool: @@ -335,10 +344,12 @@ class ES(object): keyword_fields = self.keyword_fields exact_fields = self.exact_fields match_fields = self.match_fields + fuzzy_fields = self.fuzzy_fields match = {} search = [] exact = {} + fuzzy = {} index = {} if index_in_field in kwargs: @@ -360,6 +371,9 @@ class ES(object): elif k in common_keyword_able: exact[f"{k}.keyword"] = v + + elif k in fuzzy_fields: + fuzzy[f"{k}.keyword"] = v elif k in match_fields: match[k] = v @@ -405,6 +419,7 @@ class ES(object): {'match': item} for item in search ], 'filter': self.handle_exact_fields(exact) + + self.handle_fuzzy_fields(fuzzy) + [ { 'range': { diff --git a/apps/terminal/backends/command/es.py b/apps/terminal/backends/command/es.py index 36f1af44f..e7e8a7975 100644 --- a/apps/terminal/backends/command/es.py +++ b/apps/terminal/backends/command/es.py @@ -27,11 +27,12 @@ class CommandStore(ES): "type": "long" } } - exact_fields = {'input', 'risk_level', 'user', 'asset', 'account'} + exact_fields = {} + fuzzy_fields = {'input', 'risk_level', 'user', 'asset', 'account'} match_fields = {'input'} keyword_fields = {'session', 'org_id'} - super().__init__(config, properties, keyword_fields, exact_fields, match_fields) + super().__init__(config, properties, keyword_fields, exact_fields, fuzzy_fields, match_fields) @staticmethod def make_data(command):