Changeset 6918 for TI12-security/trunk


Ignore:
Timestamp:
02/06/10 15:01:16 (9 years ago)
Author:
pjkersha
Message:

Incomplete - task 5: MyProxy? Logon HTTPS Interface

  • Updated MyProxyClient? with bootstrap capability for get trust roots and logon methods.
Location:
TI12-security/trunk/MyProxyClient
Files:
2 added
4 deleted
8 edited
1 moved

Legend:

Unmodified
Added
Removed
  • TI12-security/trunk/MyProxyClient/MyProxyClient.egg-info/SOURCES.txt

    r6845 r6918  
    1212MyProxyClient.egg-info/requires.txt 
    1313MyProxyClient.egg-info/top_level.txt 
     14dist/MyProxyClient-1.0.0-py2.5.egg 
     15dist/MyProxyClient-1.0.0-py2.6.egg 
    1416documentation/Makefile 
    15 documentation/api-objects.txt 
    16 documentation/class-tree.html 
    17 documentation/crarr.png 
    18 documentation/epydoc-log.html 
    19 documentation/epydoc.css 
    20 documentation/epydoc.js 
    21 documentation/epydoc.log 
    22 documentation/help.html 
    23 documentation/identifier-index.html 
    24 documentation/index.html 
    25 documentation/module-tree.html 
    26 documentation/myproxy-module.html 
    27 documentation/myproxy-pysrc.html 
    28 documentation/myproxy.client-module.html 
    29 documentation/myproxy.client-pysrc.html 
    30 documentation/myproxy.client.CaseSensitiveConfigParser-class.html 
    31 documentation/myproxy.client.MyProxyClient-class.html 
    32 documentation/myproxy.client.MyProxyClientConfigError-class.html 
    33 documentation/myproxy.client.MyProxyClientError-class.html 
    34 documentation/myproxy.client.MyProxyClientGetError-class.html 
    35 documentation/myproxy.client.MyProxyClientRetrieveError-class.html 
    36 documentation/myproxy.client._HostCheck-class.html 
    37 documentation/myproxy.utils-module.html 
    38 documentation/myproxy.utils-pysrc.html 
    39 documentation/myproxy.utils.openssl-module.html 
    40 documentation/myproxy.utils.openssl-pysrc.html 
    41 documentation/myproxy.utils.openssl.OpenSSLConfig-class.html 
    42 documentation/myproxy.utils.openssl.OpenSSLConfigError-class.html 
    43 documentation/redirect.html 
    44 documentation/uml_class_diagram_for_myproxy_.gif 
    45 documentation/uml_class_diagram_for_myproxy__2.gif 
    46 documentation/uml_class_diagram_for_myproxy__3.gif 
    47 documentation/uml_class_diagram_for_myproxy__4.gif 
    48 documentation/uml_class_diagram_for_myproxy__5.gif 
    49 documentation/uml_class_diagram_for_myproxy__6.gif 
    50 documentation/uml_class_diagram_for_myproxy__7.gif 
    51 documentation/uml_class_diagram_for_myproxy__8.gif 
    52 documentation/uml_class_diagram_for_myproxy__9.gif 
    5317myproxy/__init__.py 
    5418myproxy/client.py 
    5519myproxy/test/README 
    5620myproxy/test/__init__.py 
     21myproxy/test/localhost.crt 
    5722myproxy/test/myProxyClient.cfg 
    5823myproxy/test/myProxyClientTest.cfg 
  • TI12-security/trunk/MyProxyClient/documentation

    • Property svn:ignore set to
      *.*
  • TI12-security/trunk/MyProxyClient/documentation/Makefile

    r5357 r6918  
    99# @copyright: (C) 2008 STFC 
    1010# 
    11 # @license: This software may be distributed under the terms of the Q Public 
    12 # License, version 1.0 or later. 
     11# @license: http://www.apache.org/licenses/LICENSE-2.0 
    1312# 
    1413# $Id$ 
  • TI12-security/trunk/MyProxyClient/myproxy/__init__.py

    r6069 r6918  
    99__license__ = """BSD - See LICENSE file in top-level directory""" 
    1010__contact__ = "Philip.Kershaw@stfc.ac.uk" 
    11 __revision__ = '$Id: $' 
     11__revision__ = '$Id$' 
     12__import__('pkg_resources').declare_namespace(__name__) 
  • TI12-security/trunk/MyProxyClient/myproxy/client.py

    r6847 r6918  
    243243    environment variable name 
    244244     
     245    @type GLOBUS_LOCATION_ENVVARNAME: string 
     246    @param GLOBUS_LOCATION_ENVVARNAME: 'GLOBUS_LOCATION' environment variable 
     247    name 
     248     
    245249    @type GET_CMD: string 
    246250    @cvar GET_CMD: get command string 
     
    261265    @cvar GET_TRUST_ROOTS_CMD: get trust roots command string 
    262266     
    263     @type _hostCertSubDirPath: string 
    264     @cvar _hostCertSubDirPath: sub-directory path host certificate (as tuple) 
    265      
    266     @type _hostKeySubDirPath: string 
    267     @cvar _hostKeySubDirPath: sub-directory path to host key (as tuple) 
     267    @type TRUSTED_CERTS_FIELDNAME: string 
     268    @param TRUSTED_CERTS_FIELDNAME: field name in get trust roots response for 
     269    trusted certificate file names 
     270     
     271    @type TRUSTED_CERTS_FILEDATA_FIELDNAME_PREFIX: string 
     272    @param TRUSTED_CERTS_FILEDATA_FIELDNAME_PREFIX: field name prefix in get  
     273    trust roots response for trusted certificate file contents 
     274     
     275    @type HOSTCERT_SUBDIRPATH: string 
     276    @cvar HOSTCERT_SUBDIRPATH: sub-directory path host certificate (as tuple) 
     277     
     278    @type HOSTKEY_SUBDIRPATH: string 
     279    @cvar HOSTKEY_SUBDIRPATH: sub-directory path to host key (as tuple) 
    268280     
    269281    @type PRIKEY_NBITS: int 
     
    290302    @cvar PROPERTY_DEFAULTS: sets permissable element names for MyProxy config  
    291303    file 
     304 
     305    @type ROOT_USERNAME: string 
     306    @cvar ROOT_USERNAME: root username - used to determine output directory 
     307    for trust roots 
     308 
     309    @type ROOT_TRUSTROOT_DIR: string 
     310    @param ROOT_TRUSTROOT_DIR: default trust root directory if running as root 
     311    user  
     312 
     313    @type USER_TRUSTROOT_DIR: string 
     314    @param USER_TRUSTROOT_DIR: default trust root directory for users other 
     315    than root 
     316     
     317    @type X509_CERT_DIR_ENVVARNAME: string 
     318    @param X509_CERT_DIR_ENVVARNAME: environment variable name 'X509_CERT_DIR', 
     319    which if set points to the location of the trust roots  
    292320    """ 
    293321    MYPROXY_SERVER_ENVVARNAME = 'MYPROXY_SERVER' 
    294322    MYPROXY_SERVER_PORT_ENVVARNAME = 'MYPROXY_SERVER_PORT' 
    295323    MYPROXY_SERVER_DN_ENVVARNAME = 'MYPROXY_SERVER_DN' 
    296        
     324     
     325    GLOBUS_LOCATION_ENVVARNAME = 'GLOBUS_LOCATION' 
     326     
    297327    GET_CMD="""VERSION=MYPROXYv2 
    298328COMMAND=0 
     
    339369TRUSTED_CERTS=1""" 
    340370 
    341     _hostCertSubDirPath = ('etc', 'hostcert.pem') 
    342     _hostKeySubDirPath = ('etc', 'hostkey.pem') 
     371    TRUSTED_CERTS_FIELDNAME = 'TRUSTED_CERTS' 
     372    TRUSTED_CERTS_FILEDATA_FIELDNAME_PREFIX = 'FILEDATA_' 
     373     
     374    HOSTCERT_SUBDIRPATH = ('etc', 'hostcert.pem') 
     375    HOSTKEY_SUBDIRPATH = ('etc', 'hostkey.pem') 
    343376     
    344377    PROXY_FILE_PERMISSIONS = 0600 
     
    360393       'hostname':              'localhost', 
    361394       'port':                  7512, 
     395       'cnPrefix':          MyProxyServerSSLCertVerification.SERVER_CN_PREFIX, 
    362396       'serverDN':              None, 
    363397       'openSSLConfFilePath':   '', 
    364398       'proxyCertMaxLifetime':  43200, 
    365399       'proxyCertLifetime':     43200, 
    366        'caCertFilePath':        None, 
    367400       'caCertDir':             None 
    368401    } 
     402 
     403    ROOT_USERNAME = 'root' 
     404    ROOT_TRUSTROOT_DIR = '/etc/grid-security/certificates' 
     405    USER_TRUSTROOT_DIR = '~/.globus/certificates'     
     406    X509_CERT_DIR_ENVVARNAME = 'X509_CERT_DIR' 
    369407     
    370408    # Restrict attributes to the above properties, their equivalent  
     
    395433        self.__proxyCertLifetime = MyProxyClient.PROPERTY_DEFAULTS[ 
    396434                                                        'proxyCertLifetime'] 
    397         self.__caCertFilePath = None 
    398435        self.__caCertDir = None 
    399436         
     
    419456            self.serverDN = serverDN 
    420457         
     458        # Set trust root - the directory containing the CA certificates for  
     459        # verifying the MyProxy server's SSL certificate 
     460        self.setDefaultCACertDir() 
     461         
    421462        # Any keyword settings override the defaults above 
    422463        for opt, val in prop.items(): 
     
    427468        if cfgFilePath is not None: 
    428469            self.parseConfig(cfg=cfgFilePath) 
    429  
    430     def _getServerSSLCertVerify(self): 
    431         return self.__serverSSLCertVerify 
    432  
    433     serverSSLCertVerify = property(_getServerSSLCertVerify,  
    434                                    doc="Server SSL Certificate Verification " 
    435                                        "callable") 
    436  
     470             
     471    def setDefaultCACertDir(self): 
     472        '''Make default trust root setting - the directory containing the CA  
     473        certificates for verifying the MyProxy server's SSL certificate. 
     474         
     475        The setting is made by using standard Globus defined locations and 
     476        environment variable settings 
     477        ''' 
     478         
     479        # Check for X509_CERT_DIR environment variable 
     480        x509CertDir = os.environ.get(MyProxyClient.X509_CERT_DIR_ENVVARNAME) 
     481        if x509CertDir is not None: 
     482            self.caCertDir = x509CertDir 
     483             
     484        # Check for running as root user 
     485        elif os.environ.get(MyProxyClient.ROOT_USERNAME) is not None: 
     486            self.caCertDir = MyProxyClient.ROOT_TRUSTROOT_DIR 
     487             
     488        # Default to non-root standard location 
     489        else: 
     490            self.caCertDir = os.path.expanduser( 
     491                                            MyProxyClient.USER_TRUSTROOT_DIR) 
    437492 
    438493    def _getServerSSLCertVerify(self): 
     
    582637                                 doc="Default proxy cert. lifetime used in " 
    583638                                     "logon request") 
    584      
    585     def _getCACertFilePath(self): 
    586         return self.__caCertFilePath 
    587      
    588     def _setCACertFilePath(self, val): 
    589         '''@type val: basestring 
    590         @param val: file path for CA certificate to be used to verify  
    591         MyProxy server certificate''' 
    592          
    593         if isinstance(val, basestring): 
    594             if val == '': 
    595                 self.__caCertFilePath = None 
    596             else: 
    597                 self.__caCertFilePath = os.path.expandvars(val) 
    598                  
    599         elif isinstance(val, None): 
    600             raise TypeError("Expecting string type for caCertFilePath " 
    601                                  "attribute")        
    602          
    603     caCertFilePath = property(fget=_getCACertFilePath, 
    604                               fset=_setCACertFilePath, 
    605                               doc="CA certificate file path - MyProxy server " 
    606                                   "certificate must validate against it and/" 
    607                                   "or any present in caCertDir") 
    608639 
    609640    def _getCACertDir(self): 
     
    634665    caCertDir = property(fget=_getCACertDir, 
    635666                         fset=_setCACertDir, 
    636                          doc="directory containing PEM encoded CA " 
    637                              "certificates.  Use along with caCertFilePath " 
    638                              "setting to validate MyProxy server certificate") 
     667                         doc="trust roots directory containing PEM encoded CA " 
     668                             "certificates to validate MyProxy server " 
     669                             "certificate") 
    639670 
    640671 
     
    648679                        certFile=None,  
    649680                        keyFile=None, 
    650                         keyFilePassphrase=None): 
     681                        keyFilePassphrase=None, 
     682                        verifyPeerWithTrustRoots=True): 
    651683        """Initialise connection setting up SSL context and client and 
    652684        server side identity checks 
     
    661693        @type keyFilePassphrase: basestring 
    662694        @param keyFilePassphrase: pass-phrase protecting private key if set 
     695        @type verifyPeerWithTrustRoots: bool 
     696        @param verifyPeerWithTrustRoots: verify MyProxy server's SSL certificate 
     697        against a list of trusted CA certificates in the CA certificate  
     698        directory set by the "CaCertDir" attribute.  This should always be set  
     699        to True for MyProxy client calls unless using the 'bootstrap' trust 
     700        roots mode available with logon and get trust roots calls 
    663701        """ 
    664702        # Must be version 3 for MyProxy 
    665703        context = SSL.Context(SSL.SSLv3_METHOD) 
    666704         
    667         if self.caCertFilePath or self.caCertDir: 
    668             context.load_verify_locations(self.caCertFilePath, self.caCertDir) 
    669              
     705        if verifyPeerWithTrustRoots: 
     706            context.load_verify_locations(None, self.caCertDir) 
     707            verifyMode = SSL.VERIFY_PEER|SSL.VERIFY_FAIL_IF_NO_PEER_CERT 
     708        else: 
     709            log.warning("SSL Context verify mode set to SSL.VERIFY_NONE") 
     710            verifyMode = SSL.VERIFY_NONE 
     711             
     712        # Verify peer's (MyProxy server) certificate 
     713        context.set_verify(verifyMode, self.__serverSSLCertVerify) 
     714              
    670715        if certFile: 
    671716            try: 
     
    674719                                promptPassphraseTwice, 
    675720                                passphrase): 
     721                    """Private key file password callback function""" 
    676722                    if len(passphrase) > passphraseMaxLen: 
    677723                        log.error('Passphrase length %d is greater than the ' 
     
    691737                                               "connection [also check CA " 
    692738                                               "certificate settings]: %s" %  
    693                                                traceback.format_exc())  
    694              
    695         # Verify peer's (MyProxy server) certificate 
    696         context.set_verify(SSL.VERIFY_PEER|SSL.VERIFY_FAIL_IF_NO_PEER_CERT,  
    697                            self.__serverSSLCertVerify)  
    698          
     739                                               traceback.format_exc()) 
    699740            
    700741        # Disable for compatibility with myproxy server (er, globus) 
     
    713754        @param nBitsForKey: number of bits for private key generation -  
    714755        default is 2048 
    715         @rtype: string 
     756        @rtype: OpenSSL.crypto.PKey 
    716757        @return: public/private key pair 
    717758        """ 
     
    731772        @type messageDigest: basestring 
    732773        @param messageDigest: message digest type - default is MD5 
    733         @rtype: tuple 
     774        @rtype: base string 
    734775        @return certificate request PEM text and private key PEM text 
    735776        """ 
     
    949990        private key is not password protected. 
    950991        """ 
    951         globusLoc = os.environ.get('GLOBUS_LOCATION') 
     992        globusLoc = os.environ.get(MyProxyClient.GLOBUS_LOCATION_ENVVARNAME) 
    952993        if not sslCertFile: 
    953994            if globusLoc: 
    954995                sslCertFile = os.path.join(globusLoc,  
    955                                             *MyProxyClient._hostCertSubDirPath) 
     996                                            *MyProxyClient.HOSTCERT_SUBDIRPATH) 
    956997                sslKeyFile = os.path.join(globusLoc,  
    957                                             *MyProxyClient._hostKeySubDirPath) 
     998                                            *MyProxyClient.HOSTKEY_SUBDIRPATH) 
    958999            else: 
    9591000                raise MyProxyClientError( 
     
    10111052        @return none 
    10121053        """ 
    1013         globusLoc = os.environ.get('GLOBUS_LOCATION') 
     1054        globusLoc = os.environ.get(MyProxyClient.GLOBUS_LOCATION_ENVVARNAME) 
    10141055        if not sslCertFile or not sslKeyFile: 
    10151056            if globusLoc: 
    10161057                sslCertFile = os.path.join(globusLoc,  
    1017                                          *MyProxyClient._hostCertSubDirPath) 
     1058                                           *MyProxyClient.HOSTCERT_SUBDIRPATH) 
    10181059                sslKeyFile = os.path.join(globusLoc,  
    1019                                          *MyProxyClient._hostKeySubDirPath) 
     1060                                          *MyProxyClient.HOSTKEY_SUBDIRPATH) 
    10201061            else: 
    10211062                raise MyProxyClientError( 
     
    10671108        @return none 
    10681109        """ 
    1069         globusLoc = os.environ.get('GLOBUS_LOCATION') 
     1110        globusLoc = os.environ.get(MyProxyClient.GLOBUS_LOCATION_ENVVARNAME) 
    10701111        if not sslCertFile or not sslKeyFile: 
    10711112            if globusLoc: 
    10721113                sslCertFile = os.path.join(globusLoc,  
    1073                                          *MyProxyClient._hostCertSubDirPath) 
     1114                                         *MyProxyClient.HOSTCERT_SUBDIRPATH) 
    10741115                sslKeyFile = os.path.join(globusLoc,  
    1075                                          *MyProxyClient._hostKeySubDirPath) 
     1116                                         *MyProxyClient.HOSTKEY_SUBDIRPATH) 
    10761117            else: 
    10771118                raise MyProxyClientError( 
     
    11531194            passphrase = str(passphrase) 
    11541195         
    1155         globusLoc = os.environ.get('GLOBUS_LOCATION') 
     1196        globusLoc = os.environ.get(MyProxyClient.GLOBUS_LOCATION_ENVVARNAME) 
    11561197        if not sslCertFile or not sslKeyFile: 
    11571198            if globusLoc: 
    11581199                sslCertFile = os.path.join(globusLoc,  
    1159                                          *MyProxyClient._hostCertSubDirPath) 
     1200                                           *MyProxyClient.HOSTCERT_SUBDIRPATH) 
    11601201                sslKeyFile = os.path.join(globusLoc,  
    1161                                          *MyProxyClient._hostKeySubDirPath) 
     1202                                          *MyProxyClient.HOSTKEY_SUBDIRPATH) 
    11621203            else: 
    11631204                # Default so that the owner is the same as the ID of the  
     
    12111252         
    12121253    def logon(self, username, passphrase, lifetime=None, keyPair=None,  
    1213               certReq=None, nBitsForKey=PRIKEY_NBITS): 
     1254              certReq=None, nBitsForKey=PRIKEY_NBITS, bootstrap=False, 
     1255              updateTrustRoots=False): 
    12141256        """Retrieve a proxy credential from a MyProxy server 
    12151257         
     
    12251267        @type lifetime: int 
    12261268        @param lifetime: lifetime for generated certificate 
     1269         
     1270        @type keyPair: OpenSSL.crypto.PKey 
     1271        @param keyPair: Public/Private key pair.  This is ignored if a  
     1272        certificate request is passed via the certReq keyword 
     1273         
     1274        @type certReq: string 
     1275        @param certReq: ASN1 format certificate request, if none set, one is  
     1276        created along with a key pair 
     1277         
     1278        @type nBitsForKey: int 
     1279        @param nBitsForKey: number of bits to use when generating key pair, 
     1280        defaults to the PRIKEY_NBITS class variable setting.  This keyword is 
     1281        ignored if a key pair is passed in from an external source via the 
     1282        keyPair keyword 
    12271283         
    12281284        @rtype: tuple 
     
    12301286        user certificate, it's private key and the issuing certificate.  The 
    12311287        issuing certificate is only set if the user certificate is a proxy 
     1288         
     1289        @type bootstrap: bool 
     1290        @param bootstrap: If set to True, bootstrap trust roots i.e. connect to 
     1291        MyProxy server without verification of the server's SSL certificate 
     1292        against any CA certificates.  Set to False, for default behaviour: 
     1293        verify server SSL certificate against CA certificates held in location 
     1294        set by the "caCertDir" attribute.  If bootstrap is set, updateTrustRoots 
     1295        will be forced to True also 
     1296         
     1297        @type updateTrustRoots: bool 
     1298        @param updateTrustRoots: set to True to update the trust roots 
    12321299        """ 
    1233          
     1300        if bootstrap: 
     1301            log.info('Bootstrapping MyProxy server root of trust.') 
     1302             
     1303            # Bootstrap implies update to trust roots 
     1304            updateTrustRoots = True 
     1305         
     1306        if updateTrustRoots: 
     1307            self.getTrustRoots(username,  
     1308                               passphrase,  
     1309                               writeToCACertDir=True,  
     1310                               bootstrap=bootstrap) 
     1311             
    12341312        lifetime = lifetime or self.proxyCertLifetime 
    12351313 
     
    12551333        # send get command - ensure conversion from unicode before writing 
    12561334        cmd = MyProxyClient.GET_CMD % (username, passphrase, lifetime) 
     1335             
    12571336        conn.write(str(cmd)) 
    1258      
     1337         
    12591338        # process server response 
    12601339        dat = conn.recv(MyProxyClient.SERVER_RESP_BLK_SIZE) 
     1340                    
    12611341        respCode, errorTxt = self._deserializeResponse(dat) 
    12621342        if respCode: 
     
    12781358        respCode, errorTxt = self._deserializeResponse(resp) 
    12791359        if respCode: 
    1280             raise MyProxyClientRetrieveError(errorTxt) 
     1360            raise MyProxyClientRetrieveError(errorTxt)      
    12811361     
    12821362        # deserialize certs from received cert data 
     
    13041384        return self.logon(*arg, **kw) 
    13051385     
    1306     def getTrustRoots(self, username='', passphrase=''): 
     1386    def getTrustRoots(self,  
     1387                      username='',  
     1388                      passphrase='',  
     1389                      writeToCACertDir=False, 
     1390                      bootstrap=False): 
    13071391        """Get trust roots for the given MyProxy server 
    13081392         
     
    13131397        @param passphrase: pass-phrase (optional) 
    13141398        server 
     1399         
     1400        @type writeToCACertDir: bool 
     1401        @param writeToCACertDir: if set to True, write the retrieved trust roots 
     1402        out to the directory specified by the "caCertDir" attribute 
     1403         
     1404        @type bootstrap: bool 
     1405        @param bootstrap: If set to True, bootstrap trust roots i.e. connect to 
     1406        MyProxy server without verification of the server's SSL certificate 
     1407        against any CA certificates.  Set to False, for default behaviour: 
     1408        verify server SSL certificate against CA certificates held in location 
     1409        set by the "caCertDir" attribute. 
    13151410         
    13161411        @return: trust root files as a dictionary keyed by file name with each  
     
    13181413        @rtype: dict 
    13191414        """ 
     1415        if bootstrap: 
     1416            log.info('Bootstrapping MyProxy server root of trust.') 
     1417             
    13201418        # Set-up SSL connection 
    1321         conn = self._initConnection() 
     1419        conn = self._initConnection(verifyPeerWithTrustRoots=(not bootstrap)) 
    13221420        conn.connect((self.hostname, self.port)) 
    13231421         
     
    13311429        # process server response chunks until all consumed 
    13321430        dat = '' 
     1431        tries = 0 
    13331432        try: 
    13341433            for tries in range(MyProxyClient.MAX_RECV_TRIES): 
     
    13441443                        MyProxyClient.MAX_RECV_TRIES, 
    13451444                        MyProxyClient.SERVER_RESP_BLK_SIZE) 
    1346              
     1445          
     1446        fieldName = MyProxyClient.TRUSTED_CERTS_FIELDNAME 
     1447        prefix = MyProxyClient.TRUSTED_CERTS_FILEDATA_FIELDNAME_PREFIX   
    13471448        respCode, errorTxt, fileData = self._deserializeResponse(dat,  
    1348                                                                 'TRUSTED_CERTS', 
    1349                                                                 'FILEDATA_') 
     1449                                                                 fieldName, 
     1450                                                                 prefix) 
    13501451        if respCode: 
    13511452            raise MyProxyClientGetTrustRootsError(errorTxt) 
    13521453         
    1353         filesDict = dict([(k, base64.b64decode(v))  
    1354                           for k, v in fileData.items() if k != 'TRUSTED_CERTS']) 
    1355          
     1454        filesDict = dict([(k.split(prefix, 1)[1], base64.b64decode(v))  
     1455                          for k, v in fileData.items() if k != fieldName]) 
     1456         
     1457        if writeToCACertDir: 
     1458            for fileName, fileContents in filesDict.items(): 
     1459                filePath = os.path.join(self.caCertDir, fileName) 
     1460                open(filePath, 'wb').write(fileContents) 
     1461                 
    13561462        return filesDict 
    13571463         
  • TI12-security/trunk/MyProxyClient/myproxy/test/myProxyClient.cfg

    r6840 r6918  
    1212# Delete this element and take setting from MYPROXY_SERVER environment  
    1313# variable if required 
    14 hostname=localhost 
     14#hostname=localhost 
    1515 
    1616# Delete this element to take default setting 7512 or read  
     
    2222# MYPROXY_SERVER_DN environment variable if preferred 
    2323#serverDN=/O=NDG/OU=Raphael/CN=raphael 
     24 
     25# MyProxy Server CommonName prefix e.g. 'myproxy/' in order to match certificate 
     26# CN 'myproxy/<fqdn>'.  The default value is 'host/' 
     27serverCNPrefix= 
    2428 
    2529# This directory path is used to locate the OpenSSL configuration file 
     
    4044proxyCertLifetime=64800 
    4145 
    42 #caCertFilePath=$MYPROXYCLIENT_UNITTEST_DIR/ndg-test-ca.crt 
    43 caCertFilePath=$MYPROXYCLIENT_UNITTEST_DIR/test-ca.crt 
     46# Trust roots directory defaults to X509_CERT_DIR environment variable setting 
     47# or ~/.globus/certificates if not set here 
     48caCertDir=$MYPROXYCLIENT_UNITTEST_DIR/ca 
  • TI12-security/trunk/MyProxyClient/myproxy/test/myProxyClientTest.cfg

    r6844 r6918  
    1515# terminal.  To set a null password, leave the field in place but set to 
    1616# blank 
    17 [test01Store] 
     17[test02Store] 
    1818username: testuser 
    1919passphrase: testpassword 
     
    2424sslKeyFilePassphrase: testpassword 
    2525 
    26 [test02GetDelegation] 
     26[test03GetDelegation] 
    2727username: testuser 
    2828passphrase: testpassword 
     
    3131proxyKeyFileOut: $MYPROXYCLIENT_UNITTEST_DIR/proxy.key 
    3232 
    33 [test03Info] 
     33[test04Info] 
    3434username: testuser 
    3535sslCertFile: $MYPROXYCLIENT_UNITTEST_DIR/proxy.crt 
     
    3737sslKeyFilePassphrase: testpassword 
    3838 
    39 [test04ChangePassphrase] 
     39[test05GetDelegationWithBootstrappedTrustRoots] 
     40username: testuser 
     41passphrase: testpassword 
     42 
     43[test06ChangePassphrase] 
    4044username: testuser 
    4145sslCertFile: $MYPROXYCLIENT_UNITTEST_DIR/proxy.crt 
     
    4549sslKeyFilePassphrase: testpassword 
    4650 
    47 [test05Destroy] 
     51 
     52[test07Destroy] 
    4853username: testuser 
    4954sslCertFile: $MYPROXYCLIENT_UNITTEST_DIR/proxy.crt 
  • TI12-security/trunk/MyProxyClient/myproxy/test/test_myproxyclient.py

    r6847 r6918  
    1616import os 
    1717import sys 
    18 import getpass 
     18from getpass import getpass 
    1919import traceback 
    2020from os import path 
     
    3838 
    3939class MyProxyClientLiveTestCase(_MyProxyClientTestCase): 
    40     '''Tests require a connection to a real MyProxy service running on a host 
     40    '''Tests require a connection to a real MyProxy service running on a host. 
     41     
     42    The server must be set up as a credential repository - i.e. able to receive 
     43    and store credentials 
    4144    ''' 
    4245    CONFIG_FILENAME = "myProxyClientTest.cfg" 
     
    5760        configFilePath = path.expandvars(self.cfg['setUp']['cfgFilePath']) 
    5861        self.clnt = MyProxyClient(cfgFilePath=configFilePath) 
    59          
    60     def test01Store(self): 
    61         # upload X509 cert and private key to repository 
    62         thisSection = self.cfg['test01Store'] 
    63          
    64         passphrase = thisSection.get('passphrase') 
    65         if passphrase is None: 
    66             passphrase = getpass.getpass(prompt="\ntest1Store credential " 
    67                                                 "pass-phrase: ") 
    68              
    69         sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
    70         if sslKeyFilePassphrase is None: 
    71             sslKeyFilePassphrase = getpass.getpass( 
    72                         prompt="\ntest1Store credential owner pass-phrase: ") 
    73  
    74         certFile = path.expandvars(thisSection['ownerCertFile']) 
    75         keyFile = path.expandvars(thisSection['ownerKeyFile']) 
    76         sslCertFile = path.expandvars(thisSection['sslCertFile']) 
    77         sslKeyFile = path.expandvars(thisSection['sslKeyFile']) 
    78              
    79         self.clnt.store(thisSection['username'], 
    80                         passphrase, 
    81                         certFile, 
    82                         keyFile, 
    83                         sslCertFile=sslCertFile, 
    84                         sslKeyFile=sslKeyFile, 
    85                         sslKeyFilePassphrase=sslKeyFilePassphrase, 
    86                         force=False) 
    87         print("Store creds for user %s" % thisSection['username']) 
    88      
    89     def test02GetDelegation(self): 
    90         # retrieve proxy cert./private key 
    91         thisSection = self.cfg['test02GetDelegation'] 
    92          
    93         passphrase = thisSection.get('passphrase') 
    94         if passphrase is None: 
    95             passphrase = getpass.getpass(prompt="\ntest2GetDelegation " 
    96                                                 "passphrase: ") 
    97           
    98         proxyCertFile = path.expandvars(thisSection['proxyCertFileOut']) 
    99         proxyKeyFile = path.expandvars(thisSection['proxyKeyFileOut']) 
    100  
    101         creds = self.clnt.getDelegation(thisSection['username'], passphrase) 
    102         print "proxy credentials:"  
    103         print ''.join(creds) 
    104         open(proxyCertFile, 'w').write(creds[0]+''.join(creds[2:])) 
    105         open(proxyKeyFile, 'w').write(creds[1]) 
    106  
    107     def test03Info(self): 
    108         # Retrieve information about a given credential 
    109         thisSection = self.cfg['test03Info'] 
    110          
    111         # sslKeyFilePassphrase can be omitted from the congif file in which case 
    112         # the get call below would return None 
    113         sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
    114         if sslKeyFilePassphrase is None: 
    115             sslKeyFilePassphrase = getpass.getpass(prompt="\ntest3Info owner " 
    116                                               "credentials passphrase: ") 
    117  
    118         credExists, errorTxt, fields = self.clnt.info( 
    119                                  thisSection['username'], 
    120                                  path.expandvars(thisSection['sslCertFile']), 
    121                                  path.expandvars(thisSection['sslKeyFile']), 
    122                                  sslKeyFilePassphrase=sslKeyFilePassphrase) 
    123         print "test3Info... " 
    124         print "credExists: %s" % credExists 
    125         print "errorTxt: " + errorTxt 
    126         print "fields: %s" % fields 
    127  
    128     def test04ChangePassphrase(self):         
    129         # change pass-phrase protecting a given credential 
    130         thisSection = self.cfg['test04ChangePassphrase'] 
    131          
    132         passphrase = thisSection.get('passphrase') 
    133         if passphrase is None: 
    134             passphrase = getpass.getpass(prompt="test4ChangePassphrase - " 
    135                                                 "passphrase: ") 
    136          
    137         newPassphrase = thisSection.get('newPassphrase') 
    138         if newPassphrase is None: 
    139             newPassphrase = getpass.getpass(prompt="test4ChangePassphrase " 
    140                                                    "- new passphrase: ") 
    141  
    142             confirmNewPassphrase = getpass.getpass(prompt=\ 
    143                                                    "test4ChangePassphrase " 
    144                                                    "- confirm new " 
    145                                                    "passphrase: ") 
    146  
    147             if newPassphrase != confirmNewPassphrase: 
    148                 self.fail("New and confirmed new password don't match") 
    149                  
    150         sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') or passphrase 
    151  
    152         self.clnt.changePassphrase(thisSection['username'], 
    153                                passphrase, 
    154                                newPassphrase,  
    155                                path.expandvars(thisSection['sslCertFile']), 
    156                                path.expandvars(thisSection['sslKeyFile']), 
    157                                sslKeyFilePassphrase=sslKeyFilePassphrase) 
    158         print("Changed pass-phrase") 
    159  
    160     def test05Destroy(self): 
    161         # destroy credentials for a given user 
    162         thisSection = self.cfg['test05Destroy'] 
    163          
    164         sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
    165         if sslKeyFilePassphrase is None: 
    166             sslKeyFilePassphrase = getpass.getpass(prompt="\ntest5Destroy " 
    167                                               "credential owner passphrase: ") 
    168  
    169         self.clnt.destroy(thisSection['username'],  
    170                       sslCertFile=path.expandvars(thisSection['sslCertFile']), 
    171                       sslKeyFile=path.expandvars(thisSection['sslKeyFile']), 
    172                       sslKeyFilePassphrase=sslKeyFilePassphrase) 
    173         print("Destroy creds for user %s" % thisSection['username']) 
    174          
    175     def test06GetTrustRoots(self): 
    176         # Test get trust roots command 
    177         trustRoots = self.clnt.getTrustRoots() 
     62 
     63    def __del__(self): 
     64        """Clear up CA certs retrieved in test01GetTrustRoots call ready for 
     65        next run of these unit tests 
     66        """ 
     67        self._deleteTrustRootFiles() 
     68         
     69    def _deleteTrustRootFiles(self): 
     70        """Helper method clears up CA certs in trust roots directory set from 
     71        previous call to test01GetTrustRoots() 
     72        """         
     73        if hasattr(self, 'trustRootFiles'): 
     74            for fileName in self.trustRootFiles: 
     75                os.remove(fileName) 
     76             
     77    def test01GetTrustRoots(self): 
     78        # Test get trust roots command bootstrapping trust 
     79        trustRoots = self.clnt.getTrustRoots(writeToCACertDir=True,  
     80                                             bootstrap=True) 
    17881        self.assert_(trustRoots) 
    17982        self.assert_(isinstance(trustRoots, dict)) 
     
    18891                subj = cert.get_subject() 
    18992                self.assert_(subj) 
    190                 print("Trust root certificate retrieved with DN=%s" % subj) 
     93                print("Trust root certificate retrieved with DN=%s" % subj)  
     94                 
     95        # Keep for __del__ tidy up 
     96        self.trustRootFiles = [] 
     97         
     98        dirContents = os.listdir(self.clnt.caCertDir) 
     99        for fileName in trustRoots:      
     100            self.assert_(fileName in dirContents) 
     101            self.trustRootFiles.append(os.path.join(self.clnt.caCertDir,  
     102                                                    fileName)) 
     103    
     104    def test02Store(self): 
     105        # upload X509 cert and private key to repository 
     106        thisSection = self.cfg['test02Store'] 
     107         
     108        passphrase = thisSection.get('passphrase') 
     109        if passphrase is None: 
     110            passphrase = getpass("\ntest02Store credential pass-phrase: ") 
     111             
     112        sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
     113        if sslKeyFilePassphrase is None: 
     114            sslKeyFilePassphrase = getpass("\ntest02Store credential owner " 
     115                                           "pass-phrase: ") 
     116 
     117        certFile = path.expandvars(thisSection['ownerCertFile']) 
     118        keyFile = path.expandvars(thisSection['ownerKeyFile']) 
     119        sslCertFile = path.expandvars(thisSection['sslCertFile']) 
     120        sslKeyFile = path.expandvars(thisSection['sslKeyFile']) 
     121             
     122        self.clnt.store(thisSection['username'], 
     123                        passphrase, 
     124                        certFile, 
     125                        keyFile, 
     126                        sslCertFile=sslCertFile, 
     127                        sslKeyFile=sslKeyFile, 
     128                        sslKeyFilePassphrase=sslKeyFilePassphrase, 
     129                        force=False) 
     130        print("Store creds for user %s" % thisSection['username']) 
     131     
     132    def test03GetDelegation(self): 
     133        # retrieve proxy cert./private key 
     134        thisSection = self.cfg['test03GetDelegation'] 
     135         
     136        passphrase = thisSection.get('passphrase') 
     137        if passphrase is None: 
     138            passphrase = getpass("\ntest03GetDelegation passphrase: ") 
     139          
     140        proxyCertFile = path.expandvars(thisSection['proxyCertFileOut']) 
     141        proxyKeyFile = path.expandvars(thisSection['proxyKeyFileOut']) 
     142         
     143        creds = self.clnt.getDelegation(thisSection['username'], passphrase) 
     144        print "proxy credentials:"  
     145        print ''.join(creds) 
     146        open(proxyCertFile, 'w').write(creds[0]+''.join(creds[2:])) 
     147        open(proxyKeyFile, 'w').write(creds[1]) 
     148 
     149    def test04Info(self): 
     150        # Retrieve information about a given credential 
     151        thisSection = self.cfg['test04Info'] 
     152         
     153        # sslKeyFilePassphrase can be omitted from the congif file in which case 
     154        # the get call below would return None 
     155        sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
     156        if sslKeyFilePassphrase is None: 
     157            sslKeyFilePassphrase = getpass("\ntest04Info owner credentials " 
     158                                           "passphrase: ") 
     159 
     160        credExists, errorTxt, fields = self.clnt.info( 
     161                                 thisSection['username'], 
     162                                 path.expandvars(thisSection['sslCertFile']), 
     163                                 path.expandvars(thisSection['sslKeyFile']), 
     164                                 sslKeyFilePassphrase=sslKeyFilePassphrase) 
     165        print "test04Info... " 
     166        print "credExists: %s" % credExists 
     167        print "errorTxt: " + errorTxt 
     168        print "fields: %s" % fields 
     169 
     170    def test06ChangePassphrase(self):         
     171        # change pass-phrase protecting a given credential 
     172        thisSection = self.cfg['test06ChangePassphrase'] 
     173         
     174        passphrase = thisSection.get('passphrase') 
     175        if passphrase is None: 
     176            passphrase = getpass("test06ChangePassphrase - passphrase: ") 
     177         
     178        newPassphrase = thisSection.get('newPassphrase') 
     179        if newPassphrase is None: 
     180            newPassphrase = getpass("test06ChangePassphrase - new passphrase: ") 
     181 
     182            confirmNewPassphrase = getpass("test06ChangePassphrase - confirm " 
     183                                           "new passphrase: ") 
     184 
     185            if newPassphrase != confirmNewPassphrase: 
     186                self.fail("New and confirmed new password don't match") 
     187                 
     188        sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') or \ 
     189                            passphrase 
     190 
     191        self.clnt.changePassphrase(thisSection['username'], 
     192                               passphrase, 
     193                               newPassphrase,  
     194                               path.expandvars(thisSection['sslCertFile']), 
     195                               path.expandvars(thisSection['sslKeyFile']), 
     196                               sslKeyFilePassphrase=sslKeyFilePassphrase) 
     197        print("Changed pass-phrase") 
     198 
     199    def test05GetDelegationWithBootstrappedTrustRoots(self): 
     200        # Get delegation call whilst simulataneously bootstrapping trust roots 
     201        thisSection = self.cfg['test05GetDelegationWithBootstrappedTrustRoots'] 
     202         
     203        passphrase = thisSection.get('passphrase') 
     204        if passphrase is None: 
     205            passphrase = getpass("\n" 
     206                                 "test05GetDelegationWithBootstrappedTrustRoots" 
     207                                 "passphrase: ") 
     208         
     209        # Ensure any previously set trust root files are removed 
     210        self._deleteTrustRootFiles() 
     211         
     212        creds = self.clnt.getDelegation(thisSection['username'], passphrase, 
     213                                        bootstrap=True) 
     214        print "proxy credentials:"  
     215        print ''.join(creds) 
     216               
     217    def test07Destroy(self): 
     218        # destroy credentials for a given user 
     219        thisSection = self.cfg['test07Destroy'] 
     220         
     221        sslKeyFilePassphrase = thisSection.get('sslKeyFilePassphrase') 
     222        if sslKeyFilePassphrase is None: 
     223            sslKeyFilePassphrase = getpass("\ntest07Destroy credential owner " 
     224                                           "passphrase: ") 
     225 
     226        self.clnt.destroy(thisSection['username'],  
     227                      sslCertFile=path.expandvars(thisSection['sslCertFile']), 
     228                      sslKeyFile=path.expandvars(thisSection['sslKeyFile']), 
     229                      sslKeyFilePassphrase=sslKeyFilePassphrase) 
     230        print("Destroy creds for user %s" % thisSection['username']) 
    191231         
    192232         
     
    210250                                   proxyCertMaxLifetime=60000, 
    211251                                   proxyCertLifetime=30000,             
    212                                    caCertFilePath=mkPath('ndg-test-ca.crt')) 
     252                                   caCertDir=mkPath('')) 
    213253             
    214254            self.assert_(client.port == 20000) 
     
    218258            self.assert_(client.proxyCertLifetime == 30000) 
    219259            self.assert_(client.openSSLConfFilePath == mkPath('openssl.conf')) 
    220             self.assert_(client.caCertFilePath == mkPath('ndg-test-ca.crt')) 
     260            self.assert_(client.caCertDir == mkPath('')) 
    221261        finally: 
    222262            os.environ = environBackup        
     
    245285            pass 
    246286         
    247         client.caCertFilePath = mkPath('ca.pem')  
    248287        client.caCertDir = mkPath('/etc/grid-security/certificates')  
    249288         
     
    254293        self.assert_(client.proxyCertLifetime == 70000) 
    255294        self.assert_(client.openSSLConfFilePath == mkPath('ssl.cnf')) 
    256         self.assert_(client.caCertFilePath == mkPath('ca.pem'))  
    257295        self.assert_( 
    258296                client.caCertDir == mkPath('/etc/grid-security/certificates'))  
Note: See TracChangeset for help on using the changeset viewer.