# HG changeset patch # User Paul Boddie # Date 1221425759 -7200 # Node ID 0a3f4b5a51d73649e9c4edf0d7302826b12f429f # Parent 788b7bf56c1eba795085c622564f499e3dfc9cfc Added some XML-RPC methods and properties to the SOAP implementation. Moved the Python value emulation classes into the new libxml2dom.values module. Renamed the SOAP test program. Updated release information. diff -r 788b7bf56c1e -r 0a3f4b5a51d7 PKG-INFO --- a/PKG-INFO Sun Sep 14 02:30:58 2008 +0200 +++ b/PKG-INFO Sun Sep 14 22:55:59 2008 +0200 @@ -1,12 +1,12 @@ Metadata-Version: 1.1 Name: libxml2dom -Version: 0.4.8 +Version: 0.5 Author: Paul Boddie Author-email: paul at boddie org uk Maintainer: Paul Boddie Maintainer-email: paul at boddie org uk Home-page: http://www.boddie.org.uk/python/libxml2dom.html -Download-url: http://www.boddie.org.uk/python/downloads/libxml2dom-0.4.8.tar.gz +Download-url: http://www.boddie.org.uk/python/downloads/libxml2dom-0.5.tar.gz Summary: PyXML-style API for the libxml2 Python bindings License: LGPL (version 3 or later) Description: The libxml2dom package provides a traditional DOM wrapper around the Python diff -r 788b7bf56c1e -r 0a3f4b5a51d7 README.txt --- a/README.txt Sun Sep 14 02:30:58 2008 +0200 +++ b/README.txt Sun Sep 14 22:55:59 2008 +0200 @@ -73,7 +73,8 @@ * Changed some XML-RPC node properties in order to retain underlying DOM properties such as data. * Added convenience methods to the XML-RPC implementation, with combined - node creation and insertion if requested. + node creation and insertion if requested. Introduced similar conveniences + into the SOAP implementation. * Enabled prettyprinting support, finally. New in libxml2dom 0.4.7 (Changes since libxml2dom 0.4.6) diff -r 788b7bf56c1e -r 0a3f4b5a51d7 libxml2dom/soap.py --- a/libxml2dom/soap.py Sun Sep 14 02:30:58 2008 +0200 +++ b/libxml2dom/soap.py Sun Sep 14 22:55:59 2008 +0200 @@ -6,7 +6,7 @@ See: http://www.w3.org/TR/2007/REC-soap12-part0-20070427/ -Copyright (C) 2007 Paul Boddie +Copyright (C) 2007, 2008 Paul Boddie This program is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free @@ -26,13 +26,14 @@ The sending and receiving of SOAP messages can be done using traditional HTTP libraries. -See tests/soap_test.py for more details. +See tests/test_soap.py for more details. """ import libxml2dom from libxml2dom.macrolib import * from libxml2dom.macrolib import \ createDocument as Node_createDocument +from libxml2dom.values import ContentValue, SequenceValue # SOAP-related namespaces. @@ -59,68 +60,6 @@ "SOAP-ENC" : OLD_SOAP_ENCODING_NAMESPACE } -class SOAPImplementation(libxml2dom.Implementation): - - "Contains a SOAP-specific implementation." - - # Wrapping of documents. - - def adoptDocument(self, node): - return SOAPDocument(node, self) - - # Factory functions. - - def get_node(self, _node, context_node): - - """ - Get a libxml2dom node for the given low-level '_node' and libxml2dom - 'context_node'. - """ - - if Node_nodeType(_node) == context_node.ELEMENT_NODE: - - # Make special envelope elements. - - if Node_namespaceURI(_node) in (SOAP_ENVELOPE_NAMESPACE, OLD_SOAP_ENVELOPE_NAMESPACE): - if Node_localName(_node) == "Envelope": - return SOAPEnvelopeElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Header": - return SOAPHeaderElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Body": - return SOAPBodyElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Fault": - return SOAPFaultElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Code": - return SOAPCodeElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Subcode": - return SOAPSubcodeElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Value": - return SOAPValueElement(_node, self, context_node.ownerDocument) - elif Node_localName(_node) == "Text": - return SOAPTextElement(_node, self, context_node.ownerDocument) - - # Detect the method element. - - if Node_parentNode(_node) and Node_localName(Node_parentNode(_node)) == "Body" and \ - Node_namespaceURI(Node_parentNode(_node)) in (SOAP_ENVELOPE_NAMESPACE, OLD_SOAP_ENVELOPE_NAMESPACE): - - return SOAPMethodElement(_node, self, context_node.ownerDocument) - - # Otherwise, make generic SOAP elements. - - return SOAPElement(_node, self, context_node.ownerDocument) - - else: - return libxml2dom.Implementation.get_node(self, _node, context_node) - - # Convenience functions. - - def createSOAPMessage(self, namespaceURI, localName): - - "Create a new SOAP message document (fragment)." - - return SOAPDocument(Node_createDocument(namespaceURI, localName, None), self).documentElement - # Node classes. class SOAPNode(libxml2dom.Node): @@ -140,33 +79,63 @@ ns.update(namespaces or {}) return libxml2dom.Node.xpath(self, expr, variables, ns) - # All nodes support convenience methods. + def add_or_replace_element(self, new_element): + + """ + Add or replace the given 'new_element', using its localName to find any + element to be replaced. + """ + + elements = self.xpath(new_element.localName) + if elements: + self.replaceChild(new_element, elements[0]) + else: + self.appendChild(new_element) + +class SOAPElement(ContentValue, SequenceValue, SOAPNode): + + "A SOAP element." def convert(self, node): return node.textContent.strip() + def values(self): + return [v.contents for v in self.xpath("*")] + def _contents(self): # NOTE: Should check whether this should be a leaf element. if not self.xpath("*"): return (self.localName, getattr(self.ownerDocument, "convert", self.convert)(self)) else: - return (self.localName, SOAPContents(self)) + return (self.localName, self) def __len__(self): - return 2 - - def __getitem__(self, i): - return self.contents[i] + if not self.xpath("*"): + return 2 + else: + return SequenceValue.__len__(self) def __eq__(self, other): - if hasattr(other, "contents"): - return self.contents == other.contents + if not self.xpath("*"): + return ContentValue.__eq__(self, other) else: - return self.contents == other + return SequenceValue.__eq__(self, other) + + def __ne__(self, other): + if not self.xpath("*"): + return ContentValue.__ne__(self, other) + else: + return SequenceValue.__ne__(self, other) + + def __repr__(self): + if self.contents[1] is self: + return "<%s: %r>" % (self.__class__.__name__, self.values()) + else: + return "<%s: %r>" % (self.__class__.__name__, self.contents) # Node construction methods. - def createSOAPElement(self, localName): + def createSOAPElement(self, localName, insert=0): "Create an element with the appropriate namespace and prefix." @@ -176,61 +145,45 @@ name = prefix + ":" + localName else: name = localName - return self.createElementNS(ref_element.namespaceURI, name) + element = self.createElementNS(ref_element.namespaceURI, name) + if insert: + self.appendChild(element) + return element contents = property(_contents) -class SOAPContents(object): - - "A wrapper around another node in order to provide sequence-like access." - - def __init__(self, node): - self.node = node - - def __len__(self): - return len(self.node.xpath("*")) - - def __getitem__(self, i): - return self.node.xpath("*")[i] - - def __eq__(self, other): - for i, j in map(None, self, other): - if i != j: - return False - return True - class SOAPDocument(libxml2dom._Document, SOAPNode): "A SOAP document fragment." def _envelope(self): - return self.xpath("env:Envelope|SOAP-ENV:Envelope")[0] + return (self.xpath("env:Envelope|SOAP-ENV:Envelope") or [None])[0] envelope = property(_envelope) # Convenience methods and properties. def _fault(self): - return self.envelope.body.fault + if self.envelope is not None: + return self.envelope.fault + else: + return None def _method(self): - return self.envelope.body.method + if self.envelope is not None: + return self.envelope.method + else: + return None fault = property(_fault) method = property(_method) -class SOAPElement(SOAPNode): - - "A SOAP element." - - pass - -class SOAPEnvelopeElement(SOAPNode): +class SOAPEnvelopeElement(SOAPElement): "A SOAP envelope element." def _body(self): - return self.xpath("env:Body|SOAP-ENV:Body")[0] + return (self.xpath("env:Body|SOAP-ENV:Body") or [None])[0] def _setBody(self, body): self.appendChild(body) @@ -238,18 +191,40 @@ def _delBody(self): self.removeChild(self.body) - def createBody(self): - return self.createSOAPElement("Body") + # Convenience methods and properties. + + def _fault(self): + if self.body is not None: + return self.body.fault + else: + return None + + def _method(self): + if self.body is not None: + return self.body.method + else: + return None + + fault = property(_fault) + method = property(_method) + + # Node construction methods. + + def createBody(self, insert=0): + element = self.createSOAPElement("Body") + if insert: + self.add_or_replace_element(element) + return element body = property(_body, _setBody, _delBody) -class SOAPHeaderElement(SOAPNode): +class SOAPHeaderElement(SOAPElement): "A SOAP header element." pass -class SOAPBodyElement(SOAPNode): +class SOAPBodyElement(SOAPElement): "A SOAP body element." @@ -264,13 +239,24 @@ # Node construction methods. - def createFault(self): - return self.createSOAPElement("Fault") + def createMethod(self, namespaceURI, name, insert=0): + if self.method is not None: + self.removeChild(self.method) + element = self.createElementNS(namespaceURI, name) + element.setAttributeNS(SOAP_ENVELOPE_NAMESPACE, "env:encodingStyle", SOAP_ENCODING_NAMESPACE) + self.appendChild(element) + return element + + def createFault(self, insert=0): + element = self.createSOAPElement("Fault") + if insert: + self.add_or_replace_element(element) + return element fault = property(_fault) method = property(_method) -class SOAPMethodElement(SOAPNode): +class SOAPMethodElement(SOAPElement): "A SOAP method element." @@ -291,15 +277,22 @@ else: return None + def _parameters(self): + return self.xpath("*") + def _parameterValues(self): - return [value.contents for value in self.xpath("*")] + return self.values() + + def __repr__(self): + return "" % self.parameters methodName = property(_methodName) resultParameter = property(_resultParameter) resultParameterValue = property(_resultParameterValue) parameterValues = property(_parameterValues) + parameters = property(_parameters) -class SOAPFaultElement(SOAPNode): +class SOAPFaultElement(SOAPElement): "A SOAP fault element." @@ -323,15 +316,20 @@ def _detail(self): return (self.xpath("env:Detail|SOAP-ENV:Detail") or [None])[0] - def createCode(self): - return self.createSOAPElement("Code") + # Node construction methods. + + def createCode(self, insert=0): + element = self.createSOAPElement("Code") + if insert: + self.add_or_replace_element(element) + return element code = property(_code) subcode = property(_subcode) reason = property(_reason) detail = property(_detail) -class SOAPSubcodeElement(SOAPNode): +class SOAPSubcodeElement(SOAPElement): "A SOAP subcode element." @@ -351,10 +349,14 @@ self.appendChild(v) v.value = value - def createValue(self, value=None): + # Node construction methods. + + def createValue(self, value=None, insert=0): code_value = self.createSOAPElement("Value") if value is not None: code_value.value = code + if insert: + self.add_or_replace_element(code_value) return code_value value = property(_value, _setValue) @@ -366,12 +368,17 @@ def _subcode(self): return (self.xpath("env:Subcode|SOAP-ENV:Subcode") or [None])[0] - def createSubcode(self): - return self.createSOAPElement("Subcode") + # Node construction methods. + + def createSubcode(self, insert=0): + element = self.createSOAPElement("Subcode") + if insert: + self.add_or_replace_element(element) + return element subcode = property(_subcode) -class SOAPValueElement(SOAPNode): +class SOAPValueElement(SOAPElement): "A SOAP value element." @@ -398,13 +405,76 @@ lang = property(_lang, _setLang) +# Implementation-related functionality. + +class SOAPImplementation(libxml2dom.Implementation): + + "Contains a SOAP-specific implementation." + + # Mapping of element names to wrappers. + + _class_for_name = { + "Envelope" : SOAPEnvelopeElement, + "Header" : SOAPHeaderElement, + "Body" : SOAPBodyElement, + "Fault" : SOAPFaultElement, + "Code" : SOAPCodeElement, + "Subcode" : SOAPSubcodeElement, + "Value" : SOAPValueElement, + "Text" : SOAPTextElement + } + + # Wrapping of documents. + + def adoptDocument(self, node): + return SOAPDocument(node, self) + + # Factory functions. + + def get_node(self, _node, context_node): + + """ + Get a libxml2dom node for the given low-level '_node' and libxml2dom + 'context_node'. + """ + + if Node_nodeType(_node) == context_node.ELEMENT_NODE: + + # Make special envelope elements. + + if Node_namespaceURI(_node) in (SOAP_ENVELOPE_NAMESPACE, OLD_SOAP_ENVELOPE_NAMESPACE): + cls = self._class_for_name[Node_localName(_node)] + return cls(_node, self, context_node.ownerDocument) + + # Detect the method element. + + if Node_parentNode(_node) and Node_localName(Node_parentNode(_node)) == "Body" and \ + Node_namespaceURI(Node_parentNode(_node)) in (SOAP_ENVELOPE_NAMESPACE, OLD_SOAP_ENVELOPE_NAMESPACE): + + return SOAPMethodElement(_node, self, context_node.ownerDocument) + + # Otherwise, make generic SOAP elements. + + return SOAPElement(_node, self, context_node.ownerDocument) + + else: + return libxml2dom.Implementation.get_node(self, _node, context_node) + + # Convenience functions. + + def createSOAPMessage(self): + + "Create a new SOAP message document (fragment)." + + return SOAPDocument(Node_createDocument(SOAP_ENVELOPE_NAMESPACE, "env:Envelope", None), self).documentElement + # Utility functions. createDocument = libxml2dom.createDocument createDocumentType = libxml2dom.createDocumentType -def createSOAPMessage(namespaceURI, localName): - return default_impl.createSOAPMessage(namespaceURI, localName) +def createSOAPMessage(): + return default_impl.createSOAPMessage() def parse(stream_or_string, html=0, htmlencoding=None, unfinished=0, impl=None): return libxml2dom.parse(stream_or_string, html=html, htmlencoding=htmlencoding, unfinished=unfinished, impl=(impl or default_impl)) diff -r 788b7bf56c1e -r 0a3f4b5a51d7 libxml2dom/values.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/libxml2dom/values.py Sun Sep 14 22:55:59 2008 +0200 @@ -0,0 +1,59 @@ +#!/usr/bin/env python + +""" +Python value emulation. + +Copyright (C) 2008 Paul Boddie + +This program is free software; you can redistribute it and/or modify it under +the terms of the GNU Lesser General Public License as published by the Free +Software Foundation; either version 3 of the License, or (at your option) any +later version. + +This program is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more +details. + +You should have received a copy of the GNU Lesser General Public License along +with this program. If not, see . +""" + +class ContentValue: + + """ + Equality support for nodes having contents which should have some + interoperability with normal Python objects. + """ + + def __eq__(self, other): + if hasattr(other, "contents"): + return self.contents == other.contents + else: + return self.contents == other + + def __ne__(self, other): + return not self.__eq__(other) + +class SequenceValue: + + """ + Equality and access support for nodes having sequence-like contents. + """ + + def __eq__(self, other): + for i, j in map(None, self, other): + if i != j: + return False + return True + + def __ne__(self, other): + return not self.__eq__(other) + + def __len__(self): + return len(self.values()) + + def __getitem__(self, i): + return self.values()[i] + +# vim: tabstop=4 expandtab shiftwidth=4 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 libxml2dom/xmlrpc.py --- a/libxml2dom/xmlrpc.py Sun Sep 14 02:30:58 2008 +0200 +++ b/libxml2dom/xmlrpc.py Sun Sep 14 22:55:59 2008 +0200 @@ -40,6 +40,7 @@ createDocument as Node_createDocument import datetime import xml.dom +from libxml2dom.values import ContentValue, SequenceValue # Node classes. @@ -88,38 +89,6 @@ else: raise ValueError, "Value %r cannot be serialised." % value -class ContentEquality: - - "Equality testing." - - def __eq__(self, other): - if hasattr(other, "contents"): - return self.contents == other.contents - else: - return self.contents == other - - def __ne__(self, other): - return not self.__eq__(other) - -class SequenceEquality: - - "Sequence equality testing." - - def __eq__(self, other): - for i, j in map(None, self, other): - if i != j: - return False - return True - - def __ne__(self, other): - return not self.__eq__(other) - - def __len__(self): - return len(self.values()) - - def __getitem__(self, i): - return self.values()[i] - class XMLRPCElement(XMLRPCNode): "An XML-RPC element." @@ -227,7 +196,7 @@ parameterValues = property(_parameterValues, _setParameterValues) parameters = property(_parameters) -class XMLRPCParametersElement(SequenceEquality, XMLRPCNode): +class XMLRPCParametersElement(SequenceValue, XMLRPCNode): """ An XML-RPC parameters/params element. @@ -264,7 +233,7 @@ parameters = property(_parameters) -class XMLRPCParameterElement(ContentEquality, XMLRPCNode): +class XMLRPCParameterElement(ContentValue, XMLRPCNode): """ An XML-RPC parameter/param element. @@ -322,7 +291,7 @@ valueElement = property(_valueElement) contents = property(_contents) -class XMLRPCArrayElement(SequenceEquality, XMLRPCNode): +class XMLRPCArrayElement(SequenceValue, XMLRPCNode): """ An XML-RPC array element. @@ -361,7 +330,7 @@ dataElement = property(_dataElement) contents = property(_contents) -class XMLRPCStructElement(SequenceEquality, XMLRPCNode): +class XMLRPCStructElement(SequenceValue, XMLRPCNode): """ An XML-RPC structure element. @@ -415,7 +384,7 @@ members = property(_members) contents = property(_contents) -class XMLRPCDataElement(SequenceEquality, XMLRPCNode): +class XMLRPCDataElement(SequenceValue, XMLRPCNode): """ An XML-RPC array data element. @@ -522,7 +491,7 @@ valueElement = property(_valueElement) contents = property(_contents) -class XMLRPCStringElement(ContentEquality, XMLRPCNode): +class XMLRPCStringElement(ContentValue, XMLRPCNode): "An XML-RPC string element." diff -r 788b7bf56c1e -r 0a3f4b5a51d7 packages/debian-etch/python-libxml2dom/debian/changelog --- a/packages/debian-etch/python-libxml2dom/debian/changelog Sun Sep 14 02:30:58 2008 +0200 +++ b/packages/debian-etch/python-libxml2dom/debian/changelog Sun Sep 14 22:55:59 2008 +0200 @@ -1,6 +1,12 @@ -libxml2dom (0.4.8-0ubuntu1) stable; urgency=low +libxml2dom (0.5-0ubuntu1) stable; urgency=low - * Added more XML-RPC convenience methods and properties. + * Changed some XML-RPC node properties in order to retain + underlying DOM properties such as data. + * Added convenience methods to the XML-RPC implementation, + with combined node creation and insertion if requested. + Introduced similar conveniences into the SOAP + implementation. + * Enabled prettyprinting support, finally. -- Paul Boddie Wed, 10 Sep 2008 00:31:55 +0200 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 packages/debian-sarge/python2.3-libxml2dom/debian/changelog --- a/packages/debian-sarge/python2.3-libxml2dom/debian/changelog Sun Sep 14 02:30:58 2008 +0200 +++ b/packages/debian-sarge/python2.3-libxml2dom/debian/changelog Sun Sep 14 22:55:59 2008 +0200 @@ -1,6 +1,12 @@ -libxml2dom (0.4.8-0ubuntu1) stable; urgency=low +libxml2dom (0.5-0ubuntu1) stable; urgency=low - * Added more XML-RPC convenience methods and properties. + * Changed some XML-RPC node properties in order to retain + underlying DOM properties such as data. + * Added convenience methods to the XML-RPC implementation, + with combined node creation and insertion if requested. + Introduced similar conveniences into the SOAP + implementation. + * Enabled prettyprinting support, finally. -- Paul Boddie Wed, 10 Sep 2008 00:32:39 +0200 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 packages/ubuntu-feisty/python-libxml2dom/debian/changelog --- a/packages/ubuntu-feisty/python-libxml2dom/debian/changelog Sun Sep 14 02:30:58 2008 +0200 +++ b/packages/ubuntu-feisty/python-libxml2dom/debian/changelog Sun Sep 14 22:55:59 2008 +0200 @@ -1,6 +1,12 @@ -libxml2dom (0.4.8-0ubuntu1) feisty; urgency=low +libxml2dom (0.5-0ubuntu1) feisty; urgency=low - * Added more XML-RPC convenience methods and properties. + * Changed some XML-RPC node properties in order to retain + underlying DOM properties such as data. + * Added convenience methods to the XML-RPC implementation, + with combined node creation and insertion if requested. + Introduced similar conveniences into the SOAP + implementation. + * Enabled prettyprinting support, finally. -- Paul Boddie Wed, 10 Sep 2008 00:33:14 +0200 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 packages/ubuntu-hoary/python2.4-libxml2dom/debian/changelog --- a/packages/ubuntu-hoary/python2.4-libxml2dom/debian/changelog Sun Sep 14 02:30:58 2008 +0200 +++ b/packages/ubuntu-hoary/python2.4-libxml2dom/debian/changelog Sun Sep 14 22:55:59 2008 +0200 @@ -1,6 +1,12 @@ -libxml2dom (0.4.8-0ubuntu1) hoary; urgency=low +libxml2dom (0.5-0ubuntu1) hoary; urgency=low - * Added more XML-RPC convenience methods and properties. + * Changed some XML-RPC node properties in order to retain + underlying DOM properties such as data. + * Added convenience methods to the XML-RPC implementation, + with combined node creation and insertion if requested. + Introduced similar conveniences into the SOAP + implementation. + * Enabled prettyprinting support, finally. -- Paul Boddie Wed, 10 Sep 2008 00:32:59 +0200 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 tests/soap_test.py --- a/tests/soap_test.py Sun Sep 14 02:30:58 2008 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,145 +0,0 @@ -#!/usr/bin/env python -# -*- coding: iso-8859-15 -*- - -import libxml2dom.soap - -request = """ - - - 5 - - - - - FT35ZBQ - - - - Ĺke Jógvan Řyvind - - 123456789099999 - 2005-02 - - - -""" - -req = libxml2dom.soap.parseString(request) -assert req.method.methodName == "chargeReservation" -assert req.method.parameterValues == [ - ("reservation", [("code", "FT35ZBQ")]), - ("creditCard", [("name", u"Ĺke Jógvan Řyvind"), - ("number", "123456789099999"), - ("expiration", "2005-02") - ]) - ] -assert req.fault is None -print "Method name:", req.method.methodName -print "Parameter values:", req.method.parameterValues -print "Fault:", req.fault - -response = """ - - - 5 - - - - FT35ZBQ - - http://travelcompany.example.org/reservations?code=FT35ZBQ - - - -""" - -resp = libxml2dom.soap.parseString(response) -assert resp.method.methodName == "chargeReservationResponse" -assert resp.method.parameterValues == [ - ("code", "FT35ZBQ"), - ("viewAt", "http://travelcompany.example.org/reservations?code=FT35ZBQ") - ] -assert resp.fault is None -print "Method name:", resp.method.methodName -print "Parameter values:", resp.method.parameterValues -print "Fault:", resp.fault - -response2 = """ - - - 5 - - - - m:status - confirmed - FT35ZBQ - - http://travelcompany.example.org/reservations?code=FT35ZBQ - - - -""" - -resp2 = libxml2dom.soap.parseString(response2) -assert resp2.method.methodName == "chargeReservationResponse" -assert resp2.method.parameterValues == [ - ("result", "m:status"), - ("status", "confirmed"), - ("code", "FT35ZBQ"), - ("viewAt", "http://travelcompany.example.org/reservations?code=FT35ZBQ") - ] -assert resp2.fault is None -print "Method name:", resp2.method.methodName -print "Parameter values:", resp2.method.parameterValues -print "Fault:", resp2.fault - -failed = """ - - - - - env:Sender - - rpc:BadArguments - - - - Processing error - Chyba zpracování - - - - Name does not match card number - 999 - - - - -""" - -f = libxml2dom.soap.parseString(failed) -assert f.method is None -assert f.fault.code == "env:Sender" -assert f.fault.subcode == "rpc:BadArguments" -print "Fault code:", f.fault.code - -# vim: tabstop=4 expandtab shiftwidth=4 diff -r 788b7bf56c1e -r 0a3f4b5a51d7 tests/test_soap.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tests/test_soap.py Sun Sep 14 22:55:59 2008 +0200 @@ -0,0 +1,162 @@ +#!/usr/bin/env python +# -*- coding: iso-8859-15 -*- + +import libxml2dom.soap + +request = """ + + + 5 + + + + + FT35ZBQ + + + + Ĺke Jógvan Řyvind + + 123456789099999 + 2005-02 + + + +""" + +req = libxml2dom.soap.parseString(request) +print "Method name:", req.method.methodName +print "Parameter values:", req.method.parameterValues +print "Fault:", req.fault +print +assert req.method.methodName == "chargeReservation" +assert req.method.parameterValues == [ + ("reservation", [("code", "FT35ZBQ")]), + ("creditCard", [("name", u"Ĺke Jógvan Řyvind"), + ("number", "123456789099999"), + ("expiration", "2005-02") + ]) + ] +assert req.fault is None + +response = """ + + + 5 + + + + FT35ZBQ + + http://travelcompany.example.org/reservations?code=FT35ZBQ + + + +""" + +resp = libxml2dom.soap.parseString(response) +print "Method name:", resp.method.methodName +print "Parameter values:", resp.method.parameterValues +print "Fault:", resp.fault +print +print "Request parameters vs. response parameters:" +print req.method.parameters[0][0], resp.method.parameters[0] +print +assert resp.method.methodName == "chargeReservationResponse" +assert resp.method.parameterValues == [ + ("code", "FT35ZBQ"), + ("viewAt", "http://travelcompany.example.org/reservations?code=FT35ZBQ") + ] +assert resp.fault is None +assert req.method.parameters[0][0] == resp.method.parameters[0] + +response2 = """ + + + 5 + + + + m:status + confirmed + FT35ZBQ + + http://travelcompany.example.org/reservations?code=FT35ZBQ + + + +""" + +resp2 = libxml2dom.soap.parseString(response2) +print "Method name:", resp2.method.methodName +print "Parameter values:", resp2.method.parameterValues +print "Fault:", resp2.fault +print +print "Request parameters vs. response parameters:" +print req.method.parameters[0][0], resp2.method.parameters[2] +print +print "Response parameters:" +print resp.method.parameters[0], resp2.method.parameters[2] +print resp.method.parameters[1], resp2.method.parameters[3] +print +assert resp2.method.methodName == "chargeReservationResponse" +assert resp2.method.parameterValues == [ + ("result", "m:status"), + ("status", "confirmed"), + ("code", "FT35ZBQ"), + ("viewAt", "http://travelcompany.example.org/reservations?code=FT35ZBQ") + ] +assert resp2.fault is None +assert req.method.parameters[0][0] == resp2.method.parameters[2] +assert resp.method.parameters[0] == resp2.method.parameters[2] +assert resp.method.parameters[1] == resp2.method.parameters[3] + +failed = """ + + + + + env:Sender + + rpc:BadArguments + + + + Processing error + Chyba zpracování + + + + Name does not match card number + 999 + + + + +""" + +f = libxml2dom.soap.parseString(failed) +print "Fault code:", f.fault.code +assert f.method is None +assert f.fault.code == "env:Sender" +assert f.fault.subcode == "rpc:BadArguments" + +# vim: tabstop=4 expandtab shiftwidth=4