From 2689bcf953eabbdea13c95644094a165a075a79a Mon Sep 17 00:00:00 2001 From: Thomas Steinacher Date: Fri, 21 Jun 2013 17:33:53 -0700 Subject: [PATCH] Transform certain $or queries into $in queries to boost performance. --- mongoengine/queryset/visitor.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/mongoengine/queryset/visitor.py b/mongoengine/queryset/visitor.py index 41f4ebf..3783e7a 100644 --- a/mongoengine/queryset/visitor.py +++ b/mongoengine/queryset/visitor.py @@ -28,7 +28,7 @@ class DuplicateQueryConditionsError(InvalidQueryError): class SimplificationVisitor(QNodeVisitor): - """Simplifies query trees by combinging unnecessary 'and' connection nodes + """Simplifies query trees by combining unnecessary 'and' connection nodes into a single Q-object. """ @@ -73,6 +73,16 @@ class QueryCompilerVisitor(QNodeVisitor): def visit_combination(self, combination): operator = "$and" if combination.operation == combination.OR: + keys = set([key for q in combination.children for key in q.keys()]) + if len(keys) == 1: + field = keys.pop() + if not field.startswith('$') and not any([isinstance(q[field], dict) for q in combination.children]): + return { + field: { + '$in': [q[field] for q in combination.children if field in q] + } + } + operator = "$or" return {operator: combination.children}