U
    H4frG                     @   s   d dl Z d dlZd dlmZ d dlmZ d dlmZ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 e eZG dd dZG dd dZG dd dZdS )    N)OrderedDict)etree)
exceptionsns)load_external)Settings)const)elements)types)builtins)SchemaVisitorc                   @   s:  e Zd ZdZd;ddZdd Zedd Zed	d
 Zedd Z	edd Z
edd Zedd Zejej eddddZeddddZejdddZd<ddZejddd Zejdd!d"Zejdd#d$Zd%d& Zd'd( Zd)d* Z d=d+d,Z!d-d. Z"d/d0 Z#d1d2 Z$d3d4 Z%d5d6 Z&d7d8 Z'd>d9d:Z(dS )?Schemaz-A schema is a collection of schema documents.Nc                 C   s`   |pt  | _|| _t | _i | _i | _|   t|t	sL|dk	rF|gng }n|}| 
|| dS )z
        :param node:
        :param transport:
        :param location:
        :param settings: The settings object

        N)r   settings
_transport_SchemaContainer	documents_prefix_map_auto_prefix_map_custom_load_default_documents
isinstancelistadd_documents)selfnode	transportlocationr   nodes r   3/tmp/pip-unpacked-wheel-04z2hmy8/zeep/xsd/schema.py__init__   s    
zSchema.__init__c                 C   s   | j }|rd|j|jf S dS )Nz<Schema(location=%r, tns=%r)>z
<Schema()>)root_document	_location_target_namespace)r   Zmain_docr   r   r   __repr__/   s    zSchema.__repr__c                    s2   i    | j    fdd| j D   S )Nc                    s"   i | ]\}}|   kr||qS r   values).0kvretvalr   r   
<dictcomp>=   s       z%Schema.prefix_map.<locals>.<dictcomp>)updater   r   itemsr   r   r)   r   
prefix_map8   s    zSchema.prefix_mapc                 C   s   t dd | jD d S )Nc                 s   s   | ]}|j s|V  qd S N)_is_internal)r&   docr   r   r   	<genexpr>C   s      z'Schema.root_document.<locals>.<genexpr>)nextr   r.   r   r   r   r    A   s    zSchema.root_documentc                 C   s   t dd | jD S )zABoolean to indicate if this schema contains any types or elementsc                 s   s   | ]}|j V  qd S r0   )is_empty)r&   documentr   r   r   r3   H   s     z"Schema.is_empty.<locals>.<genexpr>)allr   r.   r   r   r   r5   E   s    zSchema.is_emptyc                 C   s
   | j  S r0   )r   get_all_namespacesr.   r   r   r   
namespacesJ   s    zSchema.namespacesc                 c   sB   t  }| jD ]0}|j D ] }|j|kr|V  ||j qqdS )zYYield all globla xsd.Type objects

        :rtype: Iterable of zeep.xsd.Element

        N)setr   	_elementsr%   qnameadd)r   seenr6   elementr   r   r   r	   N   s    

zSchema.elementsc                 c   sB   t  }| jD ]0}|j D ] }|j|kr|V  ||j qqdS )z]Yield all global xsd.Type objects

        :rtype: Iterable of zeep.xsd.ComplexType

        N)r:   r   _typesr%   r<   r=   )r   r>   r6   type_r   r   r   r
   \   s    

zSchema.types)schema_nodesr   returnc                 C   sD   g }|D ]}|  ||}|| q|D ]}|  q(|  | _d S r0   )create_new_documentappendresolve_create_prefix_mapr   )r   rB   r   Zresolve_queuer   r6   r   r   r   r   j   s    
zSchema.add_documents)urlrC   c                 C   s,   t || j| jd}| j||d}|  d S )N)r   )rH   )r   r   r   rD   rF   )r   rH   Zschema_noder6   r   r   r   add_document_by_urlw   s    zSchema.add_document_by_urlrC   c                 C   s   |  |}| |ddS )z7Return a global xsd.Element object with the given qnameget_elementr?   )_create_qname_get_instancer   r<   r   r   r   rK   |   s    
zSchema.get_elementFc              
   C   sZ   |  |}z| |ddW S  tjk
rT } z|rBtt| n W 5 d}~X Y nX dS )zReturn a global xsd.Type object with the given qname

        :rtype: zeep.xsd.ComplexType or zeep.xsd.AnySimpleType


        get_typetypeN)rL   rM   r   NamespaceErrorloggerdebugstr)r   r<   fail_silentlyexcr   r   r   rO      s    
zSchema.get_typec                 C   s   |  |ddS )z6Return a global xsd.Group object with the given qname.	get_groupgrouprM   rN   r   r   r   rW      s    zSchema.get_groupc                 C   s   |  |ddS )z9Return a global xsd.attribute object with the given qnameget_attribute	attributerY   rN   r   r   r   rZ      s    zSchema.get_attributec                 C   s   |  |ddS )z>Return a global xsd.attributeGroup object with the given qnameget_attribute_groupattributeGrouprY   rN   r   r   r   r\      s    zSchema.get_attribute_groupc                 C   s   || j |< d S r0   )r   )r   prefix	namespacer   r   r   set_ns_prefix   s    zSchema.set_ns_prefixc                 C   sZ   z4z| j | W W S  tk
r0   | j|  Y W S X W n  tk
rT   td| Y nX d S )NzNo such prefix %r)r   KeyErrorr   
ValueError)r   r^   r   r   r   get_ns_prefix   s    zSchema.get_ns_prefixc                 C   sX   | j  D ]\}}||kr
|  S q
| j D ]\}}||kr.|  S q.|dkrTdS |S )Nz)http://schemas.xmlsoap.org/soap/envelope/zsoap-env)r   r-   r   )r   r_   r^   Zother_namespacer   r   r   get_shorthand_for_ns   s    

zSchema.get_shorthand_for_nsc                 C   sR   |dk	r| dnd}|s|}|dkr*|}t|||}| j| || | |S )z:

        :rtype: zeep.xsd.schema.SchemaDocument

        NZtargetNamespace)getSchemaDocumentr   r=   load)r   r   rH   base_urlZtarget_namespacer_   schemar   r   r   rD      s    zSchema.create_new_documentc                 C   s&   |j D ]}| j | q|  | _dS )z%Merge an other XSD schema in this oneN)r   r=   rG   r   )r   ri   r6   r   r   r   merge   s    
zSchema.mergec                 C   s   |  |j}|j|| dS )N)ri   )rK   tagparse)r   r   elmr   r   r   deserialize   s    zSchema.deserializec                 C   sh   t tjd d }tjD ]}|dd}||j| qtjD ]}| }|	|j
| q8d|_| j| |S )NT)	is_global)rf   r   ZXSDxsd_builtins_typesr@   register_typeZ_default_qnamexsd_builtins_elementsr;   register_elementr<   r1   r   r=   )r   ri   clsinstancer   r   r   r      s    


zSchema._load_default_documentsc                 C   s   |  |}zrd}| |jD ]P}t||}z||W   W S  tjk
rj } z|}W Y qW 5 d}~X Y qX q|dk	rz|W n. tjk
r   td||j|jf Y nX dS )z1Return an object from one of the SchemaDocument'sNzBUnable to resolve %s %s. No schema available for the namespace %r.)rL   _get_schema_documentsr_   getattrr   LookupErrorrQ   text)r   r<   method_namenameZlast_exceptionri   methodrV   r   r   r   rM      s$    

zSchema._get_instancec                 C   s   t |tjr|S |ds~d|kr~| jr~|dd\}}|| jkrTt| j| |S || jkrpt| j| |S td| n
t|S dS )zCreate an `lxml.etree.QName()` object for the given qname string.

        This also expands the shorthand notation.

        :rtype: lxml.etree.QNaame

        {:   z&No namespace defined for the prefix %rN)r   r   QName
startswithr   splitr   rb   )r   r{   r^   	localnamer   r   r   rL      s    

zSchema._create_qnamec                 C   sJ   ddi}d}| j  D ].}|d ks|| kr0q||d| < |d7 }q|S )NZxsdz http://www.w3.org/2001/XMLSchemar   zns%dr   )r   r8   r%   )r   r/   ir_   r   r   r   rG     s    
zSchema._create_prefix_mapc                 C   s:   | j |s,|tjkr,td| | | | j ||S )zlReturn a list of SchemaDocument's for the given namespace.

        :rtype: list of SchemaDocument

        z'Auto importing missing known schema: %s)r   has_schema_document_for_nsr   ZAUTO_IMPORT_NAMESPACESrR   rS   rI   get_by_namespacer   r_   rU   r   r   r   rv     s    

zSchema._get_schema_documents)NNNN)F)NN)F))__name__
__module____qualname____doc__r   r#   propertyr/   r    r5   r9   r	   r
   typingListr   Z_ElementrT   r   rI   xsd_elementsElementrK   rO   GrouprW   	AttributerZ   AttributeGroupr\   r`   rc   rd   rD   rj   rn   r   rM   rL   rG   rv   r   r   r   r   r      sH   
	






 
	
r   c                   @   s   e Zd ZdZdd Zdd Zdddd	d
Zeje	 dddZ
ejd dddZe	e	ejd dddZe	edddZdd ZdS )r   zUContainer instances to store multiple SchemaDocument objects per
    namespace.

    c                 C   s   t  | _d S r0   )r   
_instancesr.   r   r   r   r   .  s    z_SchemaContainer.__init__c                 c   s   |   D ]
}|V  qd S r0   r$   )r   r6   r   r   r   __iter__1  s    z_SchemaContainer.__iter__rf   N)r6   rC   c                 C   s2   t d|jt|  | j|jg }|| dS )zAdd a schema documentz%Add document with tns %s to schema %sN)rR   rS   r_   idr   
setdefaultrE   )r   r6   r   r   r   r   r=   5  s      z_SchemaContainer.addrJ   c                 C   s   t | j S r0   )r   r   keysr.   r   r   r   r8   =  s    z#_SchemaContainer.get_all_namespacesc                 C   s*   || j kr |rg S td| | j | S )Nz(No schema available for the namespace %r)r   r   rQ   r   r   r   r   r   @  s    
z!_SchemaContainer.get_by_namespace)r_   r   rC   c                 C   s.   | j |dd}|D ]}|j|kr|  S qdS )z<Return a SchemaDocument for the given namespace AND locationT)rU   N)r   r!   )r   r_   r   r   r6   r   r   r   get_by_namespace_and_locationK  s
    

z._SchemaContainer.get_by_namespace_and_location)r_   rC   c                 C   s
   || j kS )zcReturn a boolean if there is a SchemaDocument for the namespace.

        :rtype: boolean

        )r   r   r_   r   r   r   r   U  s    z+_SchemaContainer.has_schema_document_for_nsc                 c   s$   | j  D ]}|D ]
}|V  qq
d S r0   )r   r%   )r   r   r6   r   r   r   r%   ]  s    z_SchemaContainer.values)r   r   r   r   r   r   r=   r   r   rT   r8   r   Optionalr   boolr   r%   r   r   r   r   r   (  s    
r   c                   @   s  e Zd ZdZdd Zdd Zedd Zedd	 Zd
d Z	dd Z
dd Zdd ZejejdddZejejdddZejejdddZeejdddZejejddddZejdd d!Zejd"d#d$Zejd"d%d&Zejd"d'd(Zejd"d)d*Z d+d, Z!d-d. Z"dS )/rf   zA Schema Document consists of a set of schema components for a
    specific target namespace.

    This represents an xsd:Schema object

    c                 C   sj   t d| |p|| _|| _|| _d| _d| _i | _i | _i | _	i | _
i | _t | _d| _d| _d| _d S )NzInit schema document for %rFZunqualified)rR   rS   Z	_base_urlr!   r"   r1   Z_has_empty_import_attribute_groups_attributesr;   _groupsr@   r   _importsZ_element_formZ_attribute_form	_resolved)r   r_   r   rh   r   r   r   r   k  s    
zSchemaDocument.__init__c                 C   s   d| j | j| jf S )Nz2<SchemaDocument(location=%r, tns=%r, is_empty=%r)>)r!   r"   r5   r.   r   r   r   r#     s
    zSchemaDocument.__repr__c                 C   s   | j S r0   )r"   r.   r   r   r   r_     s    zSchemaDocument.namespacec                 C   s   t | jp| jp| j S r0   )r   r   r@   r;   r.   r   r   r   r5     s    zSchemaDocument.is_emptyc                 C   s:   |dkrdS |j | js"tdt|| }|| dS )zLoad the XML Schema passed in via the node attribute.

        :type schema: zeep.xsd.schema.Schema
        :type node: etree._Element

        NzIThe document needs to be registered in the schema before it can be loaded)r   r   r"   RuntimeErrorr   Zvisit_schema)r   ri   r   Zvisitorr   r   r   rg     s    
zSchemaDocument.loadc                 C   s|   t d|  | jrd S d| _| j D ]}|D ]}|  q.q&dd }|| j || j || j || j	 || j
 d S )NzResolving in schema %sTc                 S   s   z6|   D ](\}}| }|d k	s*td|| |< q
W nD tjk
rz } z$td|j|j|j|jd W 5 d }~X Y nX d S )Nz!resolve() should return an objectzGUnable to resolve %(item_name)s %(qname)s in %(file)s. (via %(parent)s))	item_namer<   fileparent)r-   rF   AssertionErrorr   rx   r   r<   r   )valkeyobjnewrV   r   r   r   _resolve_dict  s    z-SchemaDocument.resolve.<locals>._resolve_dict)rR   rS   r   r   r%   rF   r   r   r;   r   r@   )r   schemasri   r   r   r   r   rF     s    



zSchemaDocument.resolvec                 C   s   | j |g }|| dS )zRegister an import for an other schema document.

        :type namespace: str
        :type schema: zeep.xsd.schema.SchemaDocument

        N)r   r   rE   )r   r_   ri   r   r   r   r   register_import  s    zSchemaDocument.register_importc                 C   s
   || j kS r0   )r   r   r   r   r   is_imported  s    zSchemaDocument.is_imported)r<   valuec                 C   s   |  ||| jd dS )z"Register a xsd.Type in this schemarP   N)_add_componentr@   r   r<   r   r   r   r   rq     s    zSchemaDocument.register_typec                 C   s   |  ||| jd dS )z%Register a xsd.Element in this schemar?   N)r   r;   r   r   r   r   rs     s    zSchemaDocument.register_elementc                 C   s   |  ||| jd dS )z#Register a xsd:Group in this schemarX   N)r   r   r   r   r   r   register_group  s    zSchemaDocument.register_groupc                 C   s   |  ||| jd dS )z'Register a xsd:Attribute in this schemar[   N)r   r   r   r   r   r   register_attribute  s    z!SchemaDocument.register_attributeN)r<   r   rC   c                 C   s   |  ||| jd dS )z,Register a xsd:AttributeGroup in this schemaZattribute_groupN)r   r   r   r   r   r   register_attribute_group  s    z'SchemaDocument.register_attribute_group)r<   c                 C   s   |  || jdS )zsReturn a xsd.Type object from this schema

        :rtype: zeep.xsd.ComplexType or zeep.xsd.AnySimpleType

        rP   )_get_componentr@   rN   r   r   r   rO     s    zSchemaDocument.get_typerJ   c                 C   s   |  || jdS )z,Return a xsd.Element object from this schemar?   )r   r;   rN   r   r   r   rK     s    zSchemaDocument.get_elementc                 C   s   |  || jdS )z*Return a xsd.Group object from this schemarX   )r   r   rN   r   r   r   rW     s    zSchemaDocument.get_groupc                 C   s   |  || jdS )z.Return a xsd.Attribute object from this schemar[   )r   r   rN   r   r   r   rZ     s    zSchemaDocument.get_attributec                 C   s   |  || jdS )z3Return a xsd.AttributeGroup object from this schemar]   )r   r   rN   r   r   r   r\     s    z"SchemaDocument.get_attribute_groupc                 C   s.   t |tjr|j}td||| |||< d S )Nzregister_%s(%r, %r))r   r   r   ry   rR   rS   )r   r{   r   r-   r   r   r   r   r     s    zSchemaDocument._add_componentc                 C   sb   z
|| W S  t k
r\   d| }tjd||d |j|j|pDdd ||| jdY nX d S )Nz, zpNo %(item_name)s '%(localname)s' in namespace %(namespace)s. Available %(item_name_plural)s are: %(known_items)ssz - )r   Zitem_name_pluralr   r_   known_items)r<   r   r   )ra   joinr   r   rx   r   r_   r!   )r   r<   r-   r   r   r   r   r   r     s"    
zSchemaDocument._get_component)#r   r   r   r   r   r#   r   r_   r5   rg   rF   r   r   r   r   	xsd_typesTyperq   r   r   rs   r   r   rT   r   r   r   r   rO   rK   rW   rZ   r\   r   r   r   r   r   r   rf   c  s4   

%
 rf   ) loggingr   collectionsr   lxmlr   Zzeepr   r   Zzeep.loaderr   Zzeep.settingsr   Zzeep.xsdr   r	   r   r
   r   Zzeep.xsd.elementsr   rr   Zzeep.xsd.typesrp   Zzeep.xsd.visitorr   	getLoggerr   rR   r   r   rf   r   r   r   r   <module>   s$   
  ;