equal
deleted
inserted
replaced
53 from cubicweb import _ |
53 from cubicweb import _ |
54 |
54 |
55 from functools import reduce |
55 from functools import reduce |
56 from copy import deepcopy |
56 from copy import deepcopy |
57 from datetime import datetime, timedelta |
57 from datetime import datetime, timedelta |
58 |
|
59 from six import text_type, string_types |
|
60 |
58 |
61 from logilab.mtconverter import xml_escape |
59 from logilab.mtconverter import xml_escape |
62 from logilab.common.graph import has_path |
60 from logilab.common.graph import has_path |
63 from logilab.common.decorators import cached, cachedproperty |
61 from logilab.common.decorators import cached, cachedproperty |
64 from logilab.common.date import datetime2ticks, ustrftime, ticks2datetime |
62 from logilab.common.date import datetime2ticks, ustrftime, ticks2datetime |
643 self.role, select_target_entity=True) |
641 self.role, select_target_entity=True) |
644 else: |
642 else: |
645 insert_attr_select_relation( |
643 insert_attr_select_relation( |
646 select, self.filtered_variable, self.rtype, self.role, |
644 select, self.filtered_variable, self.rtype, self.role, |
647 self.target_attr, select_target_entity=False) |
645 self.target_attr, select_target_entity=False) |
648 values = [text_type(x) for x, in self.rqlexec(select.as_string())] |
646 values = [str(x) for x, in self.rqlexec(select.as_string())] |
649 except Exception: |
647 except Exception: |
650 self.exception('while computing values for %s', self) |
648 self.exception('while computing values for %s', self) |
651 return [] |
649 return [] |
652 finally: |
650 finally: |
653 select.recover() |
651 select.recover() |
694 |
692 |
695 def rset_vocabulary(self, rset): |
693 def rset_vocabulary(self, rset): |
696 if self.i18nable: |
694 if self.i18nable: |
697 tr = self._cw._ |
695 tr = self._cw._ |
698 else: |
696 else: |
699 tr = text_type |
697 tr = str |
700 if self.rql_sort: |
698 if self.rql_sort: |
701 values = [(tr(label), eid) for eid, label in rset] |
699 values = [(tr(label), eid) for eid, label in rset] |
702 else: |
700 else: |
703 if self.label_vid is None: |
701 if self.label_vid is None: |
704 values = [(tr(label), eid) for eid, label in rset] |
702 values = [(tr(label), eid) for eid, label in rset] |
718 |
716 |
719 def value_restriction(self, restrvar, rel, value): |
717 def value_restriction(self, restrvar, rel, value): |
720 # XXX handle rel is None case in RQLPathFacet? |
718 # XXX handle rel is None case in RQLPathFacet? |
721 if self.restr_attr != 'eid': |
719 if self.restr_attr != 'eid': |
722 self.select.set_distinct(True) |
720 self.select.set_distinct(True) |
723 if isinstance(value, string_types): |
721 if isinstance(value, str): |
724 # only one value selected |
722 # only one value selected |
725 if value: |
723 if value: |
726 self.select.add_constant_restriction( |
724 self.select.add_constant_restriction( |
727 restrvar, self.restr_attr, value, |
725 restrvar, self.restr_attr, value, |
728 self.restr_attr_type) |
726 self.restr_attr_type) |
882 |
880 |
883 def rset_vocabulary(self, rset): |
881 def rset_vocabulary(self, rset): |
884 if self.i18nable: |
882 if self.i18nable: |
885 tr = self._cw._ |
883 tr = self._cw._ |
886 else: |
884 else: |
887 tr = text_type |
885 tr = str |
888 if self.rql_sort: |
886 if self.rql_sort: |
889 return [(tr(value), value) for value, in rset] |
887 return [(tr(value), value) for value, in rset] |
890 values = [(tr(value), value) for value, in rset] |
888 values = [(tr(value), value) for value, in rset] |
891 return sorted(values, reverse=not self.sortasc) |
889 return sorted(values, reverse=not self.sortasc) |
892 |
890 |
1035 ('filter_variable and label_variable should be different. ' |
1033 ('filter_variable and label_variable should be different. ' |
1036 'You may want to let label_variable undefined (ie None).') |
1034 'You may want to let label_variable undefined (ie None).') |
1037 assert self.path and isinstance(self.path, (list, tuple)), \ |
1035 assert self.path and isinstance(self.path, (list, tuple)), \ |
1038 'path should be a list of 3-uples, not %s' % self.path |
1036 'path should be a list of 3-uples, not %s' % self.path |
1039 for part in self.path: |
1037 for part in self.path: |
1040 if isinstance(part, string_types): |
1038 if isinstance(part, str): |
1041 part = part.split() |
1039 part = part.split() |
1042 assert len(part) == 3, \ |
1040 assert len(part) == 3, \ |
1043 'path should be a list of 3-uples, not %s' % part |
1041 'path should be a list of 3-uples, not %s' % part |
1044 |
1042 |
1045 def __repr__(self): |
1043 def __repr__(self): |
1088 select.save_state() |
1086 select.save_state() |
1089 try: |
1087 try: |
1090 cleanup_select(select, self.filtered_variable) |
1088 cleanup_select(select, self.filtered_variable) |
1091 varmap, restrvar = self.add_path_to_select(skiplabel=True) |
1089 varmap, restrvar = self.add_path_to_select(skiplabel=True) |
1092 select.append_selected(nodes.VariableRef(restrvar)) |
1090 select.append_selected(nodes.VariableRef(restrvar)) |
1093 values = [text_type(x) for x, in self.rqlexec(select.as_string())] |
1091 values = [str(x) for x, in self.rqlexec(select.as_string())] |
1094 except Exception: |
1092 except Exception: |
1095 self.exception('while computing values for %s', self) |
1093 self.exception('while computing values for %s', self) |
1096 return [] |
1094 return [] |
1097 finally: |
1095 finally: |
1098 select.recover() |
1096 select.recover() |
1111 |
1109 |
1112 def add_path_to_select(self, skiplabel=False, skipattrfilter=False): |
1110 def add_path_to_select(self, skiplabel=False, skipattrfilter=False): |
1113 varmap = {'X': self.filtered_variable} |
1111 varmap = {'X': self.filtered_variable} |
1114 actual_filter_variable = None |
1112 actual_filter_variable = None |
1115 for part in self.path: |
1113 for part in self.path: |
1116 if isinstance(part, string_types): |
1114 if isinstance(part, str): |
1117 part = part.split() |
1115 part = part.split() |
1118 subject, rtype, object = part |
1116 subject, rtype, object = part |
1119 if skiplabel and object == self.label_variable: |
1117 if skiplabel and object == self.label_variable: |
1120 continue |
1118 continue |
1121 if object == self.filter_variable: |
1119 if object == self.filter_variable: |
1215 """return vocabulary for this facet, eg a list of 2-uple (label, value) |
1213 """return vocabulary for this facet, eg a list of 2-uple (label, value) |
1216 """ |
1214 """ |
1217 rset = self._range_rset() |
1215 rset = self._range_rset() |
1218 if rset: |
1216 if rset: |
1219 minv, maxv = rset[0] |
1217 minv, maxv = rset[0] |
1220 return [(text_type(minv), minv), (text_type(maxv), maxv)] |
1218 return [(str(minv), minv), (str(maxv), maxv)] |
1221 return [] |
1219 return [] |
1222 |
1220 |
1223 def possible_values(self): |
1221 def possible_values(self): |
1224 """Return a list of possible values (as string since it's used to |
1222 """Return a list of possible values (as string since it's used to |
1225 compare to a form value in javascript) for this facet. |
1223 compare to a form value in javascript) for this facet. |
1234 return None |
1232 return None |
1235 return self.wdgclass(self, min(values), max(values)) |
1233 return self.wdgclass(self, min(values), max(values)) |
1236 |
1234 |
1237 def formatvalue(self, value): |
1235 def formatvalue(self, value): |
1238 """format `value` before in order to insert it in the RQL query""" |
1236 """format `value` before in order to insert it in the RQL query""" |
1239 return text_type(value) |
1237 return str(value) |
1240 |
1238 |
1241 def infvalue(self, min=False): |
1239 def infvalue(self, min=False): |
1242 if min: |
1240 if min: |
1243 return self._cw.form.get('min_%s_inf' % self.__regid__) |
1241 return self._cw.form.get('min_%s_inf' % self.__regid__) |
1244 return self._cw.form.get('%s_inf' % self.__regid__) |
1242 return self._cw.form.get('%s_inf' % self.__regid__) |
1335 select.recover() |
1333 select.recover() |
1336 # don't call rset_vocabulary on empty result set, it may be an empty |
1334 # don't call rset_vocabulary on empty result set, it may be an empty |
1337 # *list* (see rqlexec implementation) |
1335 # *list* (see rqlexec implementation) |
1338 if rset: |
1336 if rset: |
1339 minv, maxv = rset[0] |
1337 minv, maxv = rset[0] |
1340 return [(text_type(minv), minv), (text_type(maxv), maxv)] |
1338 return [(str(minv), minv), (str(maxv), maxv)] |
1341 return [] |
1339 return [] |
1342 |
1340 |
1343 |
1341 |
1344 def possible_values(self): |
1342 def possible_values(self): |
1345 """return a list of possible values (as string since it's used to |
1343 """return a list of possible values (as string since it's used to |
1354 return |
1352 return |
1355 varmap, restrvar = self.add_path_to_select( |
1353 varmap, restrvar = self.add_path_to_select( |
1356 skiplabel=True, skipattrfilter=True) |
1354 skiplabel=True, skipattrfilter=True) |
1357 restrel = None |
1355 restrel = None |
1358 for part in self.path: |
1356 for part in self.path: |
1359 if isinstance(part, string_types): |
1357 if isinstance(part, str): |
1360 part = part.split() |
1358 part = part.split() |
1361 subject, rtype, object = part |
1359 subject, rtype, object = part |
1362 if object == self.filter_variable: |
1360 if object == self.filter_variable: |
1363 restrel = rtype |
1361 restrel = rtype |
1364 assert restrel |
1362 assert restrel |
1478 mask = reduce(lambda x, y: x | (y[0] or 0), rset, 0) |
1476 mask = reduce(lambda x, y: x | (y[0] or 0), rset, 0) |
1479 return sorted([(self._cw._(label), val) for label, val in self.choices |
1477 return sorted([(self._cw._(label), val) for label, val in self.choices |
1480 if not val or val & mask]) |
1478 if not val or val & mask]) |
1481 |
1479 |
1482 def possible_values(self): |
1480 def possible_values(self): |
1483 return [text_type(val) for label, val in self.vocabulary()] |
1481 return [str(val) for label, val in self.vocabulary()] |
1484 |
1482 |
1485 |
1483 |
1486 ## html widets ################################################################ |
1484 ## html widets ################################################################ |
1487 _DEFAULT_VOCAB_WIDGET_HEIGHT = 12 |
1485 _DEFAULT_VOCAB_WIDGET_HEIGHT = 12 |
1488 _DEFAULT_FACET_GROUP_HEIGHT = 15 |
1486 _DEFAULT_FACET_GROUP_HEIGHT = 15 |
1557 def _render_value(self, w, value, label, selected, overflow): |
1555 def _render_value(self, w, value, label, selected, overflow): |
1558 cssclass = 'facetValue facetCheckBox' |
1556 cssclass = 'facetValue facetCheckBox' |
1559 if selected: |
1557 if selected: |
1560 cssclass += ' facetValueSelected' |
1558 cssclass += ' facetValueSelected' |
1561 w(u'<div class="%s" cubicweb:value="%s">\n' |
1559 w(u'<div class="%s" cubicweb:value="%s">\n' |
1562 % (cssclass, xml_escape(text_type(value)))) |
1560 % (cssclass, xml_escape(str(value)))) |
1563 # If it is overflowed one must add padding to compensate for the vertical |
1561 # If it is overflowed one must add padding to compensate for the vertical |
1564 # scrollbar; given current css values, 4 blanks work perfectly ... |
1562 # scrollbar; given current css values, 4 blanks work perfectly ... |
1565 padding = u' ' * self.scrollbar_padding_factor if overflow else u'' |
1563 padding = u' ' * self.scrollbar_padding_factor if overflow else u'' |
1566 w('<span>%s</span>' % xml_escape(label)) |
1564 w('<span>%s</span>' % xml_escape(label)) |
1567 w(padding) |
1565 w(padding) |
1716 imgalt = self._cw._('selected') |
1714 imgalt = self._cw._('selected') |
1717 else: |
1715 else: |
1718 imgsrc = self._cw.data_url(self.unselected_img) |
1716 imgsrc = self._cw.data_url(self.unselected_img) |
1719 imgalt = self._cw._('not selected') |
1717 imgalt = self._cw._('not selected') |
1720 w(u'<div class="%s" cubicweb:value="%s">\n' |
1718 w(u'<div class="%s" cubicweb:value="%s">\n' |
1721 % (cssclass, xml_escape(text_type(self.value)))) |
1719 % (cssclass, xml_escape(str(self.value)))) |
1722 w(u'<div>') |
1720 w(u'<div>') |
1723 w(u'<img src="%s" alt="%s" cubicweb:unselimg="true" /> ' % (imgsrc, imgalt)) |
1721 w(u'<img src="%s" alt="%s" cubicweb:unselimg="true" /> ' % (imgsrc, imgalt)) |
1724 w(u'<label class="facetTitle" cubicweb:facetName="%s">%s</label>' |
1722 w(u'<label class="facetTitle" cubicweb:facetName="%s">%s</label>' |
1725 % (xml_escape(self.facet.__regid__), title)) |
1723 % (xml_escape(self.facet.__regid__), title)) |
1726 w(u'</div>\n') |
1724 w(u'</div>\n') |