U
    
W[
{  ã                   @   s  d Z ddlmZmZ zddlZW n ek
r8   dZY nX dZddlZddlm	Z	 ddl
mZ ddlmZ ddlmZ dd	lmZ dd
lmZ ddlmZ ddlmZ ddlmZ ddlmZ ddlmZmZmZm Z  ddl!m"Z"m#Z# ddl$m%Z%m&Z& ddl'm(Z( edƒrPedƒrPdZ)ddl*m+Z+ ddl,m-Z- ddl.m/Z/m0Z0 ddl1m2Z2 ndZ)e3eddƒdkrldZ4ndZ4G dd„ deƒZ5G dd„ deƒZ6G d d!„ d!eƒZ7G d"d#„ d#eƒZ8G d$d%„ d%eƒZ9G d&d'„ d'eƒZ:G d(d)„ d)eƒZ;e	d*d+gƒZ<G d,d-„ d-e=ƒZ>G d.d/„ d/eƒZ?dS )0z&
Tests for L{twisted.conch.checkers}.
é    )Úabsolute_importÚdivisionNzcannot run without crypt module)Ú
namedtuple)ÚBytesIO)ÚverifyObject)Úutil)Ú_b64encodebytes)ÚFailure)ÚrequireModule)ÚTestCase)ÚFilePath)Ú'InMemoryUsernamePasswordDatabaseDontUse)ÚUsernamePasswordÚIUsernamePasswordÚSSHPrivateKeyÚISSHPrivateKey)ÚUnhandledCredentialsÚUnauthorizedLogin)ÚUserDatabaseÚShadowDatabase)ÚMockOSZcryptographyZpyasn1)Úkeys)Úcheckers)ÚNotEnoughAuthenticationÚValidPublicKey)Úkeydataz)can't run without cryptography and PyASN1Úgeteuidz0Cannot run without effective UIDs (questionable)c                   @   sX   e Zd ZdZepeZdd„ Zdd„ Zdd„ Z	dd	„ Z
d
d„ Zdd„ Zdd„ Zdd„ ZdS )ÚHelperTestszl
    Tests for helper functions L{verifyCryptedPassword}, L{_pwdGetByName} and
    L{_shadowGetByName}.
    c                 C   s   t ƒ | _d S ©N)r   Úmockos©Úself© r"   úB/usr/lib/python3/dist-packages/twisted/conch/test/test_checkers.pyÚsetUp<   s    zHelperTests.setUpc                 C   s4   d}d}t   ||¡}|  t ||¡d||f ¡ dS )z–
        L{verifyCryptedPassword} returns C{True} if the plaintext password
        passed to it matches the encrypted password passed to it.
        úsecret stringZsaltyz1%r supposed to be valid encrypted password for %rN©ÚcryptÚ
assertTruer   ÚverifyCryptedPassword©r!   ÚpasswordÚsaltÚcryptedr"   r"   r#   Útest_verifyCryptedPassword@   s    
 ÿþz&HelperTests.test_verifyCryptedPasswordc                 C   s4   d}d}t   ||¡}|  t ||¡d||f ¡ dS )zŠ
        L{verifyCryptedPassword} returns True if the provided cleartext password
        matches the provided MD5 password hash.
        r+   z$1$saltz1%r supposed to be valid encrypted password for %sNr&   r*   r"   r"   r#   Útest_verifyCryptedPasswordMD5N   s    
 ÿþz)HelperTests.test_verifyCryptedPasswordMD5c                 C   s4   d}d}t   ||¡}|  t ||¡d||f ¡ dS )zž
        L{verifyCryptedPassword} returns C{False} if the plaintext password
        passed to it does not match the encrypted password passed to it.
        zstring secretr%   z5%r not supposed to be valid encrypted password for %sN)r'   ÚassertFalser   r)   )r!   r+   Úwrongr-   r"   r"   r#   Útest_refuteCryptedPassword\   s    
 ÿþz&HelperTests.test_refuteCryptedPasswordc              	   C   sF   t ƒ }| ddddddd¡ |  td|¡ |  t d¡| d¡¡ d	S )
z‡
        L{_pwdGetByName} returns a tuple of items from the UNIX /etc/passwd
        database if the L{pwd} module is present.
        ÚaliceZsecrité   é   z
first lastú/fooú/bin/shÚpwdN)r   ÚaddUserÚpatchr   ÚassertEqualÚ_pwdGetByNameÚgetpwnam©r!   Úuserdbr"   r"   r#   Útest_pwdGetByNamej   s          ÿ ÿzHelperTests.test_pwdGetByNamec                 C   s"   |   tdd¡ |  t d¡¡ dS )zW
        If the C{pwd} module isn't present, L{_pwdGetByName} returns L{None}.
        r8   Nr3   )r:   r   ÚassertIsNoner<   r    r"   r"   r#   Útest_pwdGetByNameWithoutPwdw   s    z'HelperTests.test_pwdGetByNameWithoutPwdc                 C   s’   t ƒ }| ddddddddd	¡	 |  td
|¡ d| j_d| j_|  td| j¡ |  t 	d¡| 
d¡¡ |  | jjddg¡ |  | jjddg¡ dS )z„
        L{_shadowGetByName} returns a tuple of items from the UNIX /etc/shadow
        database if the L{spwd} is present.
        ÚbobZ
passphraser4   r5   é   é   é   é   é   Úspwdé)	  éÒ  Úosr   N)r   r9   r:   r   r   ÚeuidÚegidr   r;   Ú_shadowGetByNameZgetspnamÚseteuidCallsÚsetegidCallsr>   r"   r"   r#   Útest_shadowGetByName   s     ÿz HelperTests.test_shadowGetByNamec                 C   sB   |   tdd¡ |  t d¡¡ |  | jjg ¡ |  | jjg ¡ dS )zP
        L{_shadowGetByName} returns L{None} if C{spwd} is not present.
        rI   NrC   )r:   r   rA   rO   r;   r   rP   rQ   r    r"   r"   r#   Útest_shadowGetByNameWithoutSpwd’   s    z+HelperTests.test_shadowGetByNameWithoutSpwdN)Ú__name__Ú
__module__Ú__qualname__Ú__doc__Ú	cryptSkipÚdependencySkipÚskipr$   r.   r/   r2   r@   rB   rR   rS   r"   r"   r"   r#   r   5   s   r   c                   @   sp   e Zd ZdZepeZdd„ Zdd„ Zdd„ Z	dd	„ Z
d
d„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ ZdS )ÚSSHPublicKeyDatabaseTestsz,
    Tests for L{SSHPublicKeyDatabase}.
    c              	   C   s´   t  ¡ | _tdƒ| _tdƒ| _d| j d | j d | _tƒ | _t	|  
¡ ƒ| j_| jj ¡  |  td| j¡ | jj d¡| _| j ¡  tƒ }| dd	d
dd| jjjd¡ || j_d S )Nó   foobaró   eggspams   t1 s    foo
t2 s    egg
rL   ú.sshó   useró   passwordr4   r5   s
   first lastó
   /bin/shell)r   ÚSSHPublicKeyDatabaseÚcheckerr   Zkey1Zkey2Úcontentr   r   r   ÚmktempÚpathÚmakedirsr:   r   ÚchildÚsshDirr   r9   Z_userdbr>   r"   r"   r#   r$   ¤   s.    


ÿ
     þzSSHPublicKeyDatabaseTests.setUpc                 C   sL   | j | jgd}|  |d d t¡ |  |d d d¡ |  t|ƒd¡ dS )zJ
        L{SSHPublicKeyDatabase} is deprecated as of version 15.0
        )ZoffendingFunctionsr   ÚcategoryÚmessagezÜtwisted.conch.checkers.SSHPublicKeyDatabase was deprecated in Twisted 15.0.0: Please use twisted.conch.checkers.SSHPublicKeyChecker, initialized with an instance of twisted.conch.checkers.UNIXAuthorizedKeysFiles instead.r4   N)ZflushWarningsr$   r;   ÚDeprecationWarningÚlen)r!   ZwarningsShownr"   r"   r#   Útest_deprecated¹   s    ÿ
þz)SSHPublicKeyDatabaseTests.test_deprecatedc                 C   sj   | j  |¡ | j¡ tddƒ}d|_|  | j |¡¡ d|_|  | j |¡¡ d|_|  	| j |¡¡ d S )Nr_   r`   r\   r]   s
   notallowed)
ri   rh   Ú
setContentrd   r   Úblobr(   rc   ÚcheckKeyr0   )r!   ÚfilenameÚuserr"   r"   r#   Ú_testCheckKeyÊ   s    
z'SSHPublicKeyDatabaseTests._testCheckKeyc                 C   s.   |   d¡ |  | jjg ¡ |  | jjg ¡ dS )z˜
        L{SSHPublicKeyDatabase.checkKey} should retrieve the content of the
        authorized_keys file and check the keys against that file.
        Úauthorized_keysN©rt   r;   r   rP   rQ   r    r"   r"   r#   Útest_checkKeyÕ   s    
z'SSHPublicKeyDatabaseTests.test_checkKeyc                 C   s.   |   d¡ |  | jjg ¡ |  | jjg ¡ dS )z™
        L{SSHPublicKeyDatabase.checkKey} should retrieve the content of the
        authorized_keys2 file and check the keys against that file.
        Úauthorized_keys2Nrv   r    r"   r"   r#   Útest_checkKey2ß   s    
z(SSHPublicKeyDatabaseTests.test_checkKey2c                    sÈ   | j  d¡‰ ˆ  | j¡ ˆ  d¡ |  ˆ jd¡ | jj‰‡ ‡fdd„}d| j_d| j_	|  
| jd|¡ |  
td	| j¡ td
dƒ}d|_|  | j |¡¡ |  | jjddddg¡ |  | jjddg¡ dS )z˜
        If the key file is readable, L{SSHPublicKeyDatabase.checkKey} should
        switch its uid/gid to the ones of the authenticated user.
        ru   r   éÿ  c                    s   ˆ   d¡ ˆ| ƒS )Nrz   )Úchmod)rM   ©ZkeyFileZsavedSeteuidr"   r#   Úseteuidõ   s    
z>SSHPublicKeyDatabaseTests.test_checkKeyAsRoot.<locals>.seteuidrJ   rK   r}   rL   r_   r`   r\   r4   r5   N)ri   rh   ro   rd   r{   Z
addCleanupr   r}   rM   rN   r:   r   r   rp   r(   rc   rq   r;   rP   rQ   )r!   r}   rs   r"   r|   r#   Útest_checkKeyAsRooté   s    

z-SSHPublicKeyDatabaseTests.test_checkKeyAsRootc                    s\   dd„ }ˆ   ˆ jd|¡ tddtjdtj tj¡ 	d¡ƒ}ˆ j 
|¡}‡ fdd„}| |¡S )	z
        L{SSHPublicKeyDatabase.requestAvatarId} should return the avatar id
        passed in if its C{_checkKey} method returns True.
        c                 S   s   dS ©NTr"   ©Zignoredr"   r"   r#   Ú	_checkKey  s    zASSHPublicKeyDatabaseTests.test_requestAvatarId.<locals>._checkKeyrq   ó   testó   ssh-rsaó   fooc                    s   ˆ   | d¡ d S ©Nr‚   ©r;   ©ZavatarIdr    r"   r#   Ú_verify  s    z?SSHPublicKeyDatabaseTests.test_requestAvatarId.<locals>._verify)r:   rc   r   r   ÚpublicRSA_opensshr   ÚKeyÚ
fromStringÚprivateRSA_opensshÚsignÚrequestAvatarIdÚaddCallback)r!   r   ÚcredentialsÚdrˆ   r"   r    r#   Útest_requestAvatarId  s       þz.SSHPublicKeyDatabaseTests.test_requestAvatarIdc                 C   sB   dd„ }|   | jd|¡ tddtjddƒ}| j |¡}|  |t¡S )a(  
        L{SSHPublicKeyDatabase.requestAvatarId} should raise L{ValidPublicKey}
        if the credentials represent a valid key without a signature.  This
        tells the user that the key is valid for login, but does not actually
        allow that user to do so without a signature.
        c                 S   s   dS r   r"   r€   r"   r"   r#   r     s    zQSSHPublicKeyDatabaseTests.test_requestAvatarIdWithoutSignature.<locals>._checkKeyrq   r‚   rƒ   N)r:   rc   r   r   r‰   rŽ   ÚassertFailurer   ©r!   r   r   r‘   r"   r"   r#   Ú$test_requestAvatarIdWithoutSignature  s        ÿz>SSHPublicKeyDatabaseTests.test_requestAvatarIdWithoutSignaturec                 C   s0   dd„ }|   | jd|¡ | j d¡}|  |t¡S )z…
        If L{SSHPublicKeyDatabase.checkKey} returns False,
        C{_cbRequestAvatarId} should raise L{UnauthorizedLogin}.
        c                 S   s   dS ©NFr"   r€   r"   r"   r#   r   )  s    zKSSHPublicKeyDatabaseTests.test_requestAvatarIdInvalidKey.<locals>._checkKeyrq   N)r:   rc   rŽ   r“   r   )r!   r   r‘   r"   r"   r#   Útest_requestAvatarIdInvalidKey$  s    z8SSHPublicKeyDatabaseTests.test_requestAvatarIdInvalidKeyc                 C   sR   dd„ }|   | jd|¡ tddtjdtj tj¡ 	d¡ƒ}| j 
|¡}|  |t¡S )z¡
        Valid keys with invalid signatures should cause
        L{SSHPublicKeyDatabase.requestAvatarId} to return a {UnauthorizedLogin}
        failure
        c                 S   s   dS r   r"   r€   r"   r"   r#   r   6  s    zQSSHPublicKeyDatabaseTests.test_requestAvatarIdInvalidSignature.<locals>._checkKeyrq   r‚   rƒ   r„   )r:   rc   r   r   r‰   r   rŠ   r‹   ÚprivateDSA_opensshr   rŽ   r“   r   r”   r"   r"   r#   Ú$test_requestAvatarIdInvalidSignature0  s       þz>SSHPublicKeyDatabaseTests.test_requestAvatarIdInvalidSignaturec                    sV   dd„ }ˆ   ˆ jd|¡ tdddddƒ}ˆ j |¡}‡ fd	d
„}| |¡ ˆ  |t¡S )z~
        Exceptions raised while verifying the key should be normalized into an
        C{UnauthorizedLogin} failure.
        c                 S   s   dS r   r"   r€   r"   r"   r#   r   E  s    zSSSHPublicKeyDatabaseTests.test_requestAvatarIdNormalizeException.<locals>._checkKeyrq   r‚   Ns   blobs   sigDatas   sigc                    s    ˆ   tj¡}ˆ  t|ƒd¡ | S )Nr4   )ÚflushLoggedErrorsr   ÚBadKeyErrorr;   rm   )ZfailureÚerrorsr    r"   r#   Ú_verifyLoggedExceptionJ  s    z`SSHPublicKeyDatabaseTests.test_requestAvatarIdNormalizeException.<locals>._verifyLoggedException)r:   rc   r   rŽ   Z
addErrbackr“   r   )r!   r   r   r‘   r   r"   r    r#   Ú&test_requestAvatarIdNormalizeException@  s    
z@SSHPublicKeyDatabaseTests.test_requestAvatarIdNormalizeExceptionN)rT   rU   rV   rW   ÚeuidSkiprY   rZ   r$   rn   rt   rw   ry   r~   r’   r•   r—   r™   rž   r"   r"   r"   r#   r[   ž   s   

r[   c                   @   sD   e Zd ZdZeZdd„ Zdd„ Zdd„ Zdd	„ Z	d
d„ Z
dd„ ZdS )ÚSSHProtocolCheckerTestsz*
    Tests for L{SSHProtocolChecker}.
    c                 C   sL   t  ¡ }|  |jg ¡ | t  ¡ ¡ |  |jtg¡ |  |j t t j¡ dS )z€
        L{SSHProcotolChecker.registerChecker} should add the given checker to
        the list of registered checkers.
        N)r   ÚSSHProtocolCheckerr;   ÚcredentialInterfacesÚregisterCheckerrb   r   ÚassertIsInstance©r!   rc   r"   r"   r#   Útest_registerCheckerZ  s    ÿz,SSHProtocolCheckerTests.test_registerCheckerc                 C   sN   t  ¡ }|  |jg ¡ | t  ¡ t¡ |  |jtg¡ |  |j t t j¡ dS )zÙ
        If a specific interface is passed into
        L{SSHProtocolChecker.registerChecker}, that interface should be
        registered instead of what the checker specifies in
        credentialIntefaces.
        N)r   r¡   r;   r¢   r£   rb   r   r¤   r¥   r"   r"   r#   Ú!test_registerCheckerWithInterfaceg  s    
ÿÿz9SSHProtocolCheckerTests.test_registerCheckerWithInterfacec                    sJ   t  ¡ }tƒ }| dd¡ | |¡ | tddƒ¡}‡ fdd„}| |¡S )z†
        L{SSHProtocolChecker.requestAvatarId} should defer to one if its
        registered checkers to authenticate a user.
        r‚   c                    s   ˆ   | d¡ d S r…   r†   r‡   r    r"   r#   Ú	_callback  s    z?SSHProtocolCheckerTests.test_requestAvatarId.<locals>._callback)r   r¡   r   r9   r£   rŽ   r   r   )r!   rc   ÚpasswordDatabaser‘   r¨   r"   r    r#   r’   w  s    
z,SSHProtocolCheckerTests.test_requestAvatarIdc                 C   sV   t  ¡ }dd„ }|  |d|¡ tƒ }| dd¡ | |¡ | tddƒ¡}|  |t	¡S )zÂ
        If the client indicates that it is never satisfied, by always returning
        False from _areDone, then L{SSHProtocolChecker} should raise
        L{NotEnoughAuthentication}.
        c                 S   s   dS r–   r"   r‡   r"   r"   r#   Ú_areDone  s    zYSSHProtocolCheckerTests.test_requestAvatarIdWithNotEnoughAuthentication.<locals>._areDoneÚareDoner‚   )
r   r¡   r:   r   r9   r£   rŽ   r   r“   r   )r!   rc   rª   r©   r‘   r"   r"   r#   Ú/test_requestAvatarIdWithNotEnoughAuthentication†  s    
zGSSHProtocolCheckerTests.test_requestAvatarIdWithNotEnoughAuthenticationc                 C   s$   t  ¡ }| tddƒ¡}|  |t¡S )z™
        If the passed credentials aren't handled by any registered checker,
        L{SSHProtocolChecker} should raise L{UnhandledCredentials}.
        r‚   )r   r¡   rŽ   r   r“   r   )r!   rc   r‘   r"   r"   r#   Ú%test_requestAvatarIdInvalidCredential˜  s    z=SSHProtocolCheckerTests.test_requestAvatarIdInvalidCredentialc                 C   s   |   t ¡  d¡¡ dS )zV
        The default L{SSHProcotolChecker.areDone} should simply return True.
        N)r(   r   r¡   r«   r    r"   r"   r#   Útest_areDone¢  s    z$SSHProtocolCheckerTests.test_areDoneN)rT   rU   rV   rW   rY   rZ   r¦   r§   r’   r¬   r­   r®   r"   r"   r"   r#   r    S  s   
r    c                   @   s`   e Zd ZdZepeZdd„ Zdd„ Zdd„ Z	dd	„ Z
d
d„ Zdd„ Zdd„ Zdd„ Zdd„ ZdS )ÚUNIXPasswordDatabaseTestsz,
    Tests for L{UNIXPasswordDatabase}.
    c                 C   sP   g }|  |j¡ |  t|ƒdd¡ t|d tƒr<|d  ¡  |  |d |¡ dS )a±  
        Assert that the L{Deferred} passed in is called back with the value
        'username'.  This represents a valid login for this TestCase.

        NOTE: To work, this method's return value must be returned from the
        test method, or otherwise hooked up to the test machinery.

        @param d: a L{Deferred} from an L{IChecker.requestAvatarId} method.
        @type d: L{Deferred}
        @rtype: L{Deferred}
        r4   zlogin incompleter   N)ZaddBothÚappendr;   rm   Ú
isinstancer	   ZraiseException)r!   r‘   ÚusernameÚresultr"   r"   r#   ÚassertLoggedIn°  s    z(UNIXPasswordDatabaseTests.assertLoggedInc                 C   s<  t  ¡ }dd„ }tƒ }| d|ddƒddddd	¡ | d
dddddd	¡ tƒ }| ddddddddd¡	 | d
|d
dƒddddddd¡	 |  t d|¡ |  t d|¡ tƒ }|  td|¡ d|_d|_	t
d d!ƒ}|  | |¡d ¡ |  |jg ¡ |  |jg ¡ d"|_|  | |¡d"¡ |  |jd#dg¡ |  |jd#dg¡ d$S )%z
        L{UNIXPasswordDatabase} with no arguments has checks the C{pwd} database
        and then the C{spwd} database.
        c                 S   s    t   || ¡}t   |d| ¡}|S )Nz$1$)r'   )r²   r+   r,   r-   r"   r"   r#   r-   Ë  s    z?UNIXPasswordDatabaseTests.test_defaultCheckers.<locals>.cryptedr3   r+   r4   r5   Úfoor6   r7   rC   ÚxÚbarú/barr1   rD   rE   rF   rG   rH   é   é	   é
   é   é   é   é   r8   rI   rL   rJ   rK   ó   alicer`   ó   bobr   N)r   ÚUNIXPasswordDatabaser   r9   r   r:   r   r   rM   rN   r   r´   rŽ   r;   rP   rQ   r²   )r!   rc   r-   r8   rI   r   Úcredr"   r"   r#   Útest_defaultCheckersÄ  sH        ÿ      ÿ
z.UNIXPasswordDatabaseTests.test_defaultCheckersc                 C   s   |   tj| j|d¡ dS )aÅ  
        Asserts that the L{Deferred} passed in is erred back with an
        L{UnauthorizedLogin} L{Failure}.  This reprsents an invalid login for
        this TestCase.

        NOTE: To work, this method's return value must be returned from the
        test method, or otherwise hooked up to the test machinery.

        @param d: a L{Deferred} from an L{IChecker.requestAvatarId} method.
        @type d: L{Deferred}
        @rtype: L{None}
        zbogus valueN)ZassertRaisesr   r   r´   ©r!   r‘   r"   r"   r#   ÚassertUnauthorizedLoginí  s       ÿz1UNIXPasswordDatabaseTests.assertUnauthorizedLoginc              	   C   sR   t   dd¡}tƒ }| d|ddddd¡ t |jg¡}|  | tdd	ƒ¡d¡ d
S )zo
        L{UNIXPasswordDatabase} takes a list of functions to check for UNIX
        user information.
        ZsecretZanybodyr4   r5   rµ   r¸   r7   s   anybodys   secretN)	r'   r   r9   r   rÂ   r=   r´   rŽ   r   )r!   r+   r?   rc   r"   r"   r#   Útest_passInCheckersþ  s    þz-UNIXPasswordDatabaseTests.test_passInCheckersc                 C   sJ   dd„ }dd„ }|   td|¡ t |g¡}tddƒ}|  | |¡d¡ dS )zÝ
        If the encrypted password provided by the getpwnam function is valid
        (verified by the L{verifyCryptedPassword} function), we callback the
        C{requestAvatarId} L{Deferred} with the username.
        c                 S   s   | |kS r   r"   ©r-   Zpwr"   r"   r#   r)     s    zLUNIXPasswordDatabaseTests.test_verifyPassword.<locals>.verifyCryptedPasswordc                 S   s   | | gS r   r"   ©r²   r"   r"   r#   r=     s    z?UNIXPasswordDatabaseTests.test_verifyPassword.<locals>.getpwnamr)   ó   usernameN©r:   r   rÂ   r   r´   rŽ   ©r!   r)   r=   rc   Ú
credentialr"   r"   r#   Útest_verifyPassword  s    
z-UNIXPasswordDatabaseTests.test_verifyPasswordc                 C   s2   dd„ }t  |g¡}tddƒ}|  | |¡¡ dS )z}
        If the getpwnam function raises a KeyError, the login fails with an
        L{UnauthorizedLogin} exception.
        c                 S   s   t | ƒ‚d S r   )ÚKeyErrorrÉ   r"   r"   r#   r=   !  s    z?UNIXPasswordDatabaseTests.test_failOnKeyError.<locals>.getpwnamrÊ   N)r   rÂ   r   rÆ   rŽ   )r!   r=   rc   rÍ   r"   r"   r#   Útest_failOnKeyError  s    
z-UNIXPasswordDatabaseTests.test_failOnKeyErrorc                 C   sH   dd„ }dd„ }|   td|¡ t |g¡}tddƒ}|  | |¡¡ dS )z”
        If the verifyCryptedPassword function doesn't verify the password, the
        login fails with an L{UnauthorizedLogin} exception.
        c                 S   s   dS r–   r"   rÈ   r"   r"   r#   r)   -  s    zOUNIXPasswordDatabaseTests.test_failOnBadPassword.<locals>.verifyCryptedPasswordc                 S   s   | | gS r   r"   rÉ   r"   r"   r#   r=   /  s    zBUNIXPasswordDatabaseTests.test_failOnBadPassword.<locals>.getpwnamr)   rÊ   N)r:   r   rÂ   r   rÆ   rŽ   rÌ   r"   r"   r#   Útest_failOnBadPassword(  s    
z0UNIXPasswordDatabaseTests.test_failOnBadPasswordc                 C   sT   dd„ }dd„ }dd„ }|   td|¡ t ||g¡}tddƒ}|  | |¡d¡ d	S )
a  
        UNIXPasswordDatabase.requestAvatarId loops through each getpwnam
        function associated with it and returns a L{Deferred} which fires with
        the result of the first one which returns a value other than None.
        ones do not verify the password.
        c                 S   s   | |kS r   r"   rÈ   r"   r"   r#   r)   >  s    zRUNIXPasswordDatabaseTests.test_loopThroughFunctions.<locals>.verifyCryptedPasswordc                 S   s   | dgS )Nznot the passwordr"   rÉ   r"   r"   r#   Ú	getpwnam1@  s    zFUNIXPasswordDatabaseTests.test_loopThroughFunctions.<locals>.getpwnam1c                 S   s   | | gS r   r"   rÉ   r"   r"   r#   Ú	getpwnam2B  s    zFUNIXPasswordDatabaseTests.test_loopThroughFunctions.<locals>.getpwnam2r)   rÊ   NrË   )r!   r)   rÒ   rÓ   rc   rÍ   r"   r"   r#   Útest_loopThroughFunctions7  s    
z3UNIXPasswordDatabaseTests.test_loopThroughFunctionsc              	   C   s¶   t ƒ }| ddddddd¡ | ddddddd¡ | d	d
ddddd¡ |  td|¡ t tjg¡}tddƒ}|  | |¡¡ tddƒ}|  | |¡¡ tddƒ}|  | |¡¡ dS )z¨
        If the password returned by any function is C{""}, C{"x"}, or C{"*"} it
        is not compared against the supplied password.  Instead it is skipped.
        r3   Ú r4   r5   rµ   r·   rC   r¶   ZcarolÚ*r8   rÀ   ó    rÁ   ó   xs   caroló   *N)	r   r9   r:   r   rÂ   r<   r   rÆ   rŽ   )r!   r8   rc   rÃ   r"   r"   r#   Útest_failOnSpecialJ  s    


z,UNIXPasswordDatabaseTests.test_failOnSpecialN)rT   rU   rV   rW   rX   rY   rZ   r´   rÄ   rÆ   rÇ   rÎ   rÐ   rÑ   rÔ   rÚ   r"   r"   r"   r#   r¯   ª  s   )r¯   c                   @   s,   e Zd ZdZeZdd„ Zdd„ Zdd„ ZdS )	ÚAuthorizedKeyFileReaderTestsz5
    Tests for L{checkers.readAuthorizedKeyFile}
    c                 C   s0   t dƒ}t |dd„ ¡}|  ddgt|ƒ¡ dS )zg
        L{checkers.readAuthorizedKeyFile} does not attempt to turn comments
        into keys
        sE   # this comment is ignored
this is not
# this is again
and this is notc                 S   s   | S r   r"   ©r¶   r"   r"   r#   Ú<lambda>q  r×   zCAuthorizedKeyFileReaderTests.test_ignoresComments.<locals>.<lambda>s   this is nots   and this is notN©r   r   ZreadAuthorizedKeyFiler;   Úlist©r!   Úfileobjr³   r"   r"   r#   Útest_ignoresCommentsh  s    z1AuthorizedKeyFileReaderTests.test_ignoresCommentsc                 C   s0   t dƒ}tj|dd„ d}|  dgt|ƒ¡ dS )zw
        L{checkers.readAuthorizedKeyFile} ignores leading whitespace in
        lines, as well as empty lines
        sg   
                           # ignore
                           not ignored
                           c                 S   s   | S r   r"   rÜ   r"   r"   r#   rÝ   ~  r×   zYAuthorizedKeyFileReaderTests.test_ignoresLeadingWhitespaceAndEmptyLines.<locals>.<lambda>©ZparseKeys   not ignoredNrÞ   rà   r"   r"   r#   Ú*test_ignoresLeadingWhitespaceAndEmptyLinesu  s    zGAuthorizedKeyFileReaderTests.test_ignoresLeadingWhitespaceAndEmptyLinesc                 C   s4   dd„ }t dƒ}tj||d}|  dgt|ƒ¡ dS )zÇ
        L{checkers.readAuthorizedKeyFile} does not raise an exception
        when a key fails to parse (raises a
        L{twisted.conch.ssh.keys.BadKeyError}), but rather just keeps going
        c                 S   s   |   d¡rt d¡‚| S )Nó   fzfailed to parse)Ú
startswithr   r›   )Úliner"   r"   r#   Ú
failOnSomeˆ  s    

zKAuthorizedKeyFileReaderTests.test_ignoresUnparsableKeys.<locals>.failOnSomes   failed key
good keyrã   s   good keyNrÞ   )r!   rè   rá   r³   r"   r"   r#   Útest_ignoresUnparsableKeys‚  s    ÿz7AuthorizedKeyFileReaderTests.test_ignoresUnparsableKeysN)	rT   rU   rV   rW   rY   rZ   râ   rä   ré   r"   r"   r"   r#   rÛ   a  s
   rÛ   c                   @   s,   e Zd ZdZeZdd„ Zdd„ Zdd„ ZdS )	ÚInMemorySSHKeyDBTestsz0
    Tests for L{checkers.InMemorySSHKeyDB}
    c                 C   s    t  ddgi¡}tt j|ƒ dS )z_
        L{checkers.InMemorySSHKeyDB} implements
        L{checkers.IAuthorizedKeysDB}
        rÀ   s   keyN)r   ÚInMemorySSHKeyDBr   ÚIAuthorizedKeysDB©r!   Úkeydbr"   r"   r#   Útest_implementsInterface›  s    z.InMemorySSHKeyDBTests.test_implementsInterfacec                 C   s*   t  ddgi¡}|  g t| d¡ƒ¡ dS )z½
        If the user is not in the mapping provided to
        L{checkers.InMemorySSHKeyDB}, an empty iterator is returned
        by L{checkers.InMemorySSHKeyDB.getAuthorizedKeys}
        rÀ   s   keysrÁ   N©r   rë   r;   rß   ÚgetAuthorizedKeysrí   r"   r"   r#   Útest_noKeysForUnauthorizedUser¤  s    z4InMemorySSHKeyDBTests.test_noKeysForUnauthorizedUserc                 C   s0   t  dddgi¡}|  ddgt| d¡ƒ¡ dS )zÅ
        If the user is in the mapping provided to
        L{checkers.InMemorySSHKeyDB}, an iterator with all the keys
        is returned by L{checkers.InMemorySSHKeyDB.getAuthorizedKeys}
        rÀ   ó   aó   bNrð   rí   r"   r"   r#   Útest_allKeysForAuthorizedUser®  s    z3InMemorySSHKeyDBTests.test_allKeysForAuthorizedUserN)	rT   rU   rV   rW   rY   rZ   rï   rò   rõ   r"   r"   r"   r#   rê   ”  s
   	
rê   c                   @   sD   e Zd ZdZeZdd„ Zdd„ Zdd„ Zdd	„ Z	d
d„ Z
dd„ ZdS )ÚUNIXAuthorizedKeysFilesTestsz8
    Tests for L{checkers.UNIXAuthorizedKeysFiles}.
    c              	   C   s~   t ƒ }t|  ¡ ƒ|_|j ¡  tƒ | _| j ddddd|jjd¡ |j d¡| _	| j	 ¡  | j	 d¡}| 
d	¡ d
dg| _d S )NrÀ   r`   r4   r5   s   alice lastnamera   r^   ru   s   key 1
key 2s   key 1s   key 2)r   r   re   rf   rg   r   r?   r9   rh   ri   ro   ÚexpectedKeys)r!   r   ZauthorizedKeysr"   r"   r#   r$   À  s    
 ÿ

z"UNIXAuthorizedKeysFilesTests.setUpc                 C   s   t  | j¡}tt j|ƒ dS )zg
        L{checkers.UNIXAuthorizedKeysFiles} implements
        L{checkers.IAuthorizedKeysDB}.
        N)r   ÚUNIXAuthorizedKeysFilesr?   r   rì   rí   r"   r"   r#   rï   Ñ  s    z5UNIXAuthorizedKeysFilesTests.test_implementsInterfacec                 C   s.   t j| jdd„ d}|  g t| d¡ƒ¡ dS )zÒ
        If the user is not in the user database provided to
        L{checkers.UNIXAuthorizedKeysFiles}, an empty iterator is returned
        by L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys}.
        c                 S   s   | S r   r"   rÜ   r"   r"   r#   rÝ   á  r×   zMUNIXAuthorizedKeysFilesTests.test_noKeysForUnauthorizedUser.<locals>.<lambda>rã   rC   N)r   rø   r?   r;   rß   rñ   rí   r"   r"   r#   rò   Ú  s    ÿz;UNIXAuthorizedKeysFilesTests.test_noKeysForUnauthorizedUserc                 C   sH   | j  d¡ d¡ tj| jdd„ d}|  | jdg t| 	d¡ƒ¡ dS )a  
        If the user is in the user database provided to
        L{checkers.UNIXAuthorizedKeysFiles}, an iterator with all the keys in
        C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2} is returned
        by L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys}.
        rx   s   key 3c                 S   s   | S r   r"   rÜ   r"   r"   r#   rÝ   î  r×   z`UNIXAuthorizedKeysFilesTests.test_allKeysInAllAuthorizedFilesForAuthorizedUser.<locals>.<lambda>rã   rÀ   N)
ri   rh   ro   r   rø   r?   r;   r÷   rß   rñ   rí   r"   r"   r#   Ú1test_allKeysInAllAuthorizedFilesForAuthorizedUserå  s    ÿÿzNUNIXAuthorizedKeysFilesTests.test_allKeysInAllAuthorizedFilesForAuthorizedUserc                 C   s0   t j| jdd„ d}|  | jt| d¡ƒ¡ dS )z¸
        L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys} returns only
        the keys in C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2}
        if they exist.
        c                 S   s   | S r   r"   rÜ   r"   r"   r#   rÝ   ú  r×   zJUNIXAuthorizedKeysFilesTests.test_ignoresNonexistantFile.<locals>.<lambda>rã   rÀ   N)r   rø   r?   r;   r÷   rß   rñ   rí   r"   r"   r#   Útest_ignoresNonexistantFileó  s    ÿÿz8UNIXAuthorizedKeysFilesTests.test_ignoresNonexistantFilec                 C   s@   | j  d¡ ¡  tj| jdd„ d}|  | jt| 	d¡ƒ¡ dS )z¿
        L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys} returns only
        the keys in C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2}
        if they are readable.
        rx   c                 S   s   | S r   r"   rÜ   r"   r"   r#   rÝ     r×   zIUNIXAuthorizedKeysFilesTests.test_ignoresUnreadableFile.<locals>.<lambda>rã   rÀ   N)
ri   rh   rg   r   rø   r?   r;   r÷   rß   rñ   rí   r"   r"   r#   Útest_ignoresUnreadableFileÿ  s    ÿÿz7UNIXAuthorizedKeysFilesTests.test_ignoresUnreadableFileN)rT   rU   rV   rW   rY   rZ   r$   rï   rò   rù   rú   rû   r"   r"   r"   r#   rö   ¹  s   	rö   ZKeyDBrñ   c                   @   s   e Zd ZdZdS )Ú_DummyExceptionz0
    Fake exception to be used for testing.
    N)rT   rU   rV   rW   r"   r"   r"   r#   rü     s   rü   c                   @   sL   e Zd ZdZeZdd„ Zdd„ Zdd„ Zdd	„ Z	d
d„ Z
dd„ Zdd„ ZdS )ÚSSHPublicKeyCheckerTestsz4
    Tests for L{checkers.SSHPublicKeyChecker}.
    c                 C   sD   t ddtjdtj tj¡ d¡ƒ| _t	dd„ ƒ| _
t | j
¡| _d S )NrÀ   rƒ   r„   c                 S   s   t j tj¡gS r   )r   rŠ   r‹   r   r‰   )Ú_r"   r"   r#   rÝ   $  s    ÿz0SSHPublicKeyCheckerTests.setUp.<locals>.<lambda>)r   r   r‰   r   rŠ   r‹   rŒ   r   r   Ú_KeyDBrî   r   ZSSHPublicKeyCheckerrc   r    r"   r"   r#   r$      s       þzSSHPublicKeyCheckerTests.setUpc                 C   s"   d| j _|  | j | j ¡t¡ dS )z
        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with
        credentials that do not have a signature fails with L{ValidPublicKey}.
        N)r   Ú	signatureÚfailureResultOfrc   rŽ   r   r    r"   r"   r#   Ú test_credentialsWithoutSignature)  s    ÿz9SSHPublicKeyCheckerTests.test_credentialsWithoutSignaturec                 C   s$   d| j _|  | j | j ¡tj¡ dS )z–
        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with
        credentials that have a bad key fails with L{keys.BadKeyError}.
        r×   N)r   rp   r  rc   rŽ   r   r›   r    r"   r"   r#   Útest_credentialsWithBadKey3  s    ÿz3SSHPublicKeyCheckerTests.test_credentialsWithBadKeyc                 C   s$   t j| j_|  | j | j¡t¡ dS )zÙ
        If L{checkers.IAuthorizedKeysDB.getAuthorizedKeys} returns no keys
        that match the credentials,
        L{checkers.SSHPublicKeyChecker.requestAvatarId} fails with
        L{UnauthorizedLogin}.
        N)r   ZpublicDSA_opensshr   rp   r  rc   rŽ   r   r    r"   r"   r#   Útest_credentialsNoMatchingKey=  s    
ÿz6SSHPublicKeyCheckerTests.test_credentialsNoMatchingKeyc                 C   s2   t j tj¡ d¡| j_|  | j	 
| j¡t¡ dS )z§
        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with
        credentials that are incorrectly signed fails with
        L{UnauthorizedLogin}.
        r„   N)r   rŠ   r‹   r   r˜   r   r   r   r  rc   rŽ   r   r    r"   r"   r#   Ú test_credentialsInvalidSignatureI  s
    ÿÿz9SSHPublicKeyCheckerTests.test_credentialsInvalidSignaturec                 C   s<   dd„ }|   tjd|¡ |  | j | j¡t¡ |  t	¡ dS )z
        If L{keys.Key.verify} raises an exception,
        L{checkers.SSHPublicKeyChecker.requestAvatarId} fails with
        L{UnauthorizedLogin}.
        c                  _   s
   t ƒ ‚d S r   )rü   )ÚargsÚkwargsr"   r"   r#   Úfail[  s    z?SSHPublicKeyCheckerTests.test_failureVerifyingKey.<locals>.failZverifyN)
r:   r   rŠ   r  rc   rŽ   r   r   rš   rü   )r!   r  r"   r"   r#   Útest_failureVerifyingKeyU  s    ÿz1SSHPublicKeyCheckerTests.test_failureVerifyingKeyc                 C   s$   | j  | j¡}|  d|  |¡¡ dS )zu
        L{checker.SSHPublicKeyChecker.requestAvatarId}, if successful,
        callbacks with the username.
        rÀ   N)rc   rŽ   r   r;   ZsuccessResultOfrÅ   r"   r"   r#   Útest_usernameReturnedOnSuccesse  s    z7SSHPublicKeyCheckerTests.test_usernameReturnedOnSuccessN)rT   rU   rV   rW   rY   rZ   r$   r  r  r  r  r	  r
  r"   r"   r"   r#   rý     s   	

rý   )@rW   Z
__future__r   r   r'   ÚImportErrorrX   rL   Úcollectionsr   Úior   Zzope.interface.verifyr   Ztwisted.pythonr   Ztwisted.python.compatr   Ztwisted.python.failurer	   Ztwisted.python.reflectr
   Ztwisted.trial.unittestr   Ztwisted.python.filepathr   Ztwisted.cred.checkersr   Ztwisted.cred.credentialsr   r   r   r   Ztwisted.cred.errorr   r   Ztwisted.python.fakepwdr   r   Ztwisted.test.test_processr   rY   Ztwisted.conch.sshr   Ztwisted.conchr   Ztwisted.conch.errorr   r   Ztwisted.conch.testr   ÚgetattrrŸ   r   r[   r    r¯   rÛ   rê   rö   rÿ   Ú	Exceptionrü   rý   r"   r"   r"   r#   Ú<module>   sV   
i 6W 83%T