Ignore:
Timestamp:
01/04/10 14:54:25 (10 years ago)
Author:
pjkersha
Message:

Refactored functions package to enable dynamic creation of function classes for all the XACML primitive types for any given function e.g. equal module implements EqualBase? and dynamically creates the <type>-equal classes for all the types: string, AnyURI, Boolean etc.

File:
1 edited

Legend:

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

    r6792 r6796  
    1515import traceback 
    1616 
     17from ndg.xacml.core.context.exceptions import XacmlContextError 
    1718from ndg.xacml.core.context.pdpinterface import PDPInterface 
    1819from ndg.xacml.core.policy import Policy 
    1920from ndg.xacml.core.apply import Apply 
    20 from ndg.xacml.core.attributevalue import AttributeValue 
    21 from ndg.xacml.core.variablereference import VariableReference 
    22 from ndg.xacml.core.attributedesignator import (AttributeDesignator, 
    23                                                 SubjectAttributeDesignator, 
    24                                                 ResourceAttributeDesignator, 
    25                                                 ActionAttributeDesignator, 
    26                                                 EnvironmentAttributeDesignator) 
    27 from ndg.xacml.core.attributeselector import AttributeSelector 
    2821from ndg.xacml.core.context.request import Request 
    2922from ndg.xacml.core.context.response import Response 
     
    3326                             
    3427 
    35 class PDPError(Exception): 
     28class PDPError(XacmlContextError): 
    3629    """Base class for PDP class exceptions""" 
    37     def __init__(self, *arg, **kw): 
    38         super(PDPError, self).__init__(*arg, **kw) 
    39         self.__response = Response() 
    40         self.__response.results.append(Result.createInitialised()) 
    41          
    42         self.__response.results[0].decision = Decision.INDETERMINATE 
    43         if len(arg) > 0: 
    44             self.__response.results[0].status.statusMessage = arg[0] 
    45          
    46     @property 
    47     def response(self): 
    48         """Context response object associated with this exception 
    49         """ 
    50         return self.__response 
    51      
    52     @response.setter 
    53     def response(self, value): 
    54         if not isinstance(value, Response): 
    55             raise TypeError('Expecting %r type for "response" attribute; got ' 
    56                             '%r instead' % (Response, type(Response))) 
    57         self.__response = value 
    58  
    59   
    60 class UnsupportedFunctionError(PDPError): 
    61     """Encountered a function type that is not supported in this implementation 
    62     """ 
    63     def __init__(self, *arg, **kw): 
    64         super(UnsupportedFunctionError, self).__init__(*arg, **kw) 
    65         self.response.results[0].status.statusCode.value = \ 
    66                                                     StatusCode.PROCESSING_ERROR 
    67  
    68  
    69 class UnsupportedStdFunctionError(UnsupportedFunctionError):  
    70     """Encountered a function type that is not supported even though it is part 
    71     of the XACML spec.""" 
    72   
     30      
    7331     
    7432class UnsupportedElementError(PDPError): 
     
    8442    implementation"""   
    8543     
    86  
    87 class MissingAttributeError(PDPError): 
    88     """AttributeDesignator or AttributeSelector has specified MustBePresent 
    89     but the request context contains no match for required attribute XPath 
    90     respectively 
    91     """ 
    92      
    9344     
    9445class PDP(PDPInterface): 
     
    9647    single policy but not policy sets 
    9748    """ 
    98     __slots__ = ('__policy', '__functionMap', '__request') 
     49    __slots__ = ('__policy', '__request') 
    9950    TARGET_CHILD_ATTRS = ('subjects', 'resources', 'actions', 'environments') 
    10051     
     
    11061             
    11162        self.__functionMap = FunctionMap.withLoadedMap() 
     63             
    11264        self.__request = None 
    11365 
     
    13890                            '%r instead' % (Policy, type(value))) 
    13991        self.__policy = value 
    140      
    141     @property 
    142     def functionMap(self): 
    143         """functionMap object for PDP to retrieve functions from given XACML 
    144         function URNs""" 
    145         return self.__functionMap 
    146      
    147     @functionMap.setter 
    148     def functionMap(self, value): 
    149         '''functionMap object for PDP to retrieve functions from given XACML 
    150         function URNs''' 
    151         if not isinstance(value, FunctionMap): 
    152             raise TypeError('Expecting %r derived type for "functionMap" ' 
    153                             'input; got %r instead' % (FunctionMap,  
    154                                                        type(value))) 
    155         self.__functionMap = value 
    156  
    157      
     92 
    15893    @property 
    15994    def request(self): 
     
    350285             
    351286            # Get the match function from the Match ID 
    352             matchFunc = self.functionMap.get(childMatch.matchId) 
     287            matchFunc = self.__functionMap.get(childMatch.matchId) 
    353288            if matchFunc is NotImplemented: 
    354289                raise UnsupportedStdFunctionError('No match function ' 
     
    403338                                  'target', 
    404339                                  attribute.attributeId, 
    405                                   attribute.attributeValue.value) 
     340                                  [a.value for a in attribute.attributeValues]) 
    406341                         
    407342            matchStatus = all(attrMatchStatusValues) 
     
    465400                                          'implementation' % applyElem) 
    466401          
    467         result = self.evaluateApplyStatement(applyElem) 
    468                  
    469     def evaluateApplyStatement(self, applyElem): 
    470         """Evaluate a given Condition <Apply> statement""" 
    471          
    472         # Get function for this <Apply> statement          
    473         func = self.functionMap.get(applyElem.functionId) 
    474         if func is NotImplemented: 
    475             raise UnsupportedStdFunctionError('No match function ' 
    476                                               'implemented for MatchId="%s"' 
    477                                               % applyElem.functionId) 
    478         elif func is None: 
    479             raise UnsupportedFunctionError('<Apply> function namespace %r is ' 
    480                                            'not recognised' %  
    481                                            applyElem.functionId) 
    482              
    483         inputMarshallerMap = { 
    484             Apply: self.evaluateApplyStatement, 
    485             AttributeValue: self.evaluateAttributeValueStatement, 
    486             SubjectAttributeDesignator: self.evaluateAttributeDesignator, 
    487             AttributeSelector: NotImplemented, 
    488             VariableReference: NotImplemented 
    489         }    
    490          
    491         # Marshall inputs 
    492         funcInputs = ['',]*len(applyElem.expressions) 
    493         for i, expression in enumerate(applyElem.expressions): 
    494             marshaller = inputMarshallerMap.get(expression.__class__) 
    495             if marshaller is NotImplemented: 
    496                 raise UnsupportedStdElementError('%r type <Apply> sub-element ' 
    497                                                  'processing is not supported ' 
    498                                                  'in this implementation' %  
    499                                                  expression) 
    500             elif marshaller is None: 
    501                 raise UnsupportedElementError('%r type <Apply> sub-element ' 
    502                                               'processing is not supported in ' 
    503                                               'this implementation' %  
    504                                               expression) 
    505              
    506             funcInputs[i] = marshaller(expression) 
    507              
    508         # Execute function on the retrieved inputs 
    509         result = func(*tuple(funcInputs)) 
    510          
    511         # Pass the result back to the parent <Apply> element 
    512         return result 
    513              
    514     evaluateAttributeValueStatement = lambda self, attributeValue: ( 
    515         attributeValue.value 
    516     ) 
    517      
    518     def evaluateAttributeDesignator(self, attributeDesignator): 
    519         '''Retrieve string attribute bag for a given attribute designator 
    520         TODO: possible refactor as AttributeDesignator or ContextHandler method 
    521         ''' 
    522         attributeValues = [] 
    523         dataType = attributeDesignator.dataType 
    524          
    525         if isinstance(attributeDesignator, SubjectAttributeDesignator): 
    526             for i in self.request.subjects: 
    527                 for j in i.attributes: 
    528                     attributeValues.extend([k.value for k in j.attributeValues 
    529                                             if k.dataType == dataType]) 
    530  
    531         elif isinstance(attributeDesignator, ResourceAttributeDesignator): 
    532             for i in self.request.resources: 
    533                 for j in i.attributes: 
    534                     attributeValues.extend([k.value for k in j.attributeValues 
    535                                             if k.dataType == dataType]) 
    536  
    537         elif isinstance(attributeDesignator, ActionAttributeDesignator): 
    538             for j in i.attributes: 
    539                 attributeValues.extend([k.value for k in j.attributeValues 
    540                                         if k.dataType == dataType]) 
    541              
    542         elif isinstance(attributeDesignator, EnvironmentAttributeDesignator): 
    543             for j in i.attributes: 
    544                 attributeValues.extend([k.value for k in j.attributeValues 
    545                                         if k.dataType == dataType]) 
    546         else: 
    547             raise TypeError('Expecting %r derived type got %r' % 
    548                             (AttributeDesignator, type(attributeDesignator))) 
    549                 
    550         if len(attributeValues) == 0 and attributeDesignator.mustBePresent: 
    551             raise MissingAttributeError('No match for AttributeDesignator ' 
    552                                         'attributeId=%r, dataType=%r and ' 
    553                                         'issuer=%r' %  
    554                                         (attributeDesignator.attributeId, 
    555                                          attributeDesignator.dataType, 
    556                                          attributeDesignator.issuer))  
    557                          
    558         return attributeValues 
    559  
     402        result = applyElem.evaluate(self.request) 
     403 
     404 
     405 
Note: See TracChangeset for help on using the changeset viewer.