diff --git a/eos/db/gamedata/queries.py b/eos/db/gamedata/queries.py index 9b3865844..8a01e4dec 100644 --- a/eos/db/gamedata/queries.py +++ b/eos/db/gamedata/queries.py @@ -303,10 +303,10 @@ def getItemsByCategory(filter, where=None, eager=None): filter).all() -@cachedQuery(3, "where", "nameLike", "join") -def searchItems(nameLike, where=None, join=None, eager=None): - if not isinstance(nameLike, str): - raise TypeError("Need string as argument") +@cachedQuery(3, "tokens", "where", "join") +def searchItems(tokens, where=None, join=None, eager=None): + if not isinstance(tokens, (tuple, list)) or not all(isinstance(t, str) for t in tokens): + raise TypeError("Need tuple or list of strings as argument") if join is None: join = tuple() @@ -315,12 +315,11 @@ def searchItems(nameLike, where=None, join=None, eager=None): join = (join,) items = gamedata_session.query(Item).options(*processEager(eager)).join(*join) - for token in nameLike.split(' '): - token_safe = "%{0}%".format(sqlizeString(token)) + for token in tokens: if where is not None: - items = items.filter(and_(Item.name.like(token_safe, escape="\\"), where)) + items = items.filter(and_(Item.name.op('regexp')(token), where)) else: - items = items.filter(Item.name.like(token_safe, escape="\\")) + items = items.filter(Item.name.op('regexp')(token)) items = items.limit(100).all() return items diff --git a/service/jargon/jargon.py b/service/jargon/jargon.py index 95d3ae7f4..7f46a47c5 100644 --- a/service/jargon/jargon.py +++ b/service/jargon/jargon.py @@ -31,15 +31,14 @@ class Jargon: def get_rawdata(self) -> dict: return self._rawdata - def apply(self, query): - query_words = query.split() + def apply(self, query_words): parts = [] for word in query_words: replacement = self.get(word) if replacement: - parts.append(replacement) + parts.append('({}|{})'.format(word, replacement)) else: parts.append(word) - return ' '.join(parts) + return parts diff --git a/service/market.py b/service/market.py index d3a065d55..577f7b870 100644 --- a/service/market.py +++ b/service/market.py @@ -96,7 +96,7 @@ class SearchWorkerThread(threading.Thread): self.jargonLoader = JargonLoader.instance() # load the jargon while in an out-of-thread context, to spot any problems while in the main thread self.jargonLoader.get_jargon() - self.jargonLoader.get_jargon().apply('test string') + self.jargonLoader.get_jargon().apply('test string'.split()) self.running = True def run(self): @@ -138,24 +138,17 @@ class SearchWorkerThread(threading.Thread): else: filters = [None] - jargon_request = self.jargonLoader.get_jargon().apply(request) + requestTokens = request.split() + requestTokens = self.jargonLoader.get_jargon().apply(requestTokens) all_results = set() - if len(request) >= config.minItemSearchLength: + if len(' '.join(requestTokens)) >= config.minItemSearchLength: for filter_ in filters: - regular_results = eos.db.searchItems( - request, where=filter_, + filtered_results = eos.db.searchItems( + requestTokens, where=filter_, join=(types_Item.group, types_Group.category), eager=("group.category", "metaGroup")) - all_results.update(regular_results) - - if len(jargon_request) >= config.minItemSearchLength: - for filter_ in filters: - jargon_results = eos.db.searchItems( - jargon_request, where=filter_, - join=(types_Item.group, types_Group.category), - eager=("group.category", "metaGroup")) - all_results.update(jargon_results) + all_results.update(filtered_results) items = set() # Return only published items, consult with Market service this time