vregistry.py
branchtls-sprint
changeset 780 5b6c93816871
parent 760 95b3419e94c5
child 804 cc339d3ff7ae
equal deleted inserted replaced
779:8510e14335e1 780:5b6c93816871
   138             if len(selectors) == 1:
   138             if len(selectors) == 1:
   139                 # micro optimization: don't bother with AndSelector if there's
   139                 # micro optimization: don't bother with AndSelector if there's
   140                 # only one selector
   140                 # only one selector
   141                 select = _instantiate_selector(selectors[0])
   141                 select = _instantiate_selector(selectors[0])
   142             else:
   142             else:
   143                 select = AndSelector(*[_instantiate_selector(selector)
   143                 select = AndSelector(*selectors)
   144                                        for selector in selectors])
       
   145             cls.__select__ = select
   144             cls.__select__ = select
   146 
   145 
   147 
   146 
   148 class VRegistry(object):
   147 class VRegistry(object):
   149     """class responsible to register, propose and select the various
   148     """class responsible to register, propose and select the various
   577         if self is selector:
   576         if self is selector:
   578             return self
   577             return self
   579         if isinstance(selector, type) and isinstance(self, selector):
   578         if isinstance(selector, type) and isinstance(self, selector):
   580             return self
   579             return self
   581         return None
   580         return None
       
   581 
       
   582     def __str__(self):
       
   583         return self.__class__.__name__
   582     
   584     
   583     def __and__(self, other):
   585     def __and__(self, other):
   584         return AndSelector(self, other)
   586         return AndSelector(self, other)
   585     def __rand__(self, other):
   587     def __rand__(self, other):
   586         return AndSelector(other, self)
   588         return AndSelector(other, self)
   600     """base class for compound selector classes"""
   602     """base class for compound selector classes"""
   601     
   603     
   602     def __init__(self, *selectors):
   604     def __init__(self, *selectors):
   603         self.selectors = self.merge_selectors(selectors)
   605         self.selectors = self.merge_selectors(selectors)
   604 
   606 
       
   607     def __str__(self):
       
   608         return '%s(%s)' % (self.__class__.__name__,
       
   609                            ','.join(str(s) for s in self.selectors))
       
   610 
   605     @classmethod
   611     @classmethod
   606     def merge_selectors(cls, selectors):
   612     def merge_selectors(cls, selectors):
   607         """merge selectors when possible :
   613         """deal with selector instanciation when necessary and merge
       
   614         multi-selectors if possible:
   608 
   615 
   609         AndSelector(AndSelector(sel1, sel2), AndSelector(sel3, sel4))
   616         AndSelector(AndSelector(sel1, sel2), AndSelector(sel3, sel4))
   610         ==> AndSelector(sel1, sel2, sel3, sel4)
   617         ==> AndSelector(sel1, sel2, sel3, sel4)
   611         """
   618         """
   612         merged_selectors = []
   619         merged_selectors = []
   613         for selector in selectors:
   620         for selector in selectors:
       
   621             selector = _instantiate_selector(selector)
       
   622             assert isinstance(selector, Selector), selector
   614             if isinstance(selector, cls):
   623             if isinstance(selector, cls):
   615                 merged_selectors += selector.selectors
   624                 merged_selectors += selector.selectors
   616             else:
   625             else:
   617                 merged_selectors.append(selector)
   626                 merged_selectors.append(selector)
   618         return merged_selectors
   627         return merged_selectors
   620     def search_selector(self, selector):
   629     def search_selector(self, selector):
   621         """search for the given selector or selector instance in the selectors
   630         """search for the given selector or selector instance in the selectors
   622         tree. Return it of None if not found
   631         tree. Return it of None if not found
   623         """
   632         """
   624         for childselector in self.selectors:
   633         for childselector in self.selectors:
   625             try:
   634             if childselector is selector:
   626                 if childselector.use_selector(selector):
   635                 return childselector
   627                     return childselector
   636             found = childselector.search_selector(selector)
   628             except AttributeError: # simple function
   637             if found is not None:
   629                 if childselector is selector:
   638                 return found
   630                     return childselector
       
   631         return None
   639         return None
   632 
   640 
   633     
   641     
   634 def objectify_selector(selector_func):
   642 def objectify_selector(selector_func):
   635     """convenience decorator for simple selectors where a class definition
   643     """convenience decorator for simple selectors where a class definition
   684     the selectors fail, selection will fail, else the returned score
   692     the selectors fail, selection will fail, else the returned score
   685     will be the sum of each selector'score
   693     will be the sum of each selector'score
   686     """
   694     """
   687     assert selectors
   695     assert selectors
   688     # XXX do we need to create the AndSelector here, a tuple might be enough
   696     # XXX do we need to create the AndSelector here, a tuple might be enough
   689     selector = AndSelector(*[_instantiate_selector(selector)
   697     selector = AndSelector(*selectors)
   690                              for selector in selectors])
       
   691     if 'name' in kwargs:
   698     if 'name' in kwargs:
   692         selector.__name__ = kwargs['name']
   699         selector.__name__ = kwargs['name']
   693     return selector
   700     return selector
   694 
   701 
   695 def chainfirst(*selectors, **kwargs):
   702 def chainfirst(*selectors, **kwargs):
   696     """return a selector chaining given selectors. If all
   703     """return a selector chaining given selectors. If all
   697     the selectors fail, selection will fail, else the returned score
   704     the selectors fail, selection will fail, else the returned score
   698     will be the first non-zero selector score
   705     will be the first non-zero selector score
   699     """
   706     """
   700     assert selectors
   707     assert selectors
   701     selector = OrSelector(*[_instantiate_selector(selector)
   708     selector = OrSelector(*selectors)
   702                             for selector in selectors])
       
   703     if 'name' in kwargs:
   709     if 'name' in kwargs:
   704         selector.__name__ = kwargs['name']
   710         selector.__name__ = kwargs['name']
   705     return selector
   711     return selector