a
    /$Z|(                     @   s   d Z ddlmZ ddlZejdkr*e ZZddlZddl	m
Z
 ddlZddlZddlZddlZddlmZmZmZmZ ddlmZ ddlZddlZdd	lmZ d
d ZdZdZdZdZdZdZG dd dZ G dd de Z!dZ"G dd dZ#dS )zFPythonic simple SOAP Client plugins for WebService Security extensions    )unicode_literalsN3)Decimal   )
__author____copyright____license____version__)SimpleXMLElement)sha1c                 C   s   d dd t| D S )N c                 s   s$   | ]}t  tjtj V  qd S N)randomZSystemRandomZchoicestringZascii_uppercaseZdigits).0_ r   3/usr/lib/python3/dist-packages/pysimplesoap/wsse.py	<genexpr>$       zrandombytes.<locals>.<genexpr>)joinrange)Nr   r   r   randombytes#   s    r   zQhttp://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsdzRhttp://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsdz"http://www.w3.org/2000/09/xmldsig#zUhttp://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile-1.0#X509v3z^http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binaryzahttp://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-username-token-profile-1.0#PasswordDigestc                   @   s*   e Zd ZdZd
ddZdd Zdd Zd	S )UsernameTokenzGWebService Security extension to add a basic credentials to xml requestr   c                 C   s   d||di| _ d S )Nwsse:UsernameToken)wsse:Usernamewsse:Password)token)selfusernamepasswordr   r   r   __init__3   s
    zUsernameToken.__init__c           
      C   sF   |d|d}d}	|	|v r"||	 | _ |j|	| j ddd t||	d< dS )z)Add basic credentials to outgoing messageHeadernswsse:SecurityF)r%   Zadd_children_ns
xmlns:wsseN)r   ZmarshallWSSE_URI)
r   clientrequestmethodargskwargsheaderssoap_uriheaderkr   r   r   
preprocess;   s    
zUsernameToken.preprocessc                 C   s   dS )zAnalyze incoming credentialsNr   )r   r)   responser+   r,   r-   r.   r/   r   r   r   postprocessH   s    zUsernameToken.postprocessN)r   r   )__name__
__module____qualname____doc__r"   r2   r4   r   r   r   r   r   0   s   
r   c                   @   s"   e Zd ZdZd	ddZdd ZdS )
UsernameDigestTokenz
    WebService Security extension to add a http digest credentials to xml request
    drift -> time difference from the server in seconds, needed for 'Created' header
    r   r   c                 C   s   || _ || _tj|d| _d S )N)Zseconds)r    r!   datetimeZ	timedeltadrift)r   r    r!   r;   r   r   r   r"   S   s    zUsernameDigestToken.__init__c                 C   s   |d|d}|j ddd}	t|	d< t|	d< |	j ddd}
|
j d| jdd tj | j  d	 }|
j d
|dd td}|
j d|	dd d dd}t
|d< t }||| | j  | }|
j d|	dd d dd}t|d< d S )Nr#   r$   r&   Fr'   	xmlns:wsur   r   Zzwsu:Created   z
wsse:Noncebase64EncodingTyper   Type)Z	add_childr(   WSU_URIr    r:   Zutcnowr;   Z	isoformatr   encodeBase64Binary_URIr   updater!   digestPasswordDigest_URI)r   r)   r*   r+   r,   r-   r.   r/   r0   wsseZ	usertokenZcreatedZnonceZ	wssenonceZsha1objrG   r!   r   r   r   r2   X   s     zUsernameDigestToken.preprocessN)r   r   r   )r5   r6   r7   r8   r"   r2   r   r   r   r   r9   M   s   
r9   aZ  <?xml version="1.0" encoding="UTF-8"?>
<wsse:Security soapenv:mustUnderstand="1" xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
    <wsse:BinarySecurityToken EncodingType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary" ValueType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile-1.0#X509v3" wsu:Id="CertId-45851B081998E431E8132880700036719" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd">
%(certificate)s</wsse:BinarySecurityToken>
    <ds:Signature Id="Signature-13" xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
        %(signed_info)s
        <ds:SignatureValue>%(signature_value)s</ds:SignatureValue>
        <ds:KeyInfo Id="KeyId-45851B081998E431E8132880700036720">
            <wsse:SecurityTokenReference wsu:Id="STRId-45851B081998E431E8132880700036821" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd">
                <wsse:Reference URI="#CertId-45851B081998E431E8132880700036719" ValueType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile-1.0#X509v3"/>
            </wsse:SecurityTokenReference>
        </ds:KeyInfo>
    </ds:Signature>
</wsse:Security>
c                   @   s4   e Zd ZdZdddZdd Zdd	 ZdddZdS )BinaryTokenSignaturezEWebService Security extension to add a basic signature to xml requestr   Nc                 C   s0   d dd t|D | _|| _|| _|| _d S )Nr   c                 S   s   g | ]}| d s|qS )z---)
startswith)r   liner   r   r   
<listcomp>   s   
z1BinaryTokenSignature.__init__.<locals>.<listcomp>)r   opencertificateprivate_keyr!   cacert)r   rO   rP   r!   rQ   r   r   r   r"      s    zBinaryTokenSignature.__init__c                 C   s   |d|d}|d|d}	d|d< t |d< |dd D ]\}
}|
dr4|||
< q4t|}d	d
lm} ||d| j| j}| j|d< t	t
| }|	| dS )zSign the outgoing SOAP requestBodyr$   r#   zid-14wsu:Idr<   Nxmlnsr   xmlsecz#id-14rO   )rC   rK   reprr   rV   Zrsa_signrP   r!   rO   r
   BIN_TOKEN_TMPLZimport_node)r   r)   r*   r+   r,   r-   r.   r/   bodyr0   attrvalueref_xmlrV   varsrI   r   r   r   r2      s    


zBinaryTokenSignature.preprocessc                 C   s  ddl m} |d|d}	|d|d}
|
dtd}|dtd}| |d t | |d	 t t|d
}|j|dd}| j	st
d n|j| j	|ddstd| |	d t |	d }|dtd}|dtd}|dtd}| |dtdd d|  | |dtdd td  | |dtddtdd td  |dd D ]\}}|drH||	|< qH|t|	}||}t|dtddtd}||krtdt|d< t|}||t||}|std dS )!z-Verify the signature of the incoming responser   rU   rR   r$   r#   ZSecurityZBinarySecurityTokenrA   Z	ValueTyper?   T)Zbinaryz/No CA provided, WSSE not validating certificatez"WSSE certificate validation failedr<   rS   Z	SignatureZ
SignedInfoZSignatureValueZ	ReferenceZURI#ZSignatureMethodZ	Algorithmzrsa-sha1ZDigestMethodr   NrT   ZDigestValuezWSSE SHA1 hash digests mismatchz+WSSE RSA-SHA1 signature verification failed)r   rV   r(   _BinaryTokenSignature__checkrE   
X509v3_URIstrdecodeZx509_extract_rsa_public_keyrQ   warningswarnZx509_verifyRuntimeErrorrC   XMLDSIG_URIrK   ZcanonicalizerW   Zsha1_hash_digestZ
rsa_verify)r   r)   r3   r+   r,   r-   r.   r/   rV   rY   r0   rI   ZcertZcert_derZ
public_keyZref_uriZ	signatureZsigned_infoZsignature_valuerZ   r[   r\   Zcomputed_hashZdigest_valueZxmlokr   r   r   r4      sL    

z BinaryTokenSignature.postprocessWSSE sanity check failedc                 C   s   ||krt |d S r   )re   )r   r[   Zexpectedmsgr   r   r   Z__check   s    zBinaryTokenSignature.__check)r   r   NN)rh   )r5   r6   r7   r8   r"   r2   r4   r_   r   r   r   r   rJ      s
   
4rJ   )$r8   Z
__future__r   sysversionra   Z
basestringZunicoder:   Zdecimalr   osZloggingZhashlibrc   r   r   r   r   r	   Z	simplexmlr
   r   r   r   r   r(   rC   rf   r`   rE   rH   r   r9   rX   rJ   r   r   r   r   <module>   s4   
"