Merging upstream version 2.5.0.
This commit is contained in:
parent
039b5b30b2
commit
af618ce5e3
12
CHANGES
12
CHANGES
|
@ -1,3 +1,15 @@
|
||||||
|
2.5.0 (2018-01-06)
|
||||||
|
------------------
|
||||||
|
- Fix AnyType value rendering by guessing the xsd type for the value (#552)
|
||||||
|
- Fix AnySimpleType.xmlvalue() not implemented exception (#644)
|
||||||
|
- Add __dir__ method to value objects returned by Zeep
|
||||||
|
- Don't require content for 201 and 202 status codes (#613)
|
||||||
|
- Fix wheel package by cleaning the build directory correctly (#634)
|
||||||
|
- Handle Nil values on complexType with SimpleContent elements (#604)
|
||||||
|
- Add Client.namespaces method to list all namespaces available
|
||||||
|
- Improve support for auto-completion (#537)
|
||||||
|
|
||||||
|
|
||||||
2.4.0 (2017-08-26)
|
2.4.0 (2017-08-26)
|
||||||
------------------
|
------------------
|
||||||
- Add support for tornado async transport via gen.coroutine (#530, Kateryna Burda)
|
- Add support for tornado async transport via gen.coroutine (#530, Kateryna Burda)
|
||||||
|
|
2
PKG-INFO
2
PKG-INFO
|
@ -1,6 +1,6 @@
|
||||||
Metadata-Version: 1.1
|
Metadata-Version: 1.1
|
||||||
Name: zeep
|
Name: zeep
|
||||||
Version: 2.4.0
|
Version: 2.5.0
|
||||||
Summary: A modern/fast Python SOAP client based on lxml / requests
|
Summary: A modern/fast Python SOAP client based on lxml / requests
|
||||||
Home-page: http://docs.python-zeep.org
|
Home-page: http://docs.python-zeep.org
|
||||||
Author: Michael van Tellingen
|
Author: Michael van Tellingen
|
||||||
|
|
|
@ -4,4 +4,4 @@ import zeep
|
||||||
|
|
||||||
client = zeep.Client(
|
client = zeep.Client(
|
||||||
wsdl='http://ec.europa.eu/taxation_customs/vies/checkVatService.wsdl')
|
wsdl='http://ec.europa.eu/taxation_customs/vies/checkVatService.wsdl')
|
||||||
print(client.service.checkVat('NL', '170944128B01'))
|
print(client.service.checkVat('NL', '123456789B01'))
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
[bumpversion]
|
[bumpversion]
|
||||||
current_version = 2.4.0
|
current_version = 2.5.0
|
||||||
commit = true
|
commit = true
|
||||||
tag = true
|
tag = true
|
||||||
tag_name = {new_version}
|
tag_name = {new_version}
|
||||||
|
|
5
setup.py
5
setup.py
|
@ -39,7 +39,7 @@ tests_require = [
|
||||||
'pytest-tornado==0.4.5',
|
'pytest-tornado==0.4.5',
|
||||||
|
|
||||||
# Linting
|
# Linting
|
||||||
'isort==4.2.5',
|
'isort==4.2.15',
|
||||||
'flake8==3.3.0',
|
'flake8==3.3.0',
|
||||||
'flake8-blind-except==0.1.1',
|
'flake8-blind-except==0.1.1',
|
||||||
'flake8-debugger==1.4.0',
|
'flake8-debugger==1.4.0',
|
||||||
|
@ -58,7 +58,7 @@ with open('README.rst') as fh:
|
||||||
|
|
||||||
setup(
|
setup(
|
||||||
name='zeep',
|
name='zeep',
|
||||||
version='2.4.0',
|
version='2.5.0',
|
||||||
description='A modern/fast Python SOAP client based on lxml / requests',
|
description='A modern/fast Python SOAP client based on lxml / requests',
|
||||||
long_description=long_description,
|
long_description=long_description,
|
||||||
author="Michael van Tellingen",
|
author="Michael van Tellingen",
|
||||||
|
@ -78,7 +78,6 @@ setup(
|
||||||
package_dir={'': 'src'},
|
package_dir={'': 'src'},
|
||||||
packages=['zeep'],
|
packages=['zeep'],
|
||||||
include_package_data=True,
|
include_package_data=True,
|
||||||
|
|
||||||
license='MIT',
|
license='MIT',
|
||||||
classifiers=[
|
classifiers=[
|
||||||
'Development Status :: 5 - Production/Stable',
|
'Development Status :: 5 - Production/Stable',
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
Metadata-Version: 1.1
|
Metadata-Version: 1.1
|
||||||
Name: zeep
|
Name: zeep
|
||||||
Version: 2.4.0
|
Version: 2.5.0
|
||||||
Summary: A modern/fast Python SOAP client based on lxml / requests
|
Summary: A modern/fast Python SOAP client based on lxml / requests
|
||||||
Home-page: http://docs.python-zeep.org
|
Home-page: http://docs.python-zeep.org
|
||||||
Author: Michael van Tellingen
|
Author: Michael van Tellingen
|
||||||
|
|
|
@ -28,7 +28,6 @@ src/zeep.egg-info/PKG-INFO
|
||||||
src/zeep.egg-info/SOURCES.txt
|
src/zeep.egg-info/SOURCES.txt
|
||||||
src/zeep.egg-info/dependency_links.txt
|
src/zeep.egg-info/dependency_links.txt
|
||||||
src/zeep.egg-info/not-zip-safe
|
src/zeep.egg-info/not-zip-safe
|
||||||
src/zeep.egg-info/pbr.json
|
|
||||||
src/zeep.egg-info/requires.txt
|
src/zeep.egg-info/requires.txt
|
||||||
src/zeep.egg-info/top_level.txt
|
src/zeep.egg-info/top_level.txt
|
||||||
src/zeep/asyncio/__init__.py
|
src/zeep/asyncio/__init__.py
|
||||||
|
|
|
@ -1 +0,0 @@
|
||||||
{"is_release": false, "git_version": "70e9199"}
|
|
|
@ -22,7 +22,7 @@ pytest-cov==2.5.1
|
||||||
pytest==3.1.3
|
pytest==3.1.3
|
||||||
requests_mock>=0.7.0
|
requests_mock>=0.7.0
|
||||||
pytest-tornado==0.4.5
|
pytest-tornado==0.4.5
|
||||||
isort==4.2.5
|
isort==4.2.15
|
||||||
flake8==3.3.0
|
flake8==3.3.0
|
||||||
flake8-blind-except==0.1.1
|
flake8-blind-except==0.1.1
|
||||||
flake8-debugger==1.4.0
|
flake8-debugger==1.4.0
|
||||||
|
|
|
@ -3,4 +3,4 @@ from zeep.transports import Transport # noqa
|
||||||
from zeep.plugins import Plugin # noqa
|
from zeep.plugins import Plugin # noqa
|
||||||
from zeep.xsd.valueobjects import AnyObject # noqa
|
from zeep.xsd.valueobjects import AnyObject # noqa
|
||||||
|
|
||||||
__version__ = '2.4.0'
|
__version__ = '2.5.0'
|
||||||
|
|
|
@ -4,11 +4,11 @@ Adds asyncio support to Zeep. Contains Python 3.5+ only syntax!
|
||||||
"""
|
"""
|
||||||
import asyncio
|
import asyncio
|
||||||
import logging
|
import logging
|
||||||
from . import bindings
|
|
||||||
|
|
||||||
import aiohttp
|
import aiohttp
|
||||||
from requests import Response
|
from requests import Response
|
||||||
|
|
||||||
|
from zeep.asyncio import bindings
|
||||||
from zeep.exceptions import TransportError
|
from zeep.exceptions import TransportError
|
||||||
from zeep.transports import Transport
|
from zeep.transports import Transport
|
||||||
from zeep.utils import get_version
|
from zeep.utils import get_version
|
||||||
|
|
|
@ -14,6 +14,10 @@ class OperationProxy(object):
|
||||||
self._proxy = service_proxy
|
self._proxy = service_proxy
|
||||||
self._op_name = operation_name
|
self._op_name = operation_name
|
||||||
|
|
||||||
|
@property
|
||||||
|
def __doc__(self):
|
||||||
|
return str(self._proxy._binding._operations[self._op_name])
|
||||||
|
|
||||||
def __call__(self, *args, **kwargs):
|
def __call__(self, *args, **kwargs):
|
||||||
"""Call the operation with the given args and kwargs.
|
"""Call the operation with the given args and kwargs.
|
||||||
|
|
||||||
|
@ -67,6 +71,13 @@ class ServiceProxy(object):
|
||||||
raise AttributeError('Service has no operation %r' % key)
|
raise AttributeError('Service has no operation %r' % key)
|
||||||
return OperationProxy(self, key)
|
return OperationProxy(self, key)
|
||||||
|
|
||||||
|
def __dir__(self):
|
||||||
|
""" Return the names of the operations. """
|
||||||
|
return list(dir(super(ServiceProxy, self))
|
||||||
|
+ list(self.__dict__)
|
||||||
|
+ list(self._binding.port_type.operations))
|
||||||
|
# using list() on the dicts for Python 3 compatibility
|
||||||
|
|
||||||
|
|
||||||
class Factory(object):
|
class Factory(object):
|
||||||
def __init__(self, types, kind, namespace):
|
def __init__(self, types, kind, namespace):
|
||||||
|
@ -133,6 +144,10 @@ class Client(object):
|
||||||
self._default_port_name = port_name
|
self._default_port_name = port_name
|
||||||
self._default_soapheaders = None
|
self._default_soapheaders = None
|
||||||
|
|
||||||
|
@property
|
||||||
|
def namespaces(self):
|
||||||
|
return self.wsdl.types.prefix_map
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def service(self):
|
def service(self):
|
||||||
"""The default ServiceProxy instance
|
"""The default ServiceProxy instance
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from zeep.wsdl import bindings
|
|
||||||
from tornado import gen
|
from tornado import gen
|
||||||
|
|
||||||
|
from zeep.wsdl import bindings
|
||||||
|
|
||||||
__all__ = ['AsyncSoap11Binding', 'AsyncSoap12Binding']
|
__all__ = ['AsyncSoap11Binding', 'AsyncSoap12Binding']
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -4,12 +4,12 @@ Adds async tornado.gen support to Zeep.
|
||||||
"""
|
"""
|
||||||
import logging
|
import logging
|
||||||
import urllib
|
import urllib
|
||||||
from . import bindings
|
|
||||||
|
|
||||||
from tornado import gen, httpclient
|
|
||||||
from requests import Response, Session
|
from requests import Response, Session
|
||||||
from requests.auth import HTTPBasicAuth, HTTPDigestAuth
|
from requests.auth import HTTPBasicAuth, HTTPDigestAuth
|
||||||
|
from tornado import gen, httpclient
|
||||||
|
|
||||||
|
from zeep.tornado import bindings
|
||||||
from zeep.transports import Transport
|
from zeep.transports import Transport
|
||||||
from zeep.utils import get_version
|
from zeep.utils import get_version
|
||||||
from zeep.wsdl.utils import etree_to_string
|
from zeep.wsdl.utils import etree_to_string
|
||||||
|
@ -89,7 +89,7 @@ class TornadoAsyncTransport(Transport):
|
||||||
auth_password = self.session.password
|
auth_password = self.session.password
|
||||||
auth_mode = 'digest'
|
auth_mode = 'digest'
|
||||||
else:
|
else:
|
||||||
raise StandardError('Not supported authentication.')
|
raise Exception('Not supported authentication.')
|
||||||
|
|
||||||
# extracting client cert
|
# extracting client cert
|
||||||
client_cert = None
|
client_cert = None
|
||||||
|
@ -111,7 +111,8 @@ class TornadoAsyncTransport(Transport):
|
||||||
'auth_username': auth_username,
|
'auth_username': auth_username,
|
||||||
'auth_password': auth_password,
|
'auth_password': auth_password,
|
||||||
'auth_mode': auth_mode,
|
'auth_mode': auth_mode,
|
||||||
'validate_cert': self.session.verify,
|
'validate_cert': self.session.verify is not None,
|
||||||
|
'ca_certs': self.session.verify,
|
||||||
'client_key': client_key,
|
'client_key': client_key,
|
||||||
'client_cert': client_cert
|
'client_cert': client_cert
|
||||||
}
|
}
|
||||||
|
@ -130,4 +131,4 @@ class TornadoAsyncTransport(Transport):
|
||||||
new._content = response.body
|
new._content = response.body
|
||||||
new.status_code = response.code
|
new.status_code = response.code
|
||||||
new.headers = dict(response.headers.get_all())
|
new.headers = dict(response.headers.get_all())
|
||||||
return new
|
return new
|
||||||
|
|
|
@ -131,7 +131,10 @@ class SoapBinding(Binding):
|
||||||
:type response: requests.Response
|
:type response: requests.Response
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if response.status_code != 200 and not response.content:
|
if response.status_code in (201, 202) and not response.content:
|
||||||
|
return None
|
||||||
|
|
||||||
|
elif response.status_code != 200 and not response.content:
|
||||||
raise TransportError(
|
raise TransportError(
|
||||||
u'Server returned HTTP status %d (no content available)'
|
u'Server returned HTTP status %d (no content available)'
|
||||||
% response.status_code,
|
% response.status_code,
|
||||||
|
|
|
@ -255,8 +255,14 @@ class Definition(object):
|
||||||
for import_node in doc.findall("wsdl:import", namespaces=NSMAP):
|
for import_node in doc.findall("wsdl:import", namespaces=NSMAP):
|
||||||
namespace = import_node.get('namespace')
|
namespace = import_node.get('namespace')
|
||||||
location = import_node.get('location')
|
location = import_node.get('location')
|
||||||
location = absolute_location(location, self.location)
|
|
||||||
|
|
||||||
|
if not location:
|
||||||
|
logger.debug(
|
||||||
|
"Skipping import for namespace %s (empty location)",
|
||||||
|
namespace)
|
||||||
|
continue
|
||||||
|
|
||||||
|
location = absolute_location(location, self.location)
|
||||||
key = (namespace, location)
|
key = (namespace, location)
|
||||||
if key in self.wsdl._definitions:
|
if key in self.wsdl._definitions:
|
||||||
self.imports[key] = self.wsdl._definitions[key]
|
self.imports[key] = self.wsdl._definitions[key]
|
||||||
|
|
|
@ -55,7 +55,7 @@ class Any(Base):
|
||||||
qname = etree.QName(xmlelement.tag)
|
qname = etree.QName(xmlelement.tag)
|
||||||
if context and context.schemas:
|
if context and context.schemas:
|
||||||
for context_schema in context.schemas:
|
for context_schema in context.schemas:
|
||||||
if context_schema._has_schema_document(qname.namespace):
|
if context_schema.documents.has_schema_document_for_ns(qname.namespace):
|
||||||
schema = context_schema
|
schema = context_schema
|
||||||
break
|
break
|
||||||
|
|
||||||
|
|
|
@ -225,7 +225,7 @@ class Element(Base):
|
||||||
path=render_path)
|
path=render_path)
|
||||||
elif self.max_occurs != 'unbounded' and len(value) > self.max_occurs:
|
elif self.max_occurs != 'unbounded' and len(value) > self.max_occurs:
|
||||||
raise exceptions.ValidationError(
|
raise exceptions.ValidationError(
|
||||||
"Expected at most %d items (maxOccurs check)" % self.min_occurs,
|
"Expected at most %d items (maxOccurs check)" % self.max_occurs,
|
||||||
path=render_path)
|
path=render_path)
|
||||||
|
|
||||||
for val in value:
|
for val in value:
|
||||||
|
|
|
@ -28,7 +28,7 @@ class Schema(object):
|
||||||
|
|
||||||
self._transport = transport
|
self._transport = transport
|
||||||
|
|
||||||
self._documents = OrderedDict()
|
self.documents = _SchemaContainer()
|
||||||
self._prefix_map_auto = {}
|
self._prefix_map_auto = {}
|
||||||
self._prefix_map_custom = {}
|
self._prefix_map_custom = {}
|
||||||
|
|
||||||
|
@ -40,11 +40,12 @@ class Schema(object):
|
||||||
nodes = node
|
nodes = node
|
||||||
self.add_documents(nodes, location)
|
self.add_documents(nodes, location)
|
||||||
|
|
||||||
@property
|
def __repr__(self):
|
||||||
def documents(self):
|
main_doc = self.root_document
|
||||||
for documents in self._documents.values():
|
if main_doc:
|
||||||
for document in documents:
|
return '<Schema(location=%r, tns=%r)>' % (
|
||||||
yield document
|
main_doc._location, main_doc._target_namespace)
|
||||||
|
return '<Schema()>'
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def prefix_map(self):
|
def prefix_map(self):
|
||||||
|
@ -69,7 +70,7 @@ class Schema(object):
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def namespaces(self):
|
def namespaces(self):
|
||||||
return set(self._documents.keys())
|
return self.documents.get_all_namespaces()
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def elements(self):
|
def elements(self):
|
||||||
|
@ -99,20 +100,13 @@ class Schema(object):
|
||||||
yield type_
|
yield type_
|
||||||
seen.add(type_.qname)
|
seen.add(type_.qname)
|
||||||
|
|
||||||
def __repr__(self):
|
|
||||||
main_doc = self.root_document
|
|
||||||
if main_doc:
|
|
||||||
return '<Schema(location=%r, tns=%r)>' % (
|
|
||||||
main_doc._location, main_doc._target_namespace)
|
|
||||||
return '<Schema()>'
|
|
||||||
|
|
||||||
def add_documents(self, schema_nodes, location):
|
def add_documents(self, schema_nodes, location):
|
||||||
documents = []
|
resolve_queue = []
|
||||||
for node in schema_nodes:
|
for node in schema_nodes:
|
||||||
document = self.create_new_document(node, location)
|
document = self.create_new_document(node, location)
|
||||||
documents.append(document)
|
resolve_queue.append(document)
|
||||||
|
|
||||||
for document in documents:
|
for document in resolve_queue:
|
||||||
document.resolve()
|
document.resolve()
|
||||||
|
|
||||||
self._prefix_map_auto = self._create_prefix_map()
|
self._prefix_map_auto = self._create_prefix_map()
|
||||||
|
@ -199,19 +193,24 @@ class Schema(object):
|
||||||
return namespace
|
return namespace
|
||||||
|
|
||||||
def create_new_document(self, node, url, base_url=None):
|
def create_new_document(self, node, url, base_url=None):
|
||||||
|
"""
|
||||||
|
|
||||||
|
:rtype: zeep.xsd.schema.SchemaDocument
|
||||||
|
|
||||||
|
"""
|
||||||
namespace = node.get('targetNamespace') if node is not None else None
|
namespace = node.get('targetNamespace') if node is not None else None
|
||||||
if base_url is None:
|
if base_url is None:
|
||||||
base_url = url
|
base_url = url
|
||||||
|
|
||||||
schema = SchemaDocument(namespace, url, base_url)
|
schema = SchemaDocument(namespace, url, base_url)
|
||||||
self._add_schema_document(schema)
|
self.documents.add(schema)
|
||||||
schema.load(self, node)
|
schema.load(self, node)
|
||||||
return schema
|
return schema
|
||||||
|
|
||||||
def merge(self, schema):
|
def merge(self, schema):
|
||||||
"""Merge an other XSD schema in this one"""
|
"""Merge an other XSD schema in this one"""
|
||||||
for document in schema.documents:
|
for document in schema.documents:
|
||||||
self._add_schema_document(document)
|
self.documents.add(document)
|
||||||
self._prefix_map_auto = self._create_prefix_map()
|
self._prefix_map_auto = self._create_prefix_map()
|
||||||
|
|
||||||
def _load_default_documents(self):
|
def _load_default_documents(self):
|
||||||
|
@ -226,7 +225,7 @@ class Schema(object):
|
||||||
schema.register_element(cls.qname, instance)
|
schema.register_element(cls.qname, instance)
|
||||||
|
|
||||||
schema._is_internal = True
|
schema._is_internal = True
|
||||||
self._add_schema_document(schema)
|
self.documents.add(schema)
|
||||||
return schema
|
return schema
|
||||||
|
|
||||||
def _get_instance(self, qname, method_name, name):
|
def _get_instance(self, qname, method_name, name):
|
||||||
|
@ -277,7 +276,7 @@ class Schema(object):
|
||||||
'xsd': 'http://www.w3.org/2001/XMLSchema',
|
'xsd': 'http://www.w3.org/2001/XMLSchema',
|
||||||
}
|
}
|
||||||
i = 0
|
i = 0
|
||||||
for namespace in self._documents.keys():
|
for namespace in self.documents.get_all_namespaces():
|
||||||
if namespace is None or namespace in prefix_map.values():
|
if namespace is None or namespace in prefix_map.values():
|
||||||
continue
|
continue
|
||||||
|
|
||||||
|
@ -285,30 +284,6 @@ class Schema(object):
|
||||||
i += 1
|
i += 1
|
||||||
return prefix_map
|
return prefix_map
|
||||||
|
|
||||||
def _has_schema_document(self, namespace):
|
|
||||||
"""Return a boolean if there is a SchemaDocumnet for the namespace.
|
|
||||||
|
|
||||||
:rtype: boolean
|
|
||||||
|
|
||||||
"""
|
|
||||||
return namespace in self._documents
|
|
||||||
|
|
||||||
def _add_schema_document(self, document):
|
|
||||||
logger.debug("Add document with tns %s to schema %s", document.namespace, id(self))
|
|
||||||
documents = self._documents.setdefault(document.namespace, [])
|
|
||||||
documents.append(document)
|
|
||||||
|
|
||||||
def _get_schema_document(self, namespace, location):
|
|
||||||
"""Return a list of SchemaDocument's for the given namespace AND
|
|
||||||
location.
|
|
||||||
|
|
||||||
:rtype: SchemaDocument
|
|
||||||
|
|
||||||
"""
|
|
||||||
for document in self._documents.get(namespace, []):
|
|
||||||
if document._location == location:
|
|
||||||
return document
|
|
||||||
|
|
||||||
def _get_schema_documents(self, namespace, fail_silently=False):
|
def _get_schema_documents(self, namespace, fail_silently=False):
|
||||||
"""Return a list of SchemaDocument's for the given namespace.
|
"""Return a list of SchemaDocument's for the given namespace.
|
||||||
|
|
||||||
|
@ -316,21 +291,81 @@ class Schema(object):
|
||||||
|
|
||||||
"""
|
"""
|
||||||
if (
|
if (
|
||||||
namespace not in self._documents
|
not self.documents.has_schema_document_for_ns(namespace)
|
||||||
and namespace in const.AUTO_IMPORT_NAMESPACES
|
and namespace in const.AUTO_IMPORT_NAMESPACES
|
||||||
):
|
):
|
||||||
logger.debug("Auto importing missing known schema: %s", namespace)
|
logger.debug("Auto importing missing known schema: %s", namespace)
|
||||||
self.add_document_by_url(namespace)
|
self.add_document_by_url(namespace)
|
||||||
|
|
||||||
if namespace not in self._documents:
|
return self.documents.get_by_namespace(namespace, fail_silently)
|
||||||
|
|
||||||
|
|
||||||
|
class _SchemaContainer(object):
|
||||||
|
"""Container instances to store multiple SchemaDocument objects per
|
||||||
|
namespace.
|
||||||
|
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
self._instances = OrderedDict()
|
||||||
|
|
||||||
|
def __iter__(self):
|
||||||
|
for document in self.values():
|
||||||
|
yield document
|
||||||
|
|
||||||
|
def add(self, document):
|
||||||
|
"""Append a schema document
|
||||||
|
|
||||||
|
:param document: zeep.xsd.schema.SchemaDocument
|
||||||
|
|
||||||
|
"""
|
||||||
|
logger.debug("Add document with tns %s to schema %s", document.namespace, id(self))
|
||||||
|
documents = self._instances.setdefault(document.namespace, [])
|
||||||
|
documents.append(document)
|
||||||
|
|
||||||
|
def get_all_namespaces(self):
|
||||||
|
return self._instances.keys()
|
||||||
|
|
||||||
|
def get_by_namespace(self, namespace, fail_silently):
|
||||||
|
if namespace not in self._instances:
|
||||||
if fail_silently:
|
if fail_silently:
|
||||||
return []
|
return []
|
||||||
raise exceptions.NamespaceError(
|
raise exceptions.NamespaceError(
|
||||||
"No schema available for the namespace %r" % namespace)
|
"No schema available for the namespace %r" % namespace)
|
||||||
return self._documents[namespace]
|
return self._instances[namespace]
|
||||||
|
|
||||||
|
def get_by_namespace_and_location(self, namespace, location):
|
||||||
|
"""Return list of SchemaDocument's for the given namespace AND
|
||||||
|
location.
|
||||||
|
|
||||||
|
:rtype: zeep.xsd.schema.SchemaDocument
|
||||||
|
|
||||||
|
"""
|
||||||
|
documents = self.get_by_namespace(namespace, fail_silently=True)
|
||||||
|
for document in documents:
|
||||||
|
if document._location == location:
|
||||||
|
return document
|
||||||
|
|
||||||
|
def has_schema_document_for_ns(self, namespace):
|
||||||
|
"""Return a boolean if there is a SchemaDocument for the namespace.
|
||||||
|
|
||||||
|
:rtype: boolean
|
||||||
|
|
||||||
|
"""
|
||||||
|
return namespace in self._instances
|
||||||
|
|
||||||
|
def values(self):
|
||||||
|
for documents in self._instances.values():
|
||||||
|
for document in documents:
|
||||||
|
yield document
|
||||||
|
|
||||||
|
|
||||||
class SchemaDocument(object):
|
class SchemaDocument(object):
|
||||||
|
"""A Schema Document consists of a set of schema components for a
|
||||||
|
specific target namespace.
|
||||||
|
|
||||||
|
"""
|
||||||
|
|
||||||
def __init__(self, namespace, location, base_url):
|
def __init__(self, namespace, location, base_url):
|
||||||
logger.debug("Init schema document for %r", location)
|
logger.debug("Init schema document for %r", location)
|
||||||
|
|
||||||
|
@ -340,6 +375,7 @@ class SchemaDocument(object):
|
||||||
self._target_namespace = namespace
|
self._target_namespace = namespace
|
||||||
self._is_internal = False
|
self._is_internal = False
|
||||||
|
|
||||||
|
# Containers for specific types
|
||||||
self._attribute_groups = {}
|
self._attribute_groups = {}
|
||||||
self._attributes = {}
|
self._attributes = {}
|
||||||
self._elements = {}
|
self._elements = {}
|
||||||
|
@ -365,10 +401,16 @@ class SchemaDocument(object):
|
||||||
return not bool(self._imports or self._types or self._elements)
|
return not bool(self._imports or self._types or self._elements)
|
||||||
|
|
||||||
def load(self, schema, node):
|
def load(self, schema, node):
|
||||||
|
"""Load the XML Schema passed in via the node attribute.
|
||||||
|
|
||||||
|
:type schema: zeep.xsd.schema.Schema
|
||||||
|
:type node: etree._Element
|
||||||
|
|
||||||
|
"""
|
||||||
if node is None:
|
if node is None:
|
||||||
return
|
return
|
||||||
|
|
||||||
if not schema._has_schema_document(self._target_namespace):
|
if not schema.documents.has_schema_document_for_ns(self._target_namespace):
|
||||||
raise RuntimeError(
|
raise RuntimeError(
|
||||||
"The document needs to be registered in the schema before " +
|
"The document needs to be registered in the schema before " +
|
||||||
"it can be loaded")
|
"it can be loaded")
|
||||||
|
@ -415,44 +457,62 @@ class SchemaDocument(object):
|
||||||
_resolve_dict(self._types)
|
_resolve_dict(self._types)
|
||||||
|
|
||||||
def register_import(self, namespace, schema):
|
def register_import(self, namespace, schema):
|
||||||
|
"""Register an import for an other schema document.
|
||||||
|
|
||||||
|
:type namespace: str
|
||||||
|
:type schema: zeep.xsd.schema.SchemaDocument
|
||||||
|
|
||||||
|
"""
|
||||||
schemas = self._imports.setdefault(namespace, [])
|
schemas = self._imports.setdefault(namespace, [])
|
||||||
schemas.append(schema)
|
schemas.append(schema)
|
||||||
|
|
||||||
def is_imported(self, namespace):
|
def is_imported(self, namespace):
|
||||||
return namespace in self._imports
|
return namespace in self._imports
|
||||||
|
|
||||||
def register_type(self, name, value):
|
def register_type(self, qname, value):
|
||||||
assert not isinstance(value, type)
|
"""Register a xsd.Type in this schema
|
||||||
assert value is not None
|
|
||||||
|
|
||||||
if isinstance(name, etree.QName):
|
:type qname: str or etree.QName
|
||||||
name = name.text
|
:type value: zeep.xsd.Type
|
||||||
logger.debug("register_type(%r, %r)", name, value)
|
|
||||||
self._types[name] = value
|
|
||||||
|
|
||||||
def register_element(self, name, value):
|
"""
|
||||||
if isinstance(name, etree.QName):
|
self._add_component(qname, value, self._types, 'type')
|
||||||
name = name.text
|
|
||||||
logger.debug("register_element(%r, %r)", name, value)
|
|
||||||
self._elements[name] = value
|
|
||||||
|
|
||||||
def register_group(self, name, value):
|
def register_element(self, qname, value):
|
||||||
if isinstance(name, etree.QName):
|
"""Register a xsd.Element in this schema
|
||||||
name = name.text
|
|
||||||
logger.debug("register_group(%r, %r)", name, value)
|
|
||||||
self._groups[name] = value
|
|
||||||
|
|
||||||
def register_attribute(self, name, value):
|
:type qname: str or etree.QName
|
||||||
if isinstance(name, etree.QName):
|
:type value: zeep.xsd.Element
|
||||||
name = name.text
|
|
||||||
logger.debug("register_attribute(%r, %r)", name, value)
|
|
||||||
self._attributes[name] = value
|
|
||||||
|
|
||||||
def register_attribute_group(self, name, value):
|
"""
|
||||||
if isinstance(name, etree.QName):
|
self._add_component(qname, value, self._elements, 'element')
|
||||||
name = name.text
|
|
||||||
logger.debug("register_attribute_group(%r, %r)", name, value)
|
def register_group(self, qname, value):
|
||||||
self._attribute_groups[name] = value
|
"""Register a xsd.Element in this schema
|
||||||
|
|
||||||
|
:type qname: str or etree.QName
|
||||||
|
:type value: zeep.xsd.Element
|
||||||
|
|
||||||
|
"""
|
||||||
|
self._add_component(qname, value, self._groups, 'group')
|
||||||
|
|
||||||
|
def register_attribute(self, qname, value):
|
||||||
|
"""Register a xsd.Element in this schema
|
||||||
|
|
||||||
|
:type qname: str or etree.QName
|
||||||
|
:type value: zeep.xsd.Attribute
|
||||||
|
|
||||||
|
"""
|
||||||
|
self._add_component(qname, value, self._attributes, 'attribute')
|
||||||
|
|
||||||
|
def register_attribute_group(self, qname, value):
|
||||||
|
"""Register a xsd.Element in this schema
|
||||||
|
|
||||||
|
:type qname: str or etree.QName
|
||||||
|
:type value: zeep.xsd.Group
|
||||||
|
|
||||||
|
"""
|
||||||
|
self._add_component(qname, value, self._attribute_groups, 'attribute_group')
|
||||||
|
|
||||||
def get_type(self, qname):
|
def get_type(self, qname):
|
||||||
"""Return a xsd.Type object from this schema
|
"""Return a xsd.Type object from this schema
|
||||||
|
@ -460,7 +520,7 @@ class SchemaDocument(object):
|
||||||
:rtype: zeep.xsd.ComplexType or zeep.xsd.AnySimpleType
|
:rtype: zeep.xsd.ComplexType or zeep.xsd.AnySimpleType
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self._get_instance(qname, self._types, 'type')
|
return self._get_component(qname, self._types, 'type')
|
||||||
|
|
||||||
def get_element(self, qname):
|
def get_element(self, qname):
|
||||||
"""Return a xsd.Element object from this schema
|
"""Return a xsd.Element object from this schema
|
||||||
|
@ -468,7 +528,7 @@ class SchemaDocument(object):
|
||||||
:rtype: zeep.xsd.Element
|
:rtype: zeep.xsd.Element
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self._get_instance(qname, self._elements, 'element')
|
return self._get_component(qname, self._elements, 'element')
|
||||||
|
|
||||||
def get_group(self, qname):
|
def get_group(self, qname):
|
||||||
"""Return a xsd.Group object from this schema.
|
"""Return a xsd.Group object from this schema.
|
||||||
|
@ -476,7 +536,7 @@ class SchemaDocument(object):
|
||||||
:rtype: zeep.xsd.Group
|
:rtype: zeep.xsd.Group
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self._get_instance(qname, self._groups, 'group')
|
return self._get_component(qname, self._groups, 'group')
|
||||||
|
|
||||||
def get_attribute(self, qname):
|
def get_attribute(self, qname):
|
||||||
"""Return a xsd.Attribute object from this schema
|
"""Return a xsd.Attribute object from this schema
|
||||||
|
@ -484,7 +544,7 @@ class SchemaDocument(object):
|
||||||
:rtype: zeep.xsd.Attribute
|
:rtype: zeep.xsd.Attribute
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self._get_instance(qname, self._attributes, 'attribute')
|
return self._get_component(qname, self._attributes, 'attribute')
|
||||||
|
|
||||||
def get_attribute_group(self, qname):
|
def get_attribute_group(self, qname):
|
||||||
"""Return a xsd.AttributeGroup object from this schema
|
"""Return a xsd.AttributeGroup object from this schema
|
||||||
|
@ -492,9 +552,15 @@ class SchemaDocument(object):
|
||||||
:rtype: zeep.xsd.AttributeGroup
|
:rtype: zeep.xsd.AttributeGroup
|
||||||
|
|
||||||
"""
|
"""
|
||||||
return self._get_instance(qname, self._attribute_groups, 'attributeGroup')
|
return self._get_component(qname, self._attribute_groups, 'attributeGroup')
|
||||||
|
|
||||||
def _get_instance(self, qname, items, item_name):
|
def _add_component(self, name, value, items, item_name):
|
||||||
|
if isinstance(name, etree.QName):
|
||||||
|
name = name.text
|
||||||
|
logger.debug("register_%s(%r, %r)", item_name, name, value)
|
||||||
|
items[name] = value
|
||||||
|
|
||||||
|
def _get_component(self, qname, items, item_name):
|
||||||
try:
|
try:
|
||||||
return items[qname]
|
return items[qname]
|
||||||
except KeyError:
|
except KeyError:
|
||||||
|
|
|
@ -94,7 +94,22 @@ class AnyType(Type):
|
||||||
return self
|
return self
|
||||||
|
|
||||||
def xmlvalue(self, value):
|
def xmlvalue(self, value):
|
||||||
return value
|
"""Guess the xsd:type for the value and use corresponding serializer"""
|
||||||
|
from zeep.xsd.types import builtins
|
||||||
|
|
||||||
|
available_types = [
|
||||||
|
builtins.String,
|
||||||
|
builtins.Boolean,
|
||||||
|
builtins.Decimal,
|
||||||
|
builtins.Float,
|
||||||
|
builtins.DateTime,
|
||||||
|
builtins.Date,
|
||||||
|
builtins.Time,
|
||||||
|
]
|
||||||
|
for xsd_type in available_types:
|
||||||
|
if isinstance(value, xsd_type.accepted_types):
|
||||||
|
return xsd_type().xmlvalue(value)
|
||||||
|
return str(value)
|
||||||
|
|
||||||
def pythonvalue(self, value, schema=None):
|
def pythonvalue(self, value, schema=None):
|
||||||
return value
|
return value
|
||||||
|
|
|
@ -4,7 +4,7 @@ import six
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from zeep.exceptions import ValidationError
|
from zeep.exceptions import ValidationError
|
||||||
from zeep.xsd.const import xsd_ns
|
from zeep.xsd.const import Nil, xsd_ns, xsi_ns
|
||||||
from zeep.xsd.types.any import AnyType
|
from zeep.xsd.types.any import AnyType
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
@ -68,6 +68,9 @@ class AnySimpleType(AnyType):
|
||||||
'%s.pytonvalue() not implemented' % self.__class__.__name__)
|
'%s.pytonvalue() not implemented' % self.__class__.__name__)
|
||||||
|
|
||||||
def render(self, parent, value, xsd_type=None, render_path=None):
|
def render(self, parent, value, xsd_type=None, render_path=None):
|
||||||
|
if value is Nil:
|
||||||
|
parent.set(xsi_ns('nil'), 'true')
|
||||||
|
return
|
||||||
parent.text = self.xmlvalue(value)
|
parent.text = self.xmlvalue(value)
|
||||||
|
|
||||||
def signature(self, schema=None, standalone=True):
|
def signature(self, schema=None, standalone=True):
|
||||||
|
@ -76,7 +79,3 @@ class AnySimpleType(AnyType):
|
||||||
def validate(self, value, required=False):
|
def validate(self, value, required=False):
|
||||||
if required and value is None:
|
if required and value is None:
|
||||||
raise ValidationError("Value is required")
|
raise ValidationError("Value is required")
|
||||||
|
|
||||||
def xmlvalue(self, value):
|
|
||||||
raise NotImplementedError(
|
|
||||||
'%s.xmlvalue() not implemented' % self.__class__.__name__)
|
|
||||||
|
|
|
@ -13,6 +13,7 @@ class AnyObject(object):
|
||||||
:param value: The value
|
:param value: The value
|
||||||
|
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, xsd_object, value):
|
def __init__(self, xsd_object, value):
|
||||||
self.xsd_obj = xsd_object
|
self.xsd_obj = xsd_object
|
||||||
self.value = value
|
self.value = value
|
||||||
|
@ -110,6 +111,9 @@ class CompoundValue(object):
|
||||||
def __iter__(self):
|
def __iter__(self):
|
||||||
return self.__values__.__iter__()
|
return self.__values__.__iter__()
|
||||||
|
|
||||||
|
def __dir__(self):
|
||||||
|
return list(self.__values__.keys())
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
return PrettyPrinter().pformat(self.__values__)
|
return PrettyPrinter().pformat(self.__values__)
|
||||||
|
|
||||||
|
@ -194,7 +198,8 @@ def _process_signature(xsd_type, args, kwargs):
|
||||||
available_kwargs = set(kwargs.keys())
|
available_kwargs = set(kwargs.keys())
|
||||||
for element_name, element in xsd_type.elements_nested:
|
for element_name, element in xsd_type.elements_nested:
|
||||||
if element.accepts_multiple:
|
if element.accepts_multiple:
|
||||||
values = element.parse_kwargs(kwargs, element_name, available_kwargs)
|
values = element.parse_kwargs(
|
||||||
|
kwargs, element_name, available_kwargs)
|
||||||
else:
|
else:
|
||||||
values = element.parse_kwargs(kwargs, None, available_kwargs)
|
values = element.parse_kwargs(kwargs, None, available_kwargs)
|
||||||
|
|
||||||
|
|
|
@ -170,7 +170,7 @@ class SchemaVisitor(object):
|
||||||
|
|
||||||
# Check if the schema is already imported before based on the
|
# Check if the schema is already imported before based on the
|
||||||
# namespace. Schema's without namespace are registered as 'None'
|
# namespace. Schema's without namespace are registered as 'None'
|
||||||
document = self.schema._get_schema_document(namespace, location)
|
document = self.schema.documents.get_by_namespace_and_location(namespace, location)
|
||||||
if document:
|
if document:
|
||||||
logger.debug("Returning existing schema: %r", location)
|
logger.debug("Returning existing schema: %r", location)
|
||||||
self.register_import(namespace, document)
|
self.register_import(namespace, document)
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
import pytest
|
|
||||||
from pretend import stub
|
|
||||||
from lxml import etree
|
|
||||||
import aiohttp
|
import aiohttp
|
||||||
|
import pytest
|
||||||
from aioresponses import aioresponses
|
from aioresponses import aioresponses
|
||||||
|
from lxml import etree
|
||||||
|
from pretend import stub
|
||||||
|
|
||||||
from zeep import cache, asyncio, exceptions
|
from zeep import asyncio, exceptions
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.requests
|
@pytest.mark.requests
|
||||||
|
|
|
@ -43,6 +43,20 @@ def test_service_proxy_non_existing():
|
||||||
assert client_obj.service.NonExisting
|
assert client_obj.service.NonExisting
|
||||||
|
|
||||||
|
|
||||||
|
def test_service_proxy_dir_operations():
|
||||||
|
client_obj = client.Client('tests/wsdl_files/soap.wsdl')
|
||||||
|
operations = [op for op in dir(client_obj.service) if not op.startswith('_')]
|
||||||
|
assert set(operations) == set(['GetLastTradePrice', 'GetLastTradePriceNoOutput'])
|
||||||
|
|
||||||
|
|
||||||
|
def test_operation_proxy_doc():
|
||||||
|
client_obj = client.Client('tests/wsdl_files/soap.wsdl')
|
||||||
|
assert (client_obj.service.GetLastTradePrice.__doc__
|
||||||
|
== 'GetLastTradePrice(tickerSymbol: xsd:string, '
|
||||||
|
'account: ns0:account, '
|
||||||
|
'country: ns0:country) -> price: xsd:float')
|
||||||
|
|
||||||
|
|
||||||
def test_open_from_file_object():
|
def test_open_from_file_object():
|
||||||
with open('tests/wsdl_files/soap_transport_err.wsdl', 'rb') as fh:
|
with open('tests/wsdl_files/soap_transport_err.wsdl', 'rb') as fh:
|
||||||
client_obj = client.Client(fh)
|
client_obj = client.Client(fh)
|
||||||
|
|
|
@ -13,7 +13,7 @@ def test_factory_namespace():
|
||||||
|
|
||||||
def test_factory_no_reference():
|
def test_factory_no_reference():
|
||||||
client = Client('tests/wsdl_files/soap.wsdl')
|
client = Client('tests/wsdl_files/soap.wsdl')
|
||||||
factory = client.type_factory('http://example.com/stockquote.xsd')
|
|
||||||
obj_1 = client.get_type('ns0:ArrayOfAddress')()
|
obj_1 = client.get_type('ns0:ArrayOfAddress')()
|
||||||
obj_1.Address.append({
|
obj_1.Address.append({
|
||||||
'NameFirst': 'J',
|
'NameFirst': 'J',
|
||||||
|
|
|
@ -4,9 +4,7 @@ from collections import OrderedDict
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import assert_nodes_equal, load_xml, render_node
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import helpers, xsd
|
||||||
from six import binary_type
|
|
||||||
from zeep import helpers
|
|
||||||
from zeep.helpers import serialize_object
|
from zeep.helpers import serialize_object
|
||||||
|
|
||||||
|
|
||||||
|
@ -197,6 +195,6 @@ def test_create_xml_soap_map():
|
||||||
<value xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xs:date">2016-01-14</value>
|
<value xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xs:date">2016-01-14</value>
|
||||||
</item>
|
</item>
|
||||||
</document>
|
</document>
|
||||||
""" # noqa
|
""" # noqa
|
||||||
node = render_node(value._xsd_type, value)
|
node = render_node(value._xsd_type, value)
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from zeep.loader import parse_xml
|
|
||||||
from tests.utils import DummyTransport
|
from tests.utils import DummyTransport
|
||||||
|
from zeep.loader import parse_xml
|
||||||
|
|
||||||
|
|
||||||
def test_huge_text():
|
def test_huge_text():
|
||||||
# libxml2>=2.7.3 has XML_MAX_TEXT_LENGTH 10000000 without XML_PARSE_HUGE
|
# libxml2>=2.7.3 has XML_MAX_TEXT_LENGTH 10000000 without XML_PARSE_HUGE
|
||||||
|
|
|
@ -11,7 +11,7 @@ def test_dict():
|
||||||
'foo': '1',
|
'foo': '1',
|
||||||
'bar': {
|
'bar': {
|
||||||
'bala': 'qwe',
|
'bala': 'qwe',
|
||||||
},
|
},
|
||||||
'x': [1, 2, 3, 4],
|
'x': [1, 2, 3, 4],
|
||||||
'y': [],
|
'y': [],
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,13 +1,9 @@
|
||||||
import io
|
import io
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
import requests_mock
|
|
||||||
from lxml import etree
|
|
||||||
from pretend import stub
|
from pretend import stub
|
||||||
from six import StringIO
|
|
||||||
|
|
||||||
from tests.utils import DummyTransport, assert_nodes_equal
|
from zeep import Client
|
||||||
from zeep import Client, wsdl
|
|
||||||
from zeep.transports import Transport
|
from zeep.transports import Transport
|
||||||
|
|
||||||
|
|
||||||
|
@ -74,10 +70,12 @@ def test_parse_multiref_soap_response():
|
||||||
<wsdl:operation name="TestOperation">
|
<wsdl:operation name="TestOperation">
|
||||||
<soap:operation soapAction=""/>
|
<soap:operation soapAction=""/>
|
||||||
<wsdl:input name="TestOperationRequest">
|
<wsdl:input name="TestOperationRequest">
|
||||||
<soap:body use="encoded" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
|
<soap:body use="encoded"
|
||||||
|
encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
|
||||||
</wsdl:input>
|
</wsdl:input>
|
||||||
<wsdl:output name="TestOperationResponse">
|
<wsdl:output name="TestOperationResponse">
|
||||||
<soap:body use="encoded" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
|
<soap:body use="encoded"
|
||||||
|
encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
|
||||||
</wsdl:output>
|
</wsdl:output>
|
||||||
</wsdl:operation>
|
</wsdl:operation>
|
||||||
</wsdl:binding>
|
</wsdl:binding>
|
||||||
|
@ -88,7 +86,7 @@ def test_parse_multiref_soap_response():
|
||||||
</wsdl:port>
|
</wsdl:port>
|
||||||
</wsdl:service>
|
</wsdl:service>
|
||||||
</wsdl:definitions>
|
</wsdl:definitions>
|
||||||
""".strip())
|
""".strip()) # noqa
|
||||||
|
|
||||||
content = """
|
content = """
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -135,7 +133,6 @@ def test_parse_multiref_soap_response():
|
||||||
assert result.item_2.subitem_2 == 'bar'
|
assert result.item_2.subitem_2 == 'bar'
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.requests
|
@pytest.mark.requests
|
||||||
def test_parse_multiref_soap_response_child():
|
def test_parse_multiref_soap_response_child():
|
||||||
wsdl_file = io.StringIO(u"""
|
wsdl_file = io.StringIO(u"""
|
||||||
|
@ -218,7 +215,7 @@ def test_parse_multiref_soap_response_child():
|
||||||
</wsdl:port>
|
</wsdl:port>
|
||||||
</wsdl:service>
|
</wsdl:service>
|
||||||
</wsdl:definitions>
|
</wsdl:definitions>
|
||||||
""".strip())
|
""".strip()) # noqa
|
||||||
|
|
||||||
content = """
|
content = """
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -247,7 +244,7 @@ def test_parse_multiref_soap_response_child():
|
||||||
</multiRef>
|
</multiRef>
|
||||||
</soapenv:Body>
|
</soapenv:Body>
|
||||||
</soapenv:Envelope>
|
</soapenv:Envelope>
|
||||||
""".strip()
|
""".strip() # noqa
|
||||||
|
|
||||||
client = Client(wsdl_file, transport=Transport(),)
|
client = Client(wsdl_file, transport=Transport(),)
|
||||||
response = stub(
|
response = stub(
|
||||||
|
@ -264,4 +261,3 @@ def test_parse_multiref_soap_response_child():
|
||||||
assert result.item_2.subitem_1.subitem_1 == 'foo'
|
assert result.item_2.subitem_1.subitem_1 == 'foo'
|
||||||
assert result.item_2.subitem_1.subitem_2 == 'bar'
|
assert result.item_2.subitem_1.subitem_2 == 'bar'
|
||||||
assert result.item_2.subitem_2 == 'bar'
|
assert result.item_2.subitem_2 == 'bar'
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,13 @@
|
||||||
import io
|
import requests_mock
|
||||||
from requests_toolbelt.multipart.decoder import MultipartDecoder
|
|
||||||
from pretend import stub
|
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
from tests.utils import load_xml, assert_nodes_equal
|
from pretend import stub
|
||||||
|
from requests_toolbelt.multipart.decoder import MultipartDecoder
|
||||||
|
from six import StringIO
|
||||||
|
|
||||||
|
from tests.utils import assert_nodes_equal
|
||||||
|
from zeep import Client
|
||||||
|
from zeep.transports import Transport
|
||||||
from zeep.wsdl.attachments import MessagePack
|
from zeep.wsdl.attachments import MessagePack
|
||||||
|
|
||||||
|
|
||||||
from zeep.wsdl.messages import xop
|
from zeep.wsdl.messages import xop
|
||||||
|
|
||||||
|
|
||||||
|
@ -47,11 +49,6 @@ def test_rebuild_xml():
|
||||||
'Content-Type': 'multipart/related; boundary=MIME_boundary; type="application/soap+xml"; start="<claim@insurance.com>" 1'
|
'Content-Type': 'multipart/related; boundary=MIME_boundary; type="application/soap+xml"; start="<claim@insurance.com>" 1'
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
client = stub(
|
|
||||||
transport=None,
|
|
||||||
wsdl=stub(strict=True),
|
|
||||||
xml_huge_tree=False)
|
|
||||||
|
|
||||||
|
|
||||||
decoder = MultipartDecoder(
|
decoder = MultipartDecoder(
|
||||||
response.content, response.headers['Content-Type'], 'utf-8')
|
response.content, response.headers['Content-Type'], 'utf-8')
|
||||||
|
@ -74,16 +71,6 @@ def test_rebuild_xml():
|
||||||
assert_nodes_equal(etree.tostring(document), expected)
|
assert_nodes_equal(etree.tostring(document), expected)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
import pytest
|
|
||||||
import requests_mock
|
|
||||||
|
|
||||||
from six import StringIO
|
|
||||||
|
|
||||||
from zeep import Client
|
|
||||||
from zeep.transports import Transport
|
|
||||||
|
|
||||||
|
|
||||||
def test_xop():
|
def test_xop():
|
||||||
wsdl_main = StringIO("""
|
wsdl_main = StringIO("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -238,8 +225,8 @@ def test_xop():
|
||||||
print(response1)
|
print(response1)
|
||||||
with requests_mock.mock() as m:
|
with requests_mock.mock() as m:
|
||||||
m.post('http://tests.python-zeep.org/test',
|
m.post('http://tests.python-zeep.org/test',
|
||||||
content=response2.encode("utf-8"),
|
content=response2.encode("utf-8"),
|
||||||
headers={"Content-Type": content_type})
|
headers={"Content-Type": content_type})
|
||||||
result = service.TestOperation2("")
|
result = service.TestOperation2("")
|
||||||
assert result["_value_1"] == "BINARYDATA".encode()
|
assert result["_value_1"] == "BINARYDATA".encode()
|
||||||
|
|
||||||
|
@ -249,5 +236,3 @@ def test_xop():
|
||||||
headers={"Content-Type": content_type})
|
headers={"Content-Type": content_type})
|
||||||
result = service.TestOperation1("")
|
result = service.TestOperation1("")
|
||||||
assert result == "BINARYDATA".encode()
|
assert result == "BINARYDATA".encode()
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
import pytest
|
import pytest
|
||||||
from pretend import stub
|
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
from tornado.httpclient import HTTPResponse, HTTPRequest
|
|
||||||
from tornado.testing import gen_test, AsyncTestCase
|
|
||||||
from tornado.concurrent import Future
|
|
||||||
|
|
||||||
from mock import patch
|
from mock import patch
|
||||||
|
from pretend import stub
|
||||||
|
from tornado.concurrent import Future
|
||||||
|
from tornado.httpclient import HTTPRequest, HTTPResponse
|
||||||
|
from tornado.testing import AsyncTestCase, gen_test
|
||||||
|
|
||||||
from zeep.tornado import TornadoAsyncTransport
|
from zeep.tornado import TornadoAsyncTransport
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,6 @@ from pretend import stub
|
||||||
from zeep import cache, transports
|
from zeep import cache, transports
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.requests
|
@pytest.mark.requests
|
||||||
def test_no_cache():
|
def test_no_cache():
|
||||||
transport = transports.Transport(cache=None)
|
transport = transports.Transport(cache=None)
|
||||||
|
|
|
@ -3,7 +3,8 @@ import io
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import DummyTransport, assert_nodes_equal, load_xml, render_node
|
from tests.utils import (
|
||||||
|
DummyTransport, assert_nodes_equal, load_xml, render_node)
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -65,58 +65,6 @@ def test_parse():
|
||||||
assert operation.output.signature(as_output=True) == 'xsd:string'
|
assert operation.output.signature(as_output=True) == 'xsd:string'
|
||||||
|
|
||||||
|
|
||||||
def test_empty_input_parse():
|
|
||||||
wsdl_content = StringIO("""
|
|
||||||
<definitions xmlns="http://schemas.xmlsoap.org/wsdl/"
|
|
||||||
xmlns:tns="http://tests.python-zeep.org/tns"
|
|
||||||
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
|
|
||||||
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
|
|
||||||
targetNamespace="http://tests.python-zeep.org/tns">
|
|
||||||
<types>
|
|
||||||
<xsd:schema targetNamespace="http://tests.python-zeep.org/tns">
|
|
||||||
<xsd:element name="Request" type="xsd:string"/>
|
|
||||||
<xsd:element name="Response" type="xsd:string"/>
|
|
||||||
</xsd:schema>
|
|
||||||
</types>
|
|
||||||
|
|
||||||
<message name="Input"/>
|
|
||||||
<message name="Output">
|
|
||||||
<part element="tns:Response"/>
|
|
||||||
</message>
|
|
||||||
|
|
||||||
<portType name="TestPortType">
|
|
||||||
<operation name="TestOperation">
|
|
||||||
<input message="Input"/>
|
|
||||||
<output message="Output"/>
|
|
||||||
</operation>
|
|
||||||
</portType>
|
|
||||||
|
|
||||||
<binding name="TestBinding" type="tns:TestPortType">
|
|
||||||
<soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
|
|
||||||
<operation name="TestOperation">
|
|
||||||
<soap:operation soapAction=""/>
|
|
||||||
<input>
|
|
||||||
<soap:body use="literal"/>
|
|
||||||
</input>
|
|
||||||
<output>
|
|
||||||
<soap:body use="literal"/>
|
|
||||||
</output>
|
|
||||||
</operation>
|
|
||||||
</binding>
|
|
||||||
</definitions>
|
|
||||||
""".strip())
|
|
||||||
|
|
||||||
root = wsdl.Document(wsdl_content, None)
|
|
||||||
|
|
||||||
binding = root.bindings['{http://tests.python-zeep.org/tns}TestBinding']
|
|
||||||
operation = binding.get('TestOperation')
|
|
||||||
|
|
||||||
assert operation.input.body.signature(schema=root.types) == 'soap-env:Body()'
|
|
||||||
assert operation.input.header.signature(schema=root.types) == 'soap-env:Header()'
|
|
||||||
assert operation.input.envelope.signature(schema=root.types) == 'soap-env:envelope(body: {})'
|
|
||||||
assert operation.input.signature(as_output=False) == ''
|
|
||||||
|
|
||||||
|
|
||||||
def test_parse_with_header():
|
def test_parse_with_header():
|
||||||
wsdl_content = StringIO("""
|
wsdl_content = StringIO("""
|
||||||
<definitions xmlns="http://schemas.xmlsoap.org/wsdl/"
|
<definitions xmlns="http://schemas.xmlsoap.org/wsdl/"
|
||||||
|
|
|
@ -1,14 +1,13 @@
|
||||||
# -*- coding: utf-8 -*-
|
# -*- coding: utf-8 -*-
|
||||||
|
import platform
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
|
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
from pretend import stub
|
from pretend import stub
|
||||||
|
|
||||||
from tests.utils import load_xml
|
from tests.utils import load_xml
|
||||||
from zeep import Client
|
from zeep import Client
|
||||||
from zeep.exceptions import Fault
|
from zeep.exceptions import Fault, TransportError
|
||||||
from zeep.exceptions import TransportError
|
|
||||||
from zeep.wsdl import bindings
|
from zeep.wsdl import bindings
|
||||||
|
|
||||||
|
|
||||||
|
@ -167,6 +166,8 @@ def test_no_content_type():
|
||||||
assert result == 120.123
|
assert result == 120.123
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.skipif(platform.python_implementation() == 'PyPy',
|
||||||
|
reason="Fails on PyPy")
|
||||||
def test_wrong_content():
|
def test_wrong_content():
|
||||||
data = """
|
data = """
|
||||||
The request is answered something unexpected,
|
The request is answered something unexpected,
|
||||||
|
@ -190,6 +191,8 @@ def test_wrong_content():
|
||||||
assert data == exc.value.content
|
assert data == exc.value.content
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.skipif(platform.python_implementation() == 'PyPy',
|
||||||
|
reason="Fails on PyPy")
|
||||||
def test_wrong_no_unicode_content():
|
def test_wrong_no_unicode_content():
|
||||||
data = """
|
data = """
|
||||||
The request is answered something unexpected,
|
The request is answered something unexpected,
|
||||||
|
@ -214,6 +217,8 @@ def test_wrong_no_unicode_content():
|
||||||
assert data == exc.value.content
|
assert data == exc.value.content
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.skipif(platform.python_implementation() == 'PyPy',
|
||||||
|
reason="Fails on PyPy")
|
||||||
def test_http_error():
|
def test_http_error():
|
||||||
data = """
|
data = """
|
||||||
Unauthorized!
|
Unauthorized!
|
||||||
|
@ -384,3 +389,35 @@ def test_unexpected_headers():
|
||||||
assert result.body.price == 120.123
|
assert result.body.price == 120.123
|
||||||
assert result.header.body is None
|
assert result.header.body is None
|
||||||
assert len(result.header._raw_elements) == 1
|
assert len(result.header._raw_elements) == 1
|
||||||
|
|
||||||
|
|
||||||
|
def test_response_201():
|
||||||
|
client = Client('tests/wsdl_files/soap_header.wsdl')
|
||||||
|
binding = client.service._binding
|
||||||
|
|
||||||
|
response = stub(
|
||||||
|
status_code=201,
|
||||||
|
content='',
|
||||||
|
encoding='utf-8',
|
||||||
|
headers={}
|
||||||
|
)
|
||||||
|
|
||||||
|
result = binding.process_reply(
|
||||||
|
client, binding.get('GetLastTradePrice'), response)
|
||||||
|
assert result is None
|
||||||
|
|
||||||
|
|
||||||
|
def test_response_202():
|
||||||
|
client = Client('tests/wsdl_files/soap_header.wsdl')
|
||||||
|
binding = client.service._binding
|
||||||
|
|
||||||
|
response = stub(
|
||||||
|
status_code=202,
|
||||||
|
content='',
|
||||||
|
encoding='utf-8',
|
||||||
|
headers={}
|
||||||
|
)
|
||||||
|
|
||||||
|
result = binding.process_reply(
|
||||||
|
client, binding.get('GetLastTradePrice'), response)
|
||||||
|
assert result is None
|
||||||
|
|
|
@ -2,7 +2,6 @@ import os
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
|
||||||
|
|
||||||
from tests.utils import load_xml
|
from tests.utils import load_xml
|
||||||
from zeep import wsse
|
from zeep import wsse
|
||||||
|
|
|
@ -72,6 +72,24 @@ def test_element_simple_type():
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
|
|
||||||
|
|
||||||
|
def test_complex_type():
|
||||||
|
custom_type = xsd.ComplexType(
|
||||||
|
xsd.Sequence([
|
||||||
|
xsd.Element(
|
||||||
|
etree.QName('http://tests.python-zeep.org/', 'username'),
|
||||||
|
xsd.String()),
|
||||||
|
xsd.Element(
|
||||||
|
etree.QName('http://tests.python-zeep.org/', 'password'),
|
||||||
|
xsd.String()),
|
||||||
|
])
|
||||||
|
)
|
||||||
|
obj = custom_type('user', 'pass')
|
||||||
|
assert {key: obj[key] for key in obj} == {
|
||||||
|
'username': 'user',
|
||||||
|
'password': 'pass'
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def test_nil_elements():
|
def test_nil_elements():
|
||||||
custom_type = xsd.Element(
|
custom_type = xsd.Element(
|
||||||
'{http://tests.python-zeep.org/}container',
|
'{http://tests.python-zeep.org/}container',
|
||||||
|
@ -149,8 +167,6 @@ def test_invalid_kwarg_simple_type():
|
||||||
elm(something='is-wrong')
|
elm(something='is-wrong')
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def test_any():
|
def test_any():
|
||||||
some_type = xsd.Element(
|
some_type = xsd.Element(
|
||||||
etree.QName('http://tests.python-zeep.org/', 'doei'),
|
etree.QName('http://tests.python-zeep.org/', 'doei'),
|
||||||
|
|
|
@ -26,7 +26,6 @@ def get_any_schema():
|
||||||
"""))
|
"""))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def test_default_xsd_type():
|
def test_default_xsd_type():
|
||||||
schema = xsd.Schema(load_xml("""
|
schema = xsd.Schema(load_xml("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -257,20 +256,21 @@ def test_element_any_type():
|
||||||
schema = xsd.Schema(node)
|
schema = xsd.Schema(node)
|
||||||
|
|
||||||
container_elm = schema.get_element('{http://tests.python-zeep.org/}container')
|
container_elm = schema.get_element('{http://tests.python-zeep.org/}container')
|
||||||
obj = container_elm(something='bar')
|
obj = container_elm(something=datetime.time(18, 29, 59))
|
||||||
|
|
||||||
node = etree.Element('document')
|
node = etree.Element('document')
|
||||||
container_elm.render(node, obj)
|
container_elm.render(node, obj)
|
||||||
expected = """
|
expected = """
|
||||||
<document>
|
<document>
|
||||||
<ns0:container xmlns:ns0="http://tests.python-zeep.org/">
|
<ns0:container xmlns:ns0="http://tests.python-zeep.org/">
|
||||||
<ns0:something>bar</ns0:something>
|
<ns0:something>18:29:59</ns0:something>
|
||||||
</ns0:container>
|
</ns0:container>
|
||||||
</document>
|
</document>
|
||||||
"""
|
"""
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
item = container_elm.parse(node.getchildren()[0], schema)
|
item = container_elm.parse(node.getchildren()[0], schema)
|
||||||
assert item.something == 'bar'
|
assert item.something == '18:29:59'
|
||||||
|
|
||||||
|
|
||||||
def test_element_any_type_unknown_type():
|
def test_element_any_type_unknown_type():
|
||||||
node = etree.fromstring("""
|
node = etree.fromstring("""
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
from lxml import etree
|
|
||||||
import pytest
|
import pytest
|
||||||
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import assert_nodes_equal, load_xml, render_node
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
|
@ -295,3 +295,38 @@ def test_xml_unparsed_elements():
|
||||||
obj = container_elm.parse(expected[0], schema)
|
obj = container_elm.parse(expected[0], schema)
|
||||||
assert obj.item == 'bar'
|
assert obj.item == 'bar'
|
||||||
assert obj._raw_elements
|
assert obj._raw_elements
|
||||||
|
|
||||||
|
|
||||||
|
def test_xml_simple_content_nil():
|
||||||
|
schema = xsd.Schema(load_xml("""
|
||||||
|
<?xml version="1.0"?>
|
||||||
|
<schema xmlns="http://www.w3.org/2001/XMLSchema"
|
||||||
|
xmlns:tns="http://tests.python-zeep.org/"
|
||||||
|
targetNamespace="http://tests.python-zeep.org/"
|
||||||
|
elementFormDefault="qualified">
|
||||||
|
<element name="container" nillable="true">
|
||||||
|
<complexType>
|
||||||
|
<simpleContent>
|
||||||
|
<restriction base="string">
|
||||||
|
<maxLength value="1000"/>
|
||||||
|
</restriction>
|
||||||
|
</simpleContent>
|
||||||
|
</complexType>
|
||||||
|
</element>
|
||||||
|
</schema>
|
||||||
|
"""))
|
||||||
|
schema.set_ns_prefix('tns', 'http://tests.python-zeep.org/')
|
||||||
|
container_elm = schema.get_element('tns:container')
|
||||||
|
obj = container_elm(xsd.Nil)
|
||||||
|
result = render_node(container_elm, obj)
|
||||||
|
|
||||||
|
expected = """
|
||||||
|
<document>
|
||||||
|
<ns0:container xmlns:ns0="http://tests.python-zeep.org/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:nil="true" />
|
||||||
|
</document>
|
||||||
|
"""
|
||||||
|
result = render_node(container_elm, obj)
|
||||||
|
assert_nodes_equal(result, expected)
|
||||||
|
|
||||||
|
obj = container_elm.parse(result[0], schema)
|
||||||
|
assert obj._value_1 is None
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import assert_nodes_equal, render_node, load_xml
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,10 +1,11 @@
|
||||||
from collections import deque
|
from collections import deque
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import assert_nodes_equal, load_xml, render_node
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
from zeep.exceptions import XMLParseError, ValidationError
|
from zeep.exceptions import ValidationError, XMLParseError
|
||||||
from zeep.helpers import serialize_object
|
from zeep.helpers import serialize_object
|
||||||
|
|
||||||
|
|
||||||
|
@ -95,6 +96,7 @@ def test_choice_element_second_elm():
|
||||||
assert value.item_2 == 'foo'
|
assert value.item_2 == 'foo'
|
||||||
assert value.item_3 is None
|
assert value.item_3 is None
|
||||||
|
|
||||||
|
|
||||||
def test_choice_element_second_elm_positional():
|
def test_choice_element_second_elm_positional():
|
||||||
node = etree.fromstring("""
|
node = etree.fromstring("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -768,6 +770,8 @@ def test_choice_with_sequence_change():
|
||||||
element.render(node, elm)
|
element.render(node, elm)
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
value = element.parse(node[0], schema)
|
value = element.parse(node[0], schema)
|
||||||
|
assert value.item_1 == 'bla-1'
|
||||||
|
assert value.item_2 == 'bla-2'
|
||||||
|
|
||||||
|
|
||||||
def test_choice_with_sequence_change_named():
|
def test_choice_with_sequence_change_named():
|
||||||
|
@ -813,6 +817,8 @@ def test_choice_with_sequence_change_named():
|
||||||
element.render(node, elm)
|
element.render(node, elm)
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
value = element.parse(node[0], schema)
|
value = element.parse(node[0], schema)
|
||||||
|
assert value.item_1 == 'bla-1'
|
||||||
|
assert value.item_2 == 'bla-2'
|
||||||
|
|
||||||
|
|
||||||
def test_choice_with_sequence_multiple():
|
def test_choice_with_sequence_multiple():
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import assert_nodes_equal, render_node, load_xml
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import load_xml, render_node, assert_nodes_equal
|
from tests.utils import assert_nodes_equal, load_xml, render_node
|
||||||
from zeep import xsd
|
from zeep import xsd
|
||||||
|
|
||||||
|
|
||||||
|
@ -81,7 +81,6 @@ def test_build_min_occurs_2_max_occurs_2():
|
||||||
|
|
||||||
assert custom_type.signature()
|
assert custom_type.signature()
|
||||||
|
|
||||||
|
|
||||||
elm = custom_type(_value_1=[
|
elm = custom_type(_value_1=[
|
||||||
{'item_1': 'foo-1', 'item_2': 'bar-1'},
|
{'item_1': 'foo-1', 'item_2': 'bar-1'},
|
||||||
{'item_1': 'foo-2', 'item_2': 'bar-2'},
|
{'item_1': 'foo-2', 'item_2': 'bar-2'},
|
||||||
|
|
|
@ -198,7 +198,6 @@ def test_sequence_parse_anytype_regression_17():
|
||||||
assert result.getCustomFieldReturn.value.content == 'Test Solution'
|
assert result.getCustomFieldReturn.value.content == 'Test Solution'
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def test_nested_complex_type():
|
def test_nested_complex_type():
|
||||||
custom_type = xsd.Element(
|
custom_type = xsd.Element(
|
||||||
etree.QName('http://tests.python-zeep.org/', 'authentication'),
|
etree.QName('http://tests.python-zeep.org/', 'authentication'),
|
||||||
|
@ -324,13 +323,13 @@ def test_nested_choice_optional():
|
||||||
etree.QName('http://tests.python-zeep.org/', 'item_1'),
|
etree.QName('http://tests.python-zeep.org/', 'item_1'),
|
||||||
xsd.String()),
|
xsd.String()),
|
||||||
xsd.Choice([
|
xsd.Choice([
|
||||||
xsd.Element(
|
xsd.Element(
|
||||||
'{http://tests.python-zeep.org/}item_2',
|
'{http://tests.python-zeep.org/}item_2',
|
||||||
xsd.String()),
|
xsd.String()),
|
||||||
xsd.Element(
|
xsd.Element(
|
||||||
'{http://tests.python-zeep.org/}item_3',
|
'{http://tests.python-zeep.org/}item_3',
|
||||||
xsd.String()),
|
xsd.String()),
|
||||||
],
|
],
|
||||||
min_occurs=0, max_occurs=1
|
min_occurs=0, max_occurs=1
|
||||||
),
|
),
|
||||||
])
|
])
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
import pytest
|
import pytest
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from tests.utils import DummyTransport, load_xml
|
from tests.utils import (
|
||||||
|
DummyTransport, assert_nodes_equal, load_xml, render_node)
|
||||||
from zeep import exceptions, xsd
|
from zeep import exceptions, xsd
|
||||||
from zeep.xsd import Schema
|
from zeep.xsd import Schema
|
||||||
from zeep.xsd.types.unresolved import UnresolvedType
|
from zeep.xsd.types.unresolved import UnresolvedType
|
||||||
from tests.utils import assert_nodes_equal, load_xml, render_node
|
|
||||||
|
|
||||||
|
|
||||||
def test_default_types():
|
def test_default_types():
|
||||||
|
@ -776,6 +776,7 @@ def test_include_different_form_defaults():
|
||||||
""")
|
""")
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
|
|
||||||
|
|
||||||
def test_merge():
|
def test_merge():
|
||||||
node_a = etree.fromstring("""
|
node_a = etree.fromstring("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
from lxml import etree
|
from lxml import etree
|
||||||
|
|
||||||
from zeep import xsd
|
|
||||||
from tests.utils import load_xml
|
from tests.utils import load_xml
|
||||||
|
from zeep import xsd
|
||||||
|
|
||||||
|
|
||||||
def test_signature_complex_type_choice():
|
def test_signature_complex_type_choice():
|
||||||
|
@ -189,6 +189,7 @@ def test_signature_complex_type_sequence_with_anys():
|
||||||
'({item_1: xsd:string} | {item_2: {_value_1: ANY, _value_2: ANY}})' +
|
'({item_1: xsd:string} | {item_2: {_value_1: ANY, _value_2: ANY}})' +
|
||||||
')')
|
')')
|
||||||
|
|
||||||
|
|
||||||
def test_schema_recursive_ref():
|
def test_schema_recursive_ref():
|
||||||
schema = xsd.Schema(load_xml("""
|
schema = xsd.Schema(load_xml("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
@ -211,4 +212,3 @@ def test_schema_recursive_ref():
|
||||||
|
|
||||||
elm = schema.get_element('ns0:Container')
|
elm = schema.get_element('ns0:Container')
|
||||||
elm.signature(schema)
|
elm.signature(schema)
|
||||||
|
|
||||||
|
|
|
@ -125,6 +125,7 @@ def test_restriction_anon():
|
||||||
"""
|
"""
|
||||||
assert_nodes_equal(expected, node)
|
assert_nodes_equal(expected, node)
|
||||||
|
|
||||||
|
|
||||||
def test_simple_type_list():
|
def test_simple_type_list():
|
||||||
schema = xsd.Schema(load_xml("""
|
schema = xsd.Schema(load_xml("""
|
||||||
<?xml version="1.0"?>
|
<?xml version="1.0"?>
|
||||||
|
|
|
@ -40,13 +40,6 @@ def test_simpletype_parse():
|
||||||
assert item.parse_xmlelement(node) is None
|
assert item.parse_xmlelement(node) is None
|
||||||
|
|
||||||
|
|
||||||
def test_simpletype_xmlvalue():
|
|
||||||
item = types.AnySimpleType()
|
|
||||||
|
|
||||||
with pytest.raises(NotImplementedError):
|
|
||||||
item.xmlvalue(None)
|
|
||||||
|
|
||||||
|
|
||||||
def test_simpletype_pythonvalue():
|
def test_simpletype_pythonvalue():
|
||||||
item = types.AnySimpleType()
|
item = types.AnySimpleType()
|
||||||
|
|
||||||
|
|
|
@ -75,7 +75,6 @@ def test_validate_required_attribute():
|
||||||
result = render_node(container_elm, obj)
|
result = render_node(container_elm, obj)
|
||||||
assert 'The attribute item is not valid: Value is required (container.item)' in str(exc)
|
assert 'The attribute item is not valid: Value is required (container.item)' in str(exc)
|
||||||
|
|
||||||
|
|
||||||
obj.item = 'bar'
|
obj.item = 'bar'
|
||||||
result = render_node(container_elm, obj)
|
result = render_node(container_elm, obj)
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,3 @@
|
||||||
import json
|
|
||||||
import pickle
|
import pickle
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
|
|
Loading…
Reference in New Issue