Loading cloudcontrol/common/tql/db/db.py +8 −0 Original line number Original line Diff line number Diff line Loading @@ -32,6 +32,7 @@ from cloudcontrol.common.datastructures.ordereddict import OrderedDict from cloudcontrol.common.tql.parser.ast import (Filter, FilterPresence, from cloudcontrol.common.tql.parser.ast import (Filter, FilterPresence, UnionOperator, UnionOperator, IntersectionOperator, IntersectionOperator, DifferenceOperator, ShowOperator, LimitOperator, ShowOperator, LimitOperator, SortOperator) SortOperator) Loading Loading @@ -380,6 +381,8 @@ class TqlDatabase(object): return self._evaluate_union(objects, expression) return self._evaluate_union(objects, expression) elif isinstance(expression, IntersectionOperator): elif isinstance(expression, IntersectionOperator): return self._evaluate_intersection(objects, expression) return self._evaluate_intersection(objects, expression) elif isinstance(expression, DifferenceOperator): return self._evaluate_difference(objects, expression) elif isinstance(expression, ShowOperator): elif isinstance(expression, ShowOperator): return self._evaluate_show(objects, expression) return self._evaluate_show(objects, expression) elif isinstance(expression, SortOperator): elif isinstance(expression, SortOperator): Loading Loading @@ -408,6 +411,11 @@ class TqlDatabase(object): right = self._evaluate_expression(objects, intersection.right_expression) right = self._evaluate_expression(objects, intersection.right_expression) return left & right return left & right def _evaluate_difference(self, objects, difference): left = self._evaluate_expression(objects, difference.left_expression) right = self._evaluate_expression(objects, difference.right_expression) return left - right def _evaluate_show(self, objects, show): def _evaluate_show(self, objects, show): objects = self._evaluate_expression(objects, show.expression) objects = self._evaluate_expression(objects, show.expression) for obj in objects: for obj in objects: Loading cloudcontrol/common/tql/parser/ast.py +8 −0 Original line number Original line Diff line number Diff line Loading @@ -123,6 +123,14 @@ class IntersectionOperator(BinaryOperator): SYMBOL = '&' SYMBOL = '&' class DifferenceOperator(BinaryOperator): """ A difference operator (eg: expr/expr). """ SYMBOL = '/' class ShowOperator(object): class ShowOperator(object): """ A show operator (eg: $tag). """ A show operator (eg: $tag). Loading cloudcontrol/common/tql/parser/parser.py +12 −8 Original line number Original line Diff line number Diff line Loading @@ -23,8 +23,8 @@ import ply.lex as lex import ply.yacc as yacc import ply.yacc as yacc from ast import (TqlAst, Filter, FilterPresence, UnionOperator, from ast import (TqlAst, Filter, FilterPresence, UnionOperator, IntersectionOperator, ShowOperator, SortOperator, IntersectionOperator, DifferenceOperator, ShowOperator, LimitOperator) SortOperator, LimitOperator) from errors import ParsingError from errors import ParsingError Loading Loading @@ -61,12 +61,13 @@ class TqlLexer(object): # Tokens # Tokens # # tokens = ('UNION', 'INTERSECTION', 'CIRCUMFLEX', 'DOLLAR', 'PERCENT', tokens = ('UNION', 'INTERSECTION', 'DIFFERENCE', 'CIRCUMFLEX', 'DOLLAR', 'EQUAL', 'COLON', 'TILDE', 'GT', 'GTE', 'LT', 'LTE', 'NOT', 'PERCENT', 'EQUAL', 'COLON', 'TILDE', 'GT', 'GTE', 'LT', 'LTE', 'WORD', 'TEXT', 'LEFT_PAR', 'RIGHT_PAR', 'EOL') 'NOT', 'WORD', 'TEXT', 'LEFT_PAR', 'RIGHT_PAR', 'EOL') t_UNION = '\|' t_UNION = '\|' t_INTERSECTION = '&' t_INTERSECTION = '&' t_DIFFERENCE = '/' t_CIRCUMFLEX = '\^' t_CIRCUMFLEX = '\^' t_DOLLAR = '\$' t_DOLLAR = '\$' t_PERCENT = '%' t_PERCENT = '%' Loading @@ -78,7 +79,7 @@ class TqlLexer(object): t_LT = '<' t_LT = '<' t_LTE = '<=' t_LTE = '<=' t_NOT = '!' t_NOT = '!' t_WORD = '[^ |&^$%=:~>>=<<=!()]+' t_WORD = '[^ |&^$%=:~>>=<<=!()/]+' t_LEFT_PAR = '\(' t_LEFT_PAR = '\(' t_RIGHT_PAR = '\)' t_RIGHT_PAR = '\)' t_ignore = ' \t' t_ignore = ' \t' Loading Loading @@ -195,11 +196,14 @@ class TqlParser(object): def p_expression_binary(self, p): def p_expression_binary(self, p): """expression : expression UNION expression """expression : expression UNION expression | expression INTERSECTION expression""" | expression INTERSECTION expression | expression DIFFERENCE expression""" if p[2] == '|': if p[2] == '|': p[0] = UnionOperator(p[1], p[3]) p[0] = UnionOperator(p[1], p[3]) else: elif p[2] == '&': p[0] = IntersectionOperator(p[1], p[3]) p[0] = IntersectionOperator(p[1], p[3]) else: p[0] = DifferenceOperator(p[1], p[3]) def p_expression_show(self, p): def p_expression_show(self, p): """expression : expression DOLLAR WORD""" """expression : expression DOLLAR WORD""" Loading Loading
cloudcontrol/common/tql/db/db.py +8 −0 Original line number Original line Diff line number Diff line Loading @@ -32,6 +32,7 @@ from cloudcontrol.common.datastructures.ordereddict import OrderedDict from cloudcontrol.common.tql.parser.ast import (Filter, FilterPresence, from cloudcontrol.common.tql.parser.ast import (Filter, FilterPresence, UnionOperator, UnionOperator, IntersectionOperator, IntersectionOperator, DifferenceOperator, ShowOperator, LimitOperator, ShowOperator, LimitOperator, SortOperator) SortOperator) Loading Loading @@ -380,6 +381,8 @@ class TqlDatabase(object): return self._evaluate_union(objects, expression) return self._evaluate_union(objects, expression) elif isinstance(expression, IntersectionOperator): elif isinstance(expression, IntersectionOperator): return self._evaluate_intersection(objects, expression) return self._evaluate_intersection(objects, expression) elif isinstance(expression, DifferenceOperator): return self._evaluate_difference(objects, expression) elif isinstance(expression, ShowOperator): elif isinstance(expression, ShowOperator): return self._evaluate_show(objects, expression) return self._evaluate_show(objects, expression) elif isinstance(expression, SortOperator): elif isinstance(expression, SortOperator): Loading Loading @@ -408,6 +411,11 @@ class TqlDatabase(object): right = self._evaluate_expression(objects, intersection.right_expression) right = self._evaluate_expression(objects, intersection.right_expression) return left & right return left & right def _evaluate_difference(self, objects, difference): left = self._evaluate_expression(objects, difference.left_expression) right = self._evaluate_expression(objects, difference.right_expression) return left - right def _evaluate_show(self, objects, show): def _evaluate_show(self, objects, show): objects = self._evaluate_expression(objects, show.expression) objects = self._evaluate_expression(objects, show.expression) for obj in objects: for obj in objects: Loading
cloudcontrol/common/tql/parser/ast.py +8 −0 Original line number Original line Diff line number Diff line Loading @@ -123,6 +123,14 @@ class IntersectionOperator(BinaryOperator): SYMBOL = '&' SYMBOL = '&' class DifferenceOperator(BinaryOperator): """ A difference operator (eg: expr/expr). """ SYMBOL = '/' class ShowOperator(object): class ShowOperator(object): """ A show operator (eg: $tag). """ A show operator (eg: $tag). Loading
cloudcontrol/common/tql/parser/parser.py +12 −8 Original line number Original line Diff line number Diff line Loading @@ -23,8 +23,8 @@ import ply.lex as lex import ply.yacc as yacc import ply.yacc as yacc from ast import (TqlAst, Filter, FilterPresence, UnionOperator, from ast import (TqlAst, Filter, FilterPresence, UnionOperator, IntersectionOperator, ShowOperator, SortOperator, IntersectionOperator, DifferenceOperator, ShowOperator, LimitOperator) SortOperator, LimitOperator) from errors import ParsingError from errors import ParsingError Loading Loading @@ -61,12 +61,13 @@ class TqlLexer(object): # Tokens # Tokens # # tokens = ('UNION', 'INTERSECTION', 'CIRCUMFLEX', 'DOLLAR', 'PERCENT', tokens = ('UNION', 'INTERSECTION', 'DIFFERENCE', 'CIRCUMFLEX', 'DOLLAR', 'EQUAL', 'COLON', 'TILDE', 'GT', 'GTE', 'LT', 'LTE', 'NOT', 'PERCENT', 'EQUAL', 'COLON', 'TILDE', 'GT', 'GTE', 'LT', 'LTE', 'WORD', 'TEXT', 'LEFT_PAR', 'RIGHT_PAR', 'EOL') 'NOT', 'WORD', 'TEXT', 'LEFT_PAR', 'RIGHT_PAR', 'EOL') t_UNION = '\|' t_UNION = '\|' t_INTERSECTION = '&' t_INTERSECTION = '&' t_DIFFERENCE = '/' t_CIRCUMFLEX = '\^' t_CIRCUMFLEX = '\^' t_DOLLAR = '\$' t_DOLLAR = '\$' t_PERCENT = '%' t_PERCENT = '%' Loading @@ -78,7 +79,7 @@ class TqlLexer(object): t_LT = '<' t_LT = '<' t_LTE = '<=' t_LTE = '<=' t_NOT = '!' t_NOT = '!' t_WORD = '[^ |&^$%=:~>>=<<=!()]+' t_WORD = '[^ |&^$%=:~>>=<<=!()/]+' t_LEFT_PAR = '\(' t_LEFT_PAR = '\(' t_RIGHT_PAR = '\)' t_RIGHT_PAR = '\)' t_ignore = ' \t' t_ignore = ' \t' Loading Loading @@ -195,11 +196,14 @@ class TqlParser(object): def p_expression_binary(self, p): def p_expression_binary(self, p): """expression : expression UNION expression """expression : expression UNION expression | expression INTERSECTION expression""" | expression INTERSECTION expression | expression DIFFERENCE expression""" if p[2] == '|': if p[2] == '|': p[0] = UnionOperator(p[1], p[3]) p[0] = UnionOperator(p[1], p[3]) else: elif p[2] == '&': p[0] = IntersectionOperator(p[1], p[3]) p[0] = IntersectionOperator(p[1], p[3]) else: p[0] = DifferenceOperator(p[1], p[3]) def p_expression_show(self, p): def p_expression_show(self, p): """expression : expression DOLLAR WORD""" """expression : expression DOLLAR WORD""" Loading