Changeset 6806


Ignore:
Timestamp:
14/04/10 16:39:48 (9 years ago)
Author:
pjkersha
Message:

Moving matching and rule evaluation code out of the PDP class and into the relevant classes they pertain to e.g. target matching moved to Target class match method and so on.

Location:
TI12-security/trunk/NDG_XACML/ndg/xacml/core
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • TI12-security/trunk/NDG_XACML/ndg/xacml/core/condition.py

    r6796 r6806  
    3939                            type(value)) 
    4040        self.__expression = value 
     41     
     42    def evaluate(self, context): 
     43        """Evaluate this rule condition 
     44        @param context: the request context 
     45        @type context: ndg.xacml.core.request.Request 
     46        @return: True/False status for whether the rule condition matched or 
     47        not 
     48        @rtype: bool 
     49        """ 
     50        result = self.expression.evaluate(context) 
     51         
     52        return result 
  • TI12-security/trunk/NDG_XACML/ndg/xacml/core/context/pdp.py

    r6805 r6806  
    2323from ndg.xacml.core.context.result import Result, Decision 
    2424from ndg.xacml.core.context.result import StatusCode 
    25 from ndg.xacml.core.functions import FunctionMap 
    2625from ndg.xacml.core.exceptions import (UnsupportedStdFunctionError, 
    2726                                       UnsupportedFunctionError)      
     
    5049    """ 
    5150    __slots__ = ('__policy', '__request') 
    52     TARGET_CHILD_ATTRS = ('subjects', 'resources', 'actions', 'environments') 
    5351     
    5452    def __init__(self, policy=None): 
     
    6159        if policy is not None: 
    6260            self.policy = policy 
    63              
    64         self.__functionMap = FunctionMap.withLoadedMap() 
    6561             
    6662        self.__request = None 
     
    133129            log.debug('Checking policy target for match with request...') 
    134130             
     131            target = self.policy.target 
    135132             
    136             if not self.matchTarget(self.policy.target, request): 
     133            if target is None: 
     134                log.debug('No target set so no match with request context') 
     135                result.decision = Decision.NOT_APPLICABLE 
     136                return response 
     137             
     138            if not target.match(request): 
    137139                log.debug('No match for policy target setting %r decision', 
    138140                          Decision.NOT_APPLICABLE_STR) 
     
    146148            ruleStatusValues = [False]*len(self.policy.rules) 
    147149            for i, rule in enumerate(self.policy.rules): 
    148                 log.debug('Checking policy rule %r for match...', rule.id) 
    149                 if not self.matchTarget(rule.target, request): 
    150                     log.debug('No match to request context for target in rule ' 
    151                               '%r', rule.id) 
    152                     ruleStatusValues[i] = True 
    153                     continue    
    154                  
    155                 # Apply the condition 
    156                 ruleStatusValues[i] = self.evaluateCondition(rule.condition)  
     150                ruleStatusValues[i] = rule.evaluate() 
     151#                log.debug('Checking policy rule %r for match...', rule.id) 
     152#                if not self.matchTarget(rule.target, request): 
     153#                    log.debug('No match to request context for target in rule ' 
     154#                              '%r', rule.id) 
     155#                    ruleStatusValues[i] = True 
     156#                    continue    
     157#                 
     158#                # Apply the condition 
     159#                ruleStatusValues[i] = self.evaluateCondition(rule.condition)  
    157160                      
    158161        except PDPError, e: 
     
    176179             
    177180        return response 
    178              
    179     def matchTarget(self, target, request): 
    180         """Generic method to match a <Target> element to the request context 
    181          
    182         @param target: XACML target element 
    183         @type target: ndg.xacml.core.target.Target 
    184         @param request: XACML request context 
    185         @type request: ndg.xacml.core.context.request.Request 
    186         @return: True if request context matches the given target,  
    187         False otherwise 
    188         @rtype: bool 
    189         """ 
    190         if target is None: 
    191             log.debug('No target set so no match with request context') 
    192             return False 
    193          
    194         # From section 5.5 of the XACML 2.0 Core Spec: 
    195         # 
    196         # For the parent of the <Target> element to be applicable to the  
    197         # decision request, there MUST be at least one positive match between  
    198         # each section of the <Target> element and the corresponding section of  
    199         # the <xacml-context:Request> element. 
    200         #  
    201         # Also, 7.6: 
    202         # 
    203         # The target value SHALL be "Match" if the subjects, resources, actions  
    204         # and environments specified in the target all match values in the  
    205         # request context.  
    206         statusValues = [False]*len(self.__class__.TARGET_CHILD_ATTRS)  
    207          
    208         # Iterate for target subjects, resources, actions and environments  
    209         # elements 
    210         for i, attrName in enumerate(self.__class__.TARGET_CHILD_ATTRS): 
    211             # If any one of the <Target> children is missing then it counts as 
    212             # a match e.g. for <Subjects> child element - Section 5.5: 
    213             # 
    214             # <Subjects> [Optional] Matching specification for the subject  
    215             # attributes in the context. If this element is missing, 
    216             # then the target SHALL match all subjects. 
    217             targetElem = getattr(target, attrName) 
    218             if len(targetElem) == 0: 
    219                 statusValues[i] = True 
    220                 continue 
    221              
    222             # Iterate over each for example, subject in the list of subjects: 
    223             # <Target> 
    224             #     <Subjects> 
    225             #          <Subject> 
    226             #              ... 
    227             #          </Subject> 
    228             #          <Subject> 
    229             #              ... 
    230             #          </Subject> 
    231             #     ... 
    232             # or resource in the list of resources and so on 
    233             for targetSubElem in targetElem: 
    234                  
    235                 # For the given subject/resource/action/environment check for a 
    236                 # match with the equivalent in the request 
    237                 requestElem = getattr(request, attrName)  
    238                 for requestSubElem in requestElem: 
    239                     if self.matchTargetChild(targetSubElem, requestSubElem): 
    240                         # Within the list of e.g. subjects if one subject  
    241                         # matches then this counts as a subject match overall  
    242                         # for this target 
    243                         statusValues[i] = True 
    244   
    245         # Target matches if all the children (i.e. subjects, resources, actions 
    246         # and environment sections) have at least one match.  Otherwise it  
    247         # doesn't count as a match 
    248         return all(statusValues) 
    249      
    250     def matchTargetChild(self, targetChild, requestChild): 
    251         """Match a request child element (a <Subject>, <Resource>, <Action> or  
    252         <Environment>) with the corresponding target's <Subject>, <Resource>,  
    253         <Action> or <Environment>. 
    254          
    255         @param targetChild: Target Subject, Resource, Action or Environment 
    256         object 
    257         @type targetChild: ndg.xacml.core.TargetChildBase 
    258         @param requestChild: Request Subject, Resource, Action or Environment 
    259         object 
    260         @type requestChild: ndg.xacml.core.context.RequestChildBase 
    261         @return: True if request context matches something in the target 
    262         @rtype: bool 
    263         @raise UnsupportedElementError: AttributeSelector processing is not  
    264         currently supported.  If an AttributeSelector is found in the policy, 
    265         this exception will be raised. 
    266         @raise UnsupportedStdFunctionError: policy references a function type  
    267         which is in the XACML spec. but is not supported by this implementation 
    268         @raise UnsupportedFunctionError: policy references a function type which 
    269         is not supported by this implementation 
    270         """ 
    271         if targetChild is None: 
    272             # Default if target child is not set is to match all children 
    273             return True 
    274          
    275         matchStatusValues = [True]*len(targetChild.matches) 
    276          
    277         # Section 7.6 
    278         # 
    279         # A subject, resource, action or environment SHALL match a value in the 
    280         # request context if the value of all its <SubjectMatch>,  
    281         # <ResourceMatch>, <ActionMatch> or <EnvironmentMatch> elements,  
    282         # respectively, are "True". 
    283         # 
    284         # e.g. for <SubjectMatch>es in <Subject> ... 
    285         for childMatch, matchStatus in zip(targetChild.matches,  
    286                                            matchStatusValues): 
    287              
    288             # Get the match function from the Match ID 
    289             matchFunctionClass = self.__functionMap.get(childMatch.matchId) 
    290             if matchFunctionClass is NotImplemented: 
    291                 raise UnsupportedStdFunctionError('No match function class ' 
    292                                                   'implemented for MatchId="%s"' 
    293                                                   % childMatch.matchId) 
    294             elif matchFunctionClass is None: 
    295                 raise UnsupportedFunctionError('Match function namespace %r is ' 
    296                                                'not recognised' %  
    297                                                childMatch.matchId) 
    298                  
    299             matchAttributeValue = childMatch.attributeValue.value 
    300              
    301             # Create a match function based on the presence or absence of an 
    302             # AttributeDesignator or AttributeSelector 
    303             if childMatch.attributeDesignator is not None: 
    304                 _attributeMatch = self.attributeDesignatorMatchFuncFactory( 
    305                                                 matchFunctionClass(), 
    306                                                 childMatch.attributeValue, 
    307                                                 childMatch.attributeDesignator) 
    308                  
    309             elif childMatch.attributeSelector is not None: 
    310                 # Nb. This will require that the request provide a reference to 
    311                 # it's XML representation and an abstraction of the XML parser 
    312                 # for executing XPath searches into that representation 
    313                 raise UnsupportedElementError('This PDP implementation does ' 
    314                                               'not support <AttributeSelector> ' 
    315                                               'elements') 
    316             else: 
    317                 _attributeMatch = lambda requestChildAttribute: ( 
    318                     matchFunc.evaluate(matchAttributeValue,  
    319                                     requestChildAttribute.attributeValue.value) 
    320                 ) 
    321          
    322             # Iterate through each attribute in the request in turn matching it 
    323             # against the target using the generated _attributeMatch function 
    324             # 
    325             # Any Match element NOT matching will result in an overall status of 
    326             # no match. 
    327             # 
    328             # Continue iterating through the whole list even if a False status 
    329             # is found.  The other attributes need to be checked in case an  
    330             # error occurs.  In this case the top-level PDP exception handling  
    331             # block will catch it and set an overall decision of INDETERMINATE 
    332             attrMatchStatusValues = [False]*len(requestChild.attributes) 
    333              
    334             for attribute, attrMatchStatus in zip(requestChild.attributes,  
    335                                                   attrMatchStatusValues): 
    336                 attrMatchStatus = _attributeMatch(attribute) 
    337                 if attrMatchStatus == True: 
    338                     if log.getEffectiveLevel() <= logging.DEBUG: 
    339                         log.debug('Request attribute %r set to %r matches ' 
    340                                   'target', 
    341                                   attribute.attributeId, 
    342                                   [a.value for a in attribute.attributeValues]) 
    343                          
    344             matchStatus = all(attrMatchStatusValues) 
    345          
    346         # Any match => overall match       
    347         return any(matchStatusValues) 
    348                  
    349     def attributeDesignatorMatchFuncFactory(self, 
    350                                             matchFunc, 
    351                                             matchAttributeValue,  
    352                                             attributeDesignator): 
    353         """Define a match function to match a given request attribute against  
    354         the input attribute value and AttributeDesignator defined in a policy  
    355         target 
    356         """             
    357         attributeId = attributeDesignator.attributeId 
    358         dataType = attributeDesignator.dataType 
    359          
    360         # Issuer is an optional match - see core spec. 7.2.4 
    361         issuer = attributeDesignator.issuer 
    362         if issuer is not None: 
    363             # Issuer found - set lambda to match this against the  
    364             # issuer setting in the request 
    365             _issuerMatch = lambda requestChildIssuer: ( 
    366                                                 issuer == requestChildIssuer) 
    367         else: 
    368             # No issuer set - lambda returns True regardless 
    369             _issuerMatch = lambda requestChildIssuer: True 
    370          
    371          
    372         _attributeMatch = lambda attribute: ( 
    373             any([matchFunc.evaluate(matchAttributeValue, attrVal)  
    374                  for attrVal in attribute.attributeValues]) and 
    375             attribute.attributeId == attributeId and 
    376             attribute.dataType == dataType and 
    377             _issuerMatch(attribute.issuer) 
    378         ) 
    379          
    380         return _attributeMatch 
    381      
    382     def evaluateCondition(self, condition): 
    383         """Evaluate a rule condition 
    384         @param condition: rule condition 
    385         @type condition: ndg.xacml.core.condition.Condition 
    386         @return: True/False status for whether the rule condition matched or 
    387         not 
    388         @rtype: bool 
    389         """ 
    390          
    391         # Spec:  
    392         # 
    393         # "The condition value SHALL be "True" if the <Condition> element is  
    394         # absent"  
    395         if condition is None: 
    396             return True 
    397          
    398         applyElem = condition.expression 
    399         if not isinstance(applyElem, Apply): 
    400             raise UnsupportedElementError('%r type <Condition> sub-element ' 
    401                                           'processing is not supported in this ' 
    402                                           'implementation' % applyElem) 
    403           
    404         result = applyElem.evaluate(self.request) 
    405          
    406         return result 
    407181 
    408182 
  • TI12-security/trunk/NDG_XACML/ndg/xacml/core/match.py

    r6774 r6806  
    8686    matchId = property(_getMatchId, _setMatchId, None, "Match Id") 
    8787     
     88    def evaluate(self): 
     89        """Evaluate the match object against the relevant element in the request 
     90        context 
     91        """ 
     92        # Get the match function from the Match ID 
     93#        matchFunctionClass = self.__functionMap.get(self.matchId) 
     94#        if matchFunctionClass is NotImplemented: 
     95#            raise UnsupportedStdFunctionError('No match function class ' 
     96#                                              'implemented for MatchId="%s"' 
     97#                                              % self.matchId) 
     98#        elif matchFunctionClass is None: 
     99#            raise UnsupportedFunctionError('Match function namespace %r is ' 
     100#                                           'not recognised' %  
     101#                                           self.matchId) 
     102#             
     103#        matchAttributeValue = self.attributeValue.value 
     104         
     105        # Create a match function based on the presence or absence of an 
     106        # AttributeDesignator or AttributeSelector 
     107        if self.attributeDesignator is not None: 
     108#            _attributeMatch = self.attributeDesignatorMatchFuncFactory( 
     109#                                            matchFunctionClass(), 
     110#                                            self.attributeValue, 
     111#                                            self.attributeDesignator) 
     112             
     113        elif self.attributeSelector is not None: 
     114            # Nb. This will require that the request provide a reference to 
     115            # it's XML representation and an abstraction of the XML parser 
     116            # for executing XPath searches into that representation 
     117            raise UnsupportedElementError('This PDP implementation does ' 
     118                                          'not support <AttributeSelector> ' 
     119                                          'elements') 
     120        else: 
     121            _attributeMatch = lambda requestChildAttribute: ( 
     122                matchFunc.evaluate(matchAttributeValue,  
     123                                requestChildAttribute.attributeValue.value) 
     124            ) 
     125     
     126        # Iterate through each attribute in the request in turn matching it 
     127        # against the target using the generated _attributeMatch function 
     128        # 
     129        # Any Match element NOT matching will result in an overall status of 
     130        # no match. 
     131        # 
     132        # Continue iterating through the whole list even if a False status 
     133        # is found.  The other attributes need to be checked in case an  
     134        # error occurs.  In this case the top-level PDP exception handling  
     135        # block will catch it and set an overall decision of INDETERMINATE 
     136        attrMatchStatusValues = [False]*len(requestChild.attributes) 
     137         
     138        for attribute, attrMatchStatus in zip(requestChild.attributes,  
     139                                              attrMatchStatusValues): 
     140            attrMatchStatus = _attributeMatch(attribute) 
     141            if attrMatchStatus == True: 
     142                if log.getEffectiveLevel() <= logging.DEBUG: 
     143                    log.debug('Request attribute %r set to %r matches ' 
     144                              'target', 
     145                              attribute.attributeId, 
     146                              [a.value for a in attribute.attributeValues]) 
     147                     
     148        matchStatus = all(attrMatchStatusValues) 
     149         
     150        return matchStatus 
     151     
    88152     
    89153class SubjectMatch(MatchBase): 
  • TI12-security/trunk/NDG_XACML/ndg/xacml/core/rule.py

    r6790 r6806  
    166166            raise TypeError('Expecting %r type for "id" ' 
    167167                            'attribute; got %r' % (basestring, type(value))) 
    168              
     168          
    169169        self.__id = value    
    170170 
     
    195195    description = property(_getDescription, _setDescription,  
    196196                           doc="Rule Description text") 
     197     
     198    def evaluate(self, context): 
     199        """Evaluate a rule 
     200        @param context: the request context 
     201        @type context: ndg.xacml.core.request.Request 
     202        @return: result of the evaluation - the decision for this rule 
     203        @rtype:  
     204        """ 
     205        log.debug('Evaluating rule %r ...', rule.id) 
     206         
     207        if not self.matchTarget(self.target, request): 
     208            log.debug('No match to request context for target in rule ' 
     209                      '%r', self.id) 
     210            #ruleStatusValues[i] = True 
     211            continue    
     212         
     213        # Apply the condition 
     214        ruleStatusValues[i] = self.condition.evaluate() 
     215 
  • TI12-security/trunk/NDG_XACML/ndg/xacml/core/target.py

    r6770 r6806  
    1616__contact__ = "Philip.Kershaw@stfc.ac.uk" 
    1717__revision__ = "$Id: $" 
     18import logging 
     19log = logging.getLogger(__name__) 
     20 
    1821from ndg.xacml.core import XacmlCoreBase 
    1922from ndg.xacml.core.action import Action 
     
    2427 
    2528class Target(XacmlCoreBase): 
     29    """XACML Target element""" 
    2630    ELEMENT_LOCAL_NAME = "Target" 
    2731    SUBJECTS_ELEMENT_LOCAL_NAME = "Subjects" 
     
    2933    RESOURCES_ELEMENT_LOCAL_NAME = "Resources" 
    3034    ENVIRONMENTS_ELEMENT_LOCAL_NAME = "Environments" 
    31      
     35    CHILD_ATTRS = ('subjects', 'resources', 'actions', 'environments') 
     36    
    3237    __slots__ = ('__subjects', '__resources', '__actions', '__environments') 
    3338     
    3439    def __init__(self): 
     40        """Initial attributes""" 
    3541        self.__subjects = TypedList(Subject) 
    3642        self.__resources = TypedList(Resource) 
     
    5359    def environments(self): 
    5460        return self.__environments 
    55      
    56      
    57 class _Target(XacmlCoreBase): 
    58     """Define access behaviour for a resource match a given URI pattern""" 
    59     URI_PATTERN_LOCALNAME = "URIPattern" 
    60     ATTRIBUTES_LOCALNAME = "Attributes" 
    61     ATTRIBUTE_AUTHORITY_LOCALNAME = "AttributeAuthority" 
    62      
    63     __slots__ = ( 
    64         '__uriPattern', 
    65         '__attributes', 
    66         '__regEx'        
    67     ) 
    68        
    69     def __init__(self): 
    70         super(Target, self).__init__() 
    71         self.__uriPattern = None 
    72         self.__attributes = [] 
    73         self.__regEx = None 
    74          
    75     def getUriPattern(self): 
    76         return self.__uriPattern 
    77  
    78     def setUriPattern(self, value): 
    79         if not isinstance(value, basestring): 
    80             raise TypeError('Expecting string type for "uriPattern" ' 
    81                             'attribute; got %r' % type(value)) 
    82         self.__uriPattern = value 
    83  
    84     uriPattern = property(getUriPattern,  
    85                           setUriPattern,  
    86                           doc="URI Pattern to match this target") 
    87  
    88     def getAttributes(self): 
    89         return self.__attributes 
    90  
    91     def setAttributes(self, value): 
    92         if (not isinstance(value, TypedList) and  
    93             not issubclass(value.elementType, Attribute.__class__)): 
    94             raise TypeError('Expecting TypedList(Attribute) for "attributes" ' 
    95                             'attribute; got %r' % type(value)) 
    96         self.__attributes = value 
    97  
    98     attributes = property(getAttributes,  
    99                           setAttributes,   
    100                           doc="Attributes restricting access to this target") 
    101  
    102     def getRegEx(self): 
    103         return self.__regEx 
    104  
    105     def setRegEx(self, value): 
    106         self.__regEx = value 
    107  
    108     regEx = property(getRegEx, setRegEx, doc="RegEx's Docstring") 
    109          
    110     def parse(self, root): 
    111          
    112         self.xmlns = QName.getNs(root.tag) 
    113         version1_0attributeAuthorityURI = None 
    114          
    115         for elem in root: 
    116             localName = QName.getLocalPart(elem.tag) 
    117             if localName == Target.URI_PATTERN_LOCALNAME: 
    118                 self.uriPattern = elem.text.strip() 
    119                 self.regEx = re.compile(self.uriPattern) 
     61             
     62    def match(self, request): 
     63        """Generic method to match a <Target> element to the request context 
     64         
     65        @param target: XACML target element 
     66        @type target: ndg.xacml.core.target.Target 
     67        @param request: XACML request context 
     68        @type request: ndg.xacml.core.context.request.Request 
     69        @return: True if request context matches the given target,  
     70        False otherwise 
     71        @rtype: bool 
     72        """ 
     73         
     74        # From section 5.5 of the XACML 2.0 Core Spec: 
     75        # 
     76        # For the parent of the <Target> element to be applicable to the  
     77        # decision request, there MUST be at least one positive match between  
     78        # each section of the <Target> element and the corresponding section of  
     79        # the <xacml-context:Request> element. 
     80        #  
     81        # Also, 7.6: 
     82        # 
     83        # The target value SHALL be "Match" if the subjects, resources, actions  
     84        # and environments specified in the target all match values in the  
     85        # request context.  
     86        statusValues = [False]*len(self.__class__.CHILD_ATTRS)  
     87         
     88        # Iterate for target subjects, resources, actions and environments  
     89        # elements 
     90        for i, attrName in enumerate(self.__class__.CHILD_ATTRS): 
     91            # If any one of the <Target> children is missing then it counts as 
     92            # a match e.g. for <Subjects> child element - Section 5.5: 
     93            # 
     94            # <Subjects> [Optional] Matching specification for the subject  
     95            # attributes in the context. If this element is missing, 
     96            # then the target SHALL match all subjects. 
     97            targetElem = getattr(self, attrName) 
     98            if len(targetElem) == 0: 
     99                statusValues[i] = True 
     100                continue 
     101             
     102            # Iterate over each for example, subject in the list of subjects: 
     103            # <Target> 
     104            #     <Subjects> 
     105            #          <Subject> 
     106            #              ... 
     107            #          </Subject> 
     108            #          <Subject> 
     109            #              ... 
     110            #          </Subject> 
     111            #     ... 
     112            # or resource in the list of resources and so on 
     113            for targetSubElem in targetElem: 
    120114                 
    121             elif localName == Target.ATTRIBUTES_LOCALNAME: 
    122                 for attrElem in elem: 
    123                     if self.xmlns == Target.VERSION_1_1_XMLNS: 
    124                         self.attributes.append(Attribute.Parse(attrElem)) 
    125                     else: 
    126                         attribute = Attribute() 
    127                         attribute.name = attrElem.text.strip() 
    128                         self.attributes.append(attribute) 
    129                      
    130             elif localName == Target.ATTRIBUTE_AUTHORITY_LOCALNAME: 
    131                 # Expecting first element to contain the URI 
    132                 warnings.warn( 
    133                         Target.ATTRIBUTE_AUTHORITY_LOCALNAME_DEPRECATED_MSG, 
    134                         PendingDeprecationWarning) 
     115                # For the given subject/resource/action/environment check for a 
     116                # match with the equivalent in the request 
     117                requestElem = getattr(request, attrName)  
     118                for requestSubElem in requestElem: 
     119                    if self._matchChild(targetSubElem, requestSubElem): 
     120                        # Within the list of e.g. subjects if one subject  
     121                        # matches then this counts as a subject match overall  
     122                        # for this target 
     123                        statusValues[i] = True 
     124  
     125        # Target matches if all the children (i.e. subjects, resources, actions 
     126        # and environment sections) have at least one match.  Otherwise it  
     127        # doesn't count as a match 
     128        return all(statusValues) 
     129     
     130    def _matchChild(self, targetChild, requestChild): 
     131        """Match a request child element (a <Subject>, <Resource>, <Action> or  
     132        <Environment>) with the corresponding target's <Subject>, <Resource>,  
     133        <Action> or <Environment>. 
     134         
     135        @param targetChild: Target Subject, Resource, Action or Environment 
     136        object 
     137        @type targetChild: ndg.xacml.core.TargetChildBase 
     138        @param requestChild: Request Subject, Resource, Action or Environment 
     139        object 
     140        @type requestChild: ndg.xacml.core.context.RequestChildBase 
     141        @return: True if request context matches something in the target 
     142        @rtype: bool 
     143        @raise UnsupportedElementError: AttributeSelector processing is not  
     144        currently supported.  If an AttributeSelector is found in the policy, 
     145        this exception will be raised. 
     146        @raise UnsupportedStdFunctionError: policy references a function type  
     147        which is in the XACML spec. but is not supported by this implementation 
     148        @raise UnsupportedFunctionError: policy references a function type which 
     149        is not supported by this implementation 
     150        """ 
     151        if targetChild is None: 
     152            # Default if target child is not set is to match all children 
     153            return True 
     154         
     155        matchStatusValues = [True]*len(targetChild.matches) 
     156         
     157        # Section 7.6 
     158        # 
     159        # A subject, resource, action or environment SHALL match a value in the 
     160        # request context if the value of all its <SubjectMatch>,  
     161        # <ResourceMatch>, <ActionMatch> or <EnvironmentMatch> elements,  
     162        # respectively, are "True". 
     163        # 
     164        # e.g. for <SubjectMatch>es in <Subject> ... 
     165        for childMatch, matchStatus in zip(targetChild.matches,  
     166                                           matchStatusValues): 
     167             
     168            matchStatusValues[i] = childMatch.evaluate(requestChild) 
     169             
     170        # Any match => overall match       
     171        return any(matchStatusValues) 
     172     
    135173                 
    136                 version1_0attributeAuthorityURI = elem[-1].text.strip() 
    137             else: 
    138                 raise TargetParseError("Invalid Target attribute: %s" %  
    139                                        localName) 
    140                  
    141         if self.xmlns == Target.VERSION_1_0_XMLNS: 
    142             msg = ("Setting all attributes with Attribute Authority " 
    143                    "URI set read using Version 1.0 schema.  This will " 
    144                    "be deprecated in future releases") 
    145              
    146             warnings.warn(msg, PendingDeprecationWarning) 
    147             log.warning(msg) 
    148              
    149             if version1_0attributeAuthorityURI is None: 
    150                 raise TargetParseError("Assuming version 1.0 schema " 
    151                                        "for Attribute Authority URI setting " 
    152                                        "but no URI has been set") 
    153                  
    154             for attribute in self.attributes: 
    155                 attribute.attributeAuthorityURI = \ 
    156                     version1_0attributeAuthorityURI 
    157      
    158     @classmethod 
    159     def Parse(cls, root): 
    160         resource = cls() 
    161         resource.parse(root) 
    162         return resource 
    163      
    164     def __str__(self): 
    165         return str(self.uriPattern) 
    166  
     174    def attributeDesignatorMatchFuncFactory(self, 
     175                                            matchFunc, 
     176                                            matchAttributeValue,  
     177                                            attributeDesignator): 
     178        """Define a match function to match a given request attribute against  
     179        the input attribute value and AttributeDesignator defined in a policy  
     180        target 
     181        """             
     182        attributeId = attributeDesignator.attributeId 
     183        dataType = attributeDesignator.dataType 
     184         
     185        # Issuer is an optional match - see core spec. 7.2.4 
     186        issuer = attributeDesignator.issuer 
     187        if issuer is not None: 
     188            # Issuer found - set lambda to match this against the  
     189            # issuer setting in the request 
     190            _issuerMatch = lambda requestChildIssuer: ( 
     191                                                issuer == requestChildIssuer) 
     192        else: 
     193            # No issuer set - lambda returns True regardless 
     194            _issuerMatch = lambda requestChildIssuer: True 
     195         
     196         
     197        _attributeMatch = lambda attribute: ( 
     198            any([matchFunc.evaluate(matchAttributeValue, attrVal)  
     199                 for attrVal in attribute.attributeValues]) and 
     200            attribute.attributeId == attributeId and 
     201            attribute.dataType == dataType and 
     202            _issuerMatch(attribute.issuer) 
     203        ) 
     204         
     205        return _attributeMatch 
Note: See TracChangeset for help on using the changeset viewer.