source: TI12-security/trunk/NDGSecurity/python/ndg_security_common/ndg/security/common/utils/classfactory.py @ 6440

Subversion URL: http://proj.badc.rl.ac.uk/svn/ndg/TI12-security/trunk/NDGSecurity/python/ndg_security_common/ndg/security/common/utils/classfactory.py@6440
Revision 6440, 4.9 KB checked in by pjkersha, 10 years ago (diff)
  • #1088 Important fix to AuthnRedirectResponseMiddleware? to set redirect ONLY when SSL client authentication has just succeeded in the upstream middleware AuthKitSSLAuthnMiddleware. This bug was causing the browser to redirect to the wrong place following OpenID sign in in the case where the user is already logged into their provider and selects a new relying party to sign into.
    • Improvements to Provider decide page interface: leave out messages about attributes that the provider can't retrieve for the RP. Also included NDG style help icon.
Line 
1"""
2Generic parsers to use when reading in configuration data
3- methods available to deal with both XML and INI (flat text key/val) formats
4"""
5__author__ = "C Byrom - Tessella"
6__date__ = "28/08/08"
7__copyright__ = "(C) 2009 Science and Technology Facilities Council"
8__license__ = "BSD - see LICENSE file in top-level directory"
9__contact__ = "Philip.Kershaw@stfc.ac.uk"
10__revision__ = '$Id: $'
11import traceback
12import logging, os, sys
13log = logging.getLogger(__name__)
14
15
16class ClassFactoryError(Exception):
17    """Exception handling for NDG classfactory module."""
18    def __init__(self, msg):
19        log.error(msg)
20        Exception.__init__(self, msg)
21
22
23def importClass(moduleName, className=None, objectType=None):
24    '''Import a class from a string module name and class name.
25   
26    @param moduleName: Name of module containing the class
27    @type moduleName: str
28    @param className: Name of the class to import.  If none is given, the
29    class name will be assumed to be the last component of modulePath
30    @type className: str
31    @rtype: class object
32    @return: imported class'''
33   
34    if className is None:
35        _moduleName, className = moduleName.rsplit('.', 1)
36    else:
37        _moduleName = moduleName
38   
39    log.debug("Importing class %s ..." % className) 
40     
41    module = __import__(_moduleName, globals(), locals(), [])
42    components = _moduleName.split('.')
43    try:
44        for component in components[1:]:
45            module = getattr(module, component)
46    except AttributeError, e:
47        raise AttributeError("Error importing class %s: %s" %
48                             (className, traceback.format_exc()))
49
50    importedClass = getattr(module, className)
51
52    # Check class inherits from a base class
53    if objectType and not issubclass(importedClass, objectType):
54        raise TypeError("Specified class %s must be derived from %s; got %s" %
55                        (className, objectType, importedClass))
56   
57    log.info('Imported "%s" class from module, "%s"', className, _moduleName)
58    return importedClass
59   
60
61def instantiateClass(moduleName, className=None, moduleFilePath=None, 
62                     objectType=None, classArgs=(), classProperties={}):
63    '''
64    Create and return an instance of the specified class
65    @param moduleName: Name of module containing the class
66    @type moduleName: str
67    @param className: Name of the class to instantiate.  May be None in
68    which case, the class name is parsed from the moduleName last element
69    @type className: str
70    @param moduleFilePath: Path to the module - if unset, assume module on
71    system path already
72    @type moduleFilePath: str
73    @param classProperties: dict of properties to use when instantiating the
74    class
75    @type classProperties: dict
76    @param objectType: expected type for the object to instantiate - to
77    enforce use of specific interfaces
78    @type objectType: object
79    @return: object - instance of the class specified
80    '''
81
82   
83    # ensure that classproperties is a dict - NB, it may be passed in as a null
84    # value which can override the default val
85    if not classProperties:
86        classProperties = {}
87
88    # variable to store original state of the system path
89    sysPathBak = None
90    try:
91        try:
92            # Module file path may be None if the new module to be loaded
93            # can be found in the existing system path           
94            if moduleFilePath:
95                if not os.path.exists(moduleFilePath):
96                    raise IOError("Module file path '%s' doesn't exist" % 
97                                  moduleFilePath)
98                         
99                # Temporarily extend system path ready for import
100                sysPathBak = sys.path
101                         
102                sys.path.append(moduleFilePath)
103
104           
105            # Import module name specified in properties file
106            importedClass = importClass(moduleName, 
107                                        className=className,
108                                        objectType=objectType)
109        finally:
110            # revert back to original sys path, if necessary
111            # NB, python requires the use of a try/finally OR a try/except
112            # block - not both combined
113            if sysPathBak:
114                sys.path = sysPathBak
115                           
116    except Exception, e:
117        log.error('%s module import raised %s type exception: %s' % 
118                  (moduleName, e.__class__, e))
119        raise 
120
121    # Instantiate class
122    log.debug('Instantiating class "%s"' % importedClass.__name__)
123    try:
124        if classArgs:
125            object = importedClass(*classArgs, **classProperties)
126        else:
127            object = importedClass(**classProperties)
128           
129        return object
130
131    except Exception, e:
132        log.error("Instantiating class, %s: %s" % (importedClass.__name__, 
133                                                   traceback.format_exc()))
134        raise
135           
136                 
Note: See TracBrowser for help on using the repository browser.