cubicweb/predicates.py
changeset 12508 a8c1ea390400
parent 11956 3199a40db419
child 12542 85194bd49119
equal deleted inserted replaced
12507:211472ab15c8 12508:a8c1ea390400
    25 from operator import eq
    25 from operator import eq
    26 
    26 
    27 from six import string_types, integer_types
    27 from six import string_types, integer_types
    28 from six.moves import range
    28 from six.moves import range
    29 
    29 
    30 from logilab.common.deprecation import deprecated
    30 from logilab.common.registry import Predicate, objectify_predicate
    31 from logilab.common.registry import Predicate, objectify_predicate, yes
       
    32 
    31 
    33 from yams.schema import BASE_TYPES, role_name
    32 from yams.schema import BASE_TYPES, role_name
    34 from rql.nodes import Function
    33 from rql.nodes import Function
    35 
    34 
    36 from cubicweb import (Unauthorized, NoSelectableObject, NotAnEntity,
    35 from cubicweb import (Unauthorized, NoSelectableObject, NotAnEntity,
    37                       CW_EVENT_MANAGER, role)
    36                       CW_EVENT_MANAGER, role)
    38 from cubicweb.uilib import eid_param
    37 from cubicweb.uilib import eid_param
    39 from cubicweb.schema import split_expression
    38 from cubicweb.schema import split_expression
    40 
    39 
    41 yes = deprecated('[3.15] import yes() from use logilab.common.registry')(yes)
       
    42 
       
    43 
    40 
    44 # abstract predicates / mixin helpers ###########################################
    41 # abstract predicates / mixin helpers ###########################################
    45 
    42 
    46 class PartialPredicateMixIn(object):
    43 class PartialPredicateMixIn(object):
    47     """convenience mix-in for predicates that will look into the containing
    44     """convenience mix-in for predicates that will look into the containing
    83         returned
    80         returned
    84 
    81 
    85       - `accept_none` is False and some cell in the column has a None value
    82       - `accept_none` is False and some cell in the column has a None value
    86         (this may occurs with outer join)
    83         (this may occurs with outer join)
    87     """
    84     """
    88     def __init__(self, once_is_enough=None, accept_none=True, mode='all'):
    85     def __init__(self, accept_none=True, mode='all'):
    89         if once_is_enough is not None:
       
    90             warn("[3.14] once_is_enough is deprecated, use mode='any'",
       
    91                  DeprecationWarning, stacklevel=2)
       
    92             if once_is_enough:
       
    93                 mode = 'any'
       
    94         assert mode in ('any', 'all'), 'bad mode %s' % mode
    86         assert mode in ('any', 'all'), 'bad mode %s' % mode
    95         self.once_is_enough = mode == 'any'
    87         self.once_is_enough = mode == 'any'
    96         self.accept_none = accept_none
    88         self.accept_none = accept_none
    97 
    89 
    98     def __call__(self, cls, req, rset=None, row=None, col=0, entity=None,
    90     def __call__(self, cls, req, rset=None, row=None, col=0, entity=None,
   670     value at the end.
   662     value at the end.
   671 
   663 
   672     See :class:`~cubicweb.predicates.EntityPredicate` documentation for entity
   664     See :class:`~cubicweb.predicates.EntityPredicate` documentation for entity
   673     lookup / score rules according to the input context.
   665     lookup / score rules according to the input context.
   674     """
   666     """
   675     def __init__(self, scorefunc, once_is_enough=None, mode='all'):
   667     def __init__(self, scorefunc, mode='all'):
   676         super(score_entity, self).__init__(mode=mode, once_is_enough=once_is_enough)
   668         super(score_entity, self).__init__(mode=mode)
   677         def intscore(*args, **kwargs):
   669         def intscore(*args, **kwargs):
   678             score = scorefunc(*args, **kwargs)
   670             score = scorefunc(*args, **kwargs)
   679             if not score:
   671             if not score:
   680                 return 0
   672                 return 0
   681             if isinstance(score, integer_types):
   673             if isinstance(score, integer_types):
   688     """Return 1 if the entity adapt to IDownloadable and has the given MIME type.
   680     """Return 1 if the entity adapt to IDownloadable and has the given MIME type.
   689 
   681 
   690     You can give 'image/' to match any image for instance, or 'image/png' to match
   682     You can give 'image/' to match any image for instance, or 'image/png' to match
   691     only PNG images.
   683     only PNG images.
   692     """
   684     """
   693     def __init__(self, mimetype, once_is_enough=None, mode='all'):
   685     def __init__(self, mimetype, mode='all'):
   694         super(has_mimetype, self).__init__(mode=mode, once_is_enough=once_is_enough)
   686         super(has_mimetype, self).__init__(mode=mode)
   695         self.mimetype = mimetype
   687         self.mimetype = mimetype
   696 
   688 
   697     def score_entity(self, entity):
   689     def score_entity(self, entity):
   698         idownloadable = entity.cw_adapt_to('IDownloadable')
   690         idownloadable = entity.cw_adapt_to('IDownloadable')
   699         if idownloadable is None:
   691         if idownloadable is None:
   993         benefit from the ORM's request entities cache.
   985         benefit from the ORM's request entities cache.
   994 
   986 
   995     See :class:`~cubicweb.predicates.EntityPredicate` documentation for entity
   987     See :class:`~cubicweb.predicates.EntityPredicate` documentation for entity
   996     lookup / score rules according to the input context.
   988     lookup / score rules according to the input context.
   997     """
   989     """
   998     def __init__(self, expression, once_is_enough=None, mode='all', user_condition=False):
   990     def __init__(self, expression, mode='all', user_condition=False):
   999         super(rql_condition, self).__init__(mode=mode, once_is_enough=once_is_enough)
   991         super(rql_condition, self).__init__(mode=mode)
  1000         self.user_condition = user_condition
   992         self.user_condition = user_condition
  1001         if user_condition:
   993         if user_condition:
  1002             rql = 'Any COUNT(U) WHERE U eid %%(u)s, %s' % expression
   994             rql = 'Any COUNT(U) WHERE U eid %%(u)s, %s' % expression
  1003         elif 'U' in frozenset(split_expression(expression)):
   995         elif 'U' in frozenset(split_expression(expression)):
  1004             rql = 'Any COUNT(X) WHERE X eid %%(x)s, U eid %%(u)s, %s' % expression
   996             rql = 'Any COUNT(X) WHERE X eid %%(x)s, U eid %%(u)s, %s' % expression
  1389     which will not score at edit time::
  1381     which will not score at edit time::
  1390 
  1382 
  1391      is_instance('Version') & (match_transition('ready') |
  1383      is_instance('Version') & (match_transition('ready') |
  1392                                attribute_edited('publication_date'))
  1384                                attribute_edited('publication_date'))
  1393     """
  1385     """
  1394     def __init__(self, attribute, once_is_enough=None, mode='all'):
  1386     def __init__(self, attribute, mode='all'):
  1395         super(attribute_edited, self).__init__(mode=mode, once_is_enough=once_is_enough)
  1387         super(attribute_edited, self).__init__(mode=mode)
  1396         self._attribute = attribute
  1388         self._attribute = attribute
  1397 
  1389 
  1398     def score_entity(self, entity):
  1390     def score_entity(self, entity):
  1399         return eid_param(role_name(self._attribute, 'subject'), entity.eid) in entity._cw.form
  1391         return eid_param(role_name(self._attribute, 'subject'), entity.eid) in entity._cw.form
  1400 
  1392