23 import traceback |
23 import traceback |
24 from itertools import repeat |
24 from itertools import repeat |
25 |
25 |
26 from rql import RQLSyntaxError, CoercionError |
26 from rql import RQLSyntaxError, CoercionError |
27 from rql.stmts import Union |
27 from rql.stmts import Union |
28 from rql.nodes import ETYPE_PYOBJ_MAP, etype_from_pyobj, Relation, Exists, Not |
28 from rql.nodes import ETYPE_PYOBJ_MAP, etype_from_pyobj, Relation, Exists, Not,\ |
|
29 VariableRef, Constant |
29 from yams import BASE_TYPES |
30 from yams import BASE_TYPES |
30 |
31 |
31 from cubicweb import ValidationError, Unauthorized, UnknownEid, QueryError |
32 from cubicweb import ValidationError, Unauthorized, UnknownEid, QueryError |
32 from cubicweb.rqlrewrite import RQLRelationRewriter |
33 from cubicweb.rqlrewrite import RQLRelationRewriter |
33 from cubicweb import Binary, server |
34 from cubicweb import Binary, server |
577 query_debug_informations["time"] = ((time.time() - start) * 1000) |
578 query_debug_informations["time"] = ((time.time() - start) * 1000) |
578 query_debug_informations["result"] = results |
579 query_debug_informations["result"] = results |
579 |
580 |
580 # build a description for the results if necessary |
581 # build a description for the results if necessary |
581 descr = () |
582 descr = () |
|
583 variables = None |
582 if build_descr: |
584 if build_descr: |
583 if rqlst.TYPE == 'select': |
585 if rqlst.TYPE == 'select': |
584 # sample selection |
586 # sample selection |
585 if len(rqlst.children) == 1 and len(rqlst.children[0].solutions) == 1: |
587 if len(rqlst.children) == 1 and len(rqlst.children[0].solutions) == 1: |
586 # easy, all lines are identical |
588 # easy, all lines are identical |
587 selected = rqlst.children[0].selection |
589 selected = rqlst.children[0].selection |
588 solution = rqlst.children[0].solutions[0] |
590 solution = rqlst.children[0].solutions[0] |
589 description = _make_description(selected, args, solution) |
591 description = _make_description(selected, args, solution) |
590 descr = RepeatList(len(results), tuple(description)) |
592 descr = RepeatList(len(results), tuple(description)) |
|
593 variables = [self._get_projected_name(projected, rqlst.children[0].stinfo) |
|
594 for projected in selected] |
591 else: |
595 else: |
592 # hard, delegate the work :o) |
596 # hard, delegate the work :o) |
593 descr = manual_build_descr(cnx, rqlst, args, results) |
597 descr = manual_build_descr(cnx, rqlst, args, results) |
594 elif rqlst.TYPE == 'insert': |
598 elif rqlst.TYPE == 'insert': |
595 # on insert plan, some entities may have been auto-casted, |
599 # on insert plan, some entities may have been auto-casted, |
603 query_debug_informations["description"] = descr |
607 query_debug_informations["description"] = descr |
604 |
608 |
605 emit_to_debug_channel("rql", query_debug_informations) |
609 emit_to_debug_channel("rql", query_debug_informations) |
606 |
610 |
607 # return a result set object |
611 # return a result set object |
608 return ResultSet(results, rql, args, descr) |
612 return ResultSet(results, rql, args, descr, variables) |
609 |
613 |
610 # these are overridden by set_log_methods below |
614 # these are overridden by set_log_methods below |
611 # only defining here to prevent pylint from complaining |
615 # only defining here to prevent pylint from complaining |
612 info = warning = error = critical = exception = debug = lambda msg,*a,**kw: None |
616 info = warning = error = critical = exception = debug = lambda msg,*a,**kw: None |
|
617 |
|
618 @staticmethod |
|
619 def _get_projected_name(projected, stinfo): |
|
620 if isinstance(projected, VariableRef): |
|
621 return projected.name |
|
622 elif isinstance(projected, Constant): |
|
623 if stinfo['rewritten'] is None: |
|
624 return str(projected) |
|
625 for name, value in stinfo['rewritten'].items(): |
|
626 if [projected] == value: |
|
627 return name |
|
628 return str(projected) |
613 |
629 |
614 |
630 |
615 class RQLCache(object): |
631 class RQLCache(object): |
616 |
632 |
617 def __init__(self, repo, schema): |
633 def __init__(self, repo, schema): |