From: <bov...@us...> - 2007-02-01 06:15:25
|
Revision: 1352 http://svn.sourceforge.net/pywebsvcs/?rev=1352&view=rev Author: boverhof Date: 2007-01-31 22:15:24 -0800 (Wed, 31 Jan 2007) Log Message: ----------- M test/wsdl2py/test_EchoWSAddr200403.py M test/wsdl2py/config.txt M test/wsdl2py/ServiceTest.py M test/wsdl2py/servers/EchoWSAddr200403Server.py M ZSI/TC.py M ZSI/fault.py M ZSI/address.py [ 1618810 ] address.py assumes reference parameters, which are optional TC -- Fixed a pyclass problem with ZSI.TC.URI TC -- Simplified Any, AnyElement fault -- Made all faults "lax" processing Modified Paths: -------------- trunk/zsi/ZSI/TC.py trunk/zsi/ZSI/address.py trunk/zsi/ZSI/fault.py trunk/zsi/test/wsdl2py/ServiceTest.py trunk/zsi/test/wsdl2py/config.txt trunk/zsi/test/wsdl2py/servers/EchoWSAddr200403Server.py trunk/zsi/test/wsdl2py/test_EchoWSAddr200403.py Modified: trunk/zsi/ZSI/TC.py =================================================================== --- trunk/zsi/ZSI/TC.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/ZSI/TC.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -516,12 +516,11 @@ logger = _GetLogger('ZSI.TC.Any') parsemap, serialmap = {}, {} - def __init__(self, pname=None, aslist=False, minOccurs=0, **kw): - TypeCode.__init__(self, pname, minOccurs=minOccurs, **kw) + def __init__(self, pname=None, aslist=False, minOccurs=0, unique=False, **kw): + TypeCode.__init__(self, pname, minOccurs=minOccurs, unique=unique, **kw) self.aslist = aslist - self.kwargs = {'aslist':aslist} + self.kwargs = dict(aslist=aslist, unique=unique) self.kwargs.update(kw) - self.unique = False # input arg v should be a list of tuples (name, value). def listify(self, v): @@ -623,13 +622,13 @@ "xsd:anyType[" + str(len(pyobj)) + "]" ) for o in pyobj: #TODO maybe this should take **self.kwargs... - serializer = getattr(o, 'typecode', self.__class__()) # also used by _AnyLax() + serializer = getattr(o, 'typecode', Any()) serializer.serialize(array, sw, o, name='element', **kw) else: struct = elt.createAppendElement(ns, n) for o in pyobj: #TODO maybe this should take **self.kwargs... - serializer = getattr(o, 'typecode', self.__class__()) # also used by _AnyLax() + serializer = getattr(o, 'typecode', Any()) serializer.serialize(struct, sw, o, **kw) return @@ -737,14 +736,13 @@ def text_to_data(self, text, elt, ps): '''text --> typecode specific data. ''' - val = String.text_to_data(self, text, elt, ps) - return urldecode(val) + return String.text_to_data(self, urldecode(text), elt, ps) def get_formatted_content(self, pyobj): '''typecode data --> text ''' - pyobj = String.get_formatted_content(self, pyobj) - return urlencode(pyobj, safe=self.reserved) + return String.get_formatted_content(self, + urlencode(pyobj, safe=self.reserved)) class QName(String): @@ -1352,7 +1350,7 @@ pyclass = GTD(namespaceURI, typeName) if not pyclass: if _is_xsd_or_soap_ns(namespaceURI): - pyclass = _AnyStrict + pyclass = Any elif (str(namespaceURI).lower()==str(Apache.Map.type[0]).lower())\ and (str(typeName).lower() ==str(Apache.Map.type[1]).lower()): pyclass = Apache.Map @@ -1402,13 +1400,13 @@ tc = (types.ClassType, pyobj.__class__.__name__) what = Any.serialmap.get(tc) + self.logger.debug('processContents: %s', self.processContents) + # failed to find a registered type for class if what is None: #TODO: seems incomplete. what about facets. - if self.processContents == 'strict': - what = _AnyStrict(pname=(self.nspname,self.pname)) - else: - what = _AnyLax(pname=(self.nspname,self.pname)) + #if self.processContents == 'strict': + what = Any(pname=(self.nspname,self.pname)) self.logger.debug('serialize with %s', what.__class__.__name__) what.serialize(elt, sw, pyobj, **kw) @@ -1455,25 +1453,36 @@ if skip: what = XML(pname=(nspname,pname), wrapped=False) elif self.processContents == 'lax': - what = _AnyLax(pname=(nspname,pname)) + what = Any(pname=(nspname,pname), unique=True) else: - what = _AnyStrict(pname=(nspname,pname)) + what = Any(pname=(nspname,pname), unique=True) try: - return what.parse(elt, ps) + pyobj = what.parse(elt, ps) except EvaluateException, ex: self.logger.debug("error parsing: %s" %str(ex)) - if len(_children(elt)) == 0: + if len(_children(elt)) != 0: + self.logger.debug('parse <any>, return as dict') + return Any(aslist=False).parse_into_dict_or_list(elt, ps) + self.logger.debug("Give up, parse (%s,%s) as a String", what.nspname, what.pname) what = String(pname=(nspname,pname), typed=False) return WrapImmutable(what.parse(elt, ps), what) - self.logger.debug('parse <any>, return as dict') - return Any(aslist=False).parse_into_dict_or_list(elt, ps) + if pyobj is None: + return + try: + pyobj.typecode = what + except AttributeError: + pyobj = WrapImmutable(pyobj, what) + return pyobj + + + class Union(SimpleType): '''simpleType Union @@ -1667,113 +1676,6 @@ el.createAppendTextNode(s.getvalue()) -class _AnyStrict(Any): - ''' Handles an unspecified types when using a concrete schemas and - processContents = "strict". - ''' - #WARNING: unstable - logger = _GetLogger('ZSI.TC._AnyStrict') - - def __init__(self, pname=None, aslist=False, **kw): - Any.__init__(self, pname=pname, aslist=aslist, **kw) - self.unique = True - - def serialize(self, elt, sw, pyobj, name=None, **kw): - if not (type(pyobj) is dict and not self.aslist): - Any.serialize(self, elt=elt,sw=sw,pyobj=pyobj,name=name, **kw) - - raise EvaluateException( - 'Serializing dictionaries not implemented when processContents=\"strict\".' + - 'Try as a list or use processContents=\"lax\".' - ) - - -class _AnyLax(Any): - ''' Handles unspecified types when using a concrete schemas and - processContents = "lax". - ''' - logger = _GetLogger('ZSI.TC._AnyLax') - - def __init__(self, pname=None, aslist=False, **kw): - Any.__init__(self, pname=pname, aslist=aslist, **kw) - self.unique = True - - def parse_into_dict_or_list(self, elt, ps): - c = _child_elements(elt) - count = len(c) - v = [] - if count == 0: - href = _find_href(elt) - if not href: return {} - elt = ps.FindLocalHREF(href, elt) - self.checktype(elt, ps) - c = _child_elements(elt) - count = len(c) - if count == 0: return self.listify([]) - if self.nilled(elt, ps): return Nilled - - # group consecutive elements with the same name together - # We treat consecutive elements with the same name as lists. - groupedElements = [] # tuples of (name, elementList) - previousName = "" - currentElementList = None - for ce in _child_elements(elt): - name = ce.localName - if (name != previousName): # new name, so new group - if currentElementList != None: # store previous group if there is one - groupedElements.append( (previousName, currentElementList) ) - currentElementList = list() - currentElementList.append(ce) # append to list - previousName = name - # add the last group if necessary - if currentElementList != None: # store previous group if there is one - groupedElements.append( (previousName, currentElementList) ) - - # parse the groups of names - if len(groupedElements) < 1: # should return earlier - return None - # return a list if there is one name and multiple data - elif (len(groupedElements) == 1) and (len(groupedElements[0][0]) > 1): - self.aslist = False - # else return a dictionary - - for name,eltList in groupedElements: - lst = [] - for elt in eltList: - #aslist = self.aslist - lst.append( self.parse(elt, ps) ) - #self.aslist = aslist # restore the aslist setting - if len(lst) > 1: # consecutive elements with the same name means a list - v.append( (name, lst) ) - elif len(lst) == 1: - v.append( (name, lst[0]) ) - - return self.listify(v) - - def checkname(self, elt, ps): - '''See if the name and type of the "elt" element is what we're - looking for. Return the element's type. - Since this is _AnyLax, it's ok if names don't resolve. - ''' - - parselist,errorlist = self.get_parse_and_errorlist() - ns, name = _get_element_nsuri_name(elt) - if ns == SOAP.ENC: - if parselist and \ - (None, name) not in parselist and (ns, name) not in parselist: - raise EvaluateException( - 'Element mismatch (got %s wanted %s) (SOAP encoding namespace)' % \ - (name, errorlist), ps.Backtrace(elt)) - return (ns, name) - - # Not a type, check name matches. - if self.nspname and ns != self.nspname: - raise EvaluateException('Element NS mismatch (got %s wanted %s)' % \ - (ns, self.nspname), ps.Backtrace(elt)) - - return self.checktype(elt, ps) - - def RegisterType(C, clobber=0, *args, **keywords): instance = apply(C, args, keywords) for t in C.__dict__.get('parselist', []): @@ -1800,6 +1702,7 @@ str(C) + ' duplicating serial registration for ' + str(t)) Any.serialmap[key] = instance + def _DynamicImport(moduleName, className): ''' Utility function for RegisterTypeWithSchemaAndClass Modified: trunk/zsi/ZSI/address.py =================================================================== --- trunk/zsi/ZSI/address.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/ZSI/address.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -183,19 +183,14 @@ raise EvaluateException, 'endPointReference must be of type %s' \ %GTD(namespaceURI ,'EndpointReferenceType') - ReferenceProperties = endPointReference._ReferenceProperties - any = ReferenceProperties._any or [] - #if not (what.maxOccurs=='unbounded' and type(any) in _seqtypes): - # raise EvaluateException, 'ReferenceProperties <any> assumed maxOccurs unbounded' + ReferenceProperties = getattr(endPointReference, '_ReferenceProperties', None) + if ReferenceProperties is not None: + for v in getattr(ReferenceProperties, '_any', ()): + if not hasattr(v,'typecode'): + raise EvaluateException, '<any> element, instance missing typecode attribute' - for v in any: - if not hasattr(v,'typecode'): - raise EvaluateException, '<any> element, instance missing typecode attribute' + pyobjs.append(v) - pyobjs.append(v) - - #pyobjs.append(v) - self.header_pyobjs = tuple(pyobjs) def setResponseFromWSAddress(self, address, localURL): @@ -249,83 +244,6 @@ self._from = pyobjs[(namespaceURI,elements[3])] self._relatesTo = pyobjs[(namespaceURI,elements[4])] -# TODO: Remove MessageContainer. Hopefully the new <any> functionality -# makes this irrelevant. But could create an Interop problem. -""" -class MessageContainer: - '''Automatically wraps all primitive types so attributes - can be specified. - ''' - class IntHolder(int): pass - class StrHolder(str): pass - class UnicodeHolder(unicode): pass - class LongHolder(long): pass - class FloatHolder(float): pass - class BoolHolder(int): pass - #class TupleHolder(tuple): pass - #class ListHolder(list): pass - typecode = None - pyclass_list = [IntHolder,StrHolder,UnicodeHolder,LongHolder, - FloatHolder,BoolHolder,] - def __setattr__(self, key, value): - '''wrap all primitives with Holders if present. - ''' - if type(value) in _seqtypes: - value = list(value) - for indx in range(len(value)): - try: - item = self._wrap(value[indx]) - except TypeError, ex: - pass - else: - value[indx] = item - elif type(value) is bool: - value = BoolHolder(value) - else: - try: - value = self._wrap(value) - except TypeError, ex: - pass - self.__dict__[key] = value - def _wrap(self, value): - '''wrap primitive, return None - ''' - if value is None: - return value - for pyclass in self.pyclass_list: - if issubclass(value.__class__, pyclass): break - else: - raise TypeError, 'MessageContainer does not know about type %s' %(type(value)) - return pyclass(value) - - def setUp(self, typecode=None, pyclass=None): - '''set up all attribute names (aname) in this python instance. - If what is a ComplexType or a simpleType w/attributes instantiate - a new MessageContainer, else set attribute aname to None. - ''' - if typecode is None: - typecode = self.typecode - else: - self.typecode = typecode - - if not isinstance(typecode, TypeCode): - raise TypeError, 'typecode must be a TypeCode class instance' - - if isinstance(typecode, ComplexType): - if typecode.has_attributes() is True: - setattr(self, typecode.attrs_aname, {}) - if typecode.mixed is True: - setattr(self, typecode.mixed_aname, None) - for what in typecode.ofwhat: - setattr(self, what.aname, None) - if isinstance(what, ComplexType): - setattr(self, what.aname, MessageContainer()) - getattr(self, what.aname).setUp(typecode=what) - else: - raise TypeError, 'Primitive type' -""" - - if __name__ == '__main__': print _copyright Modified: trunk/zsi/ZSI/fault.py =================================================================== --- trunk/zsi/ZSI/fault.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/ZSI/fault.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -35,7 +35,7 @@ String(pname='faultstring'), URI(pname=(SOAP.ENV,'faultactor'), minOccurs=0), Detail.typecode, - AnyElement(aname='any',minOccurs=0, maxOccurs=UNBOUNDED), + AnyElement(aname='any',minOccurs=0, maxOccurs=UNBOUNDED, processContents="lax"), ], pname=(SOAP.ENV,'Fault'), inline=True, @@ -48,7 +48,7 @@ ZSIHeaderDetail.typecode =\ Struct(ZSIHeaderDetail, - [AnyElement(aname='any', minOccurs=0, maxOccurs=UNBOUNDED)], + [AnyElement(aname='any', minOccurs=0, maxOccurs=UNBOUNDED, processContents="lax")], pname=(ZSI_SCHEMA_URI, 'detail')) Modified: trunk/zsi/test/wsdl2py/ServiceTest.py =================================================================== --- trunk/zsi/test/wsdl2py/ServiceTest.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/test/wsdl2py/ServiceTest.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -34,7 +34,7 @@ SECTION_DISPATCH = 'dispatch' TRACEFILE = sys.stdout TOPDIR = os.getcwd() -MODULEDIR = TOPDIR + '/stubs' +MODULEDIR = os.path.join(TOPDIR, 'stubs') SECTION_SERVERS = 'servers' CONFIG_PARSER.read(CONFIG_FILE) Modified: trunk/zsi/test/wsdl2py/config.txt =================================================================== --- trunk/zsi/test/wsdl2py/config.txt 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/test/wsdl2py/config.txt 2007-02-01 06:15:24 UTC (rev 1352) @@ -19,7 +19,7 @@ # ########################################################################## [configuration] -tracefile = False +tracefile = 1 debug = False skip = False twisted = False Modified: trunk/zsi/test/wsdl2py/servers/EchoWSAddr200403Server.py =================================================================== --- trunk/zsi/test/wsdl2py/servers/EchoWSAddr200403Server.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/test/wsdl2py/servers/EchoWSAddr200403Server.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -6,6 +6,7 @@ import sys from ZSI.ServiceContainer import AsServer from EchoWSAddr200403Server_server import EchoWSAddr200403Server as EchoServer +from ZSI.schema import GTD """ EchoServer example service @@ -14,10 +15,20 @@ """ +EndpointReferenceType = GTD('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReferenceType') + + class WSAService(EchoServer): def wsa_Echo(self, ps, addr): response = EchoServer.wsa_Echo(self, ps, addr) response.EchoResult = self.request.EchoIn + + if isinstance(response.EchoResult, EndpointReferenceType): + addr1 = response.EchoResult + for a in addr.Any: + if a not in addr1.ReferenceProperties.Any: + raise RuntimeError, 'EPRs dont match' + return response Modified: trunk/zsi/test/wsdl2py/test_EchoWSAddr200403.py =================================================================== --- trunk/zsi/test/wsdl2py/test_EchoWSAddr200403.py 2007-01-30 20:03:06 UTC (rev 1351) +++ trunk/zsi/test/wsdl2py/test_EchoWSAddr200403.py 2007-02-01 06:15:24 UTC (rev 1352) @@ -5,7 +5,9 @@ ########################################################################### import os, sys, unittest from ServiceTest import main, ServiceTestCase, ServiceTestSuite -from ZSI import FaultException +from ZSI import FaultException, TC +from ZSI.schema import GED, GTD + """ Unittest @@ -46,9 +48,7 @@ def __init__(self, methodName): ServiceTestCase.__init__(self, methodName) - self.wsdl2py_args.append('-a') - self.wsdl2py_args.append('-b') - self.wsdl2dispatch_args.append('-a') + self.wsdl2py_args.append('-ab') def getPortKWArgs(self): kw = ServiceTestCase.getPortKWArgs(self) @@ -68,7 +68,73 @@ rsp = port.Echo(msg) self.failUnless(rsp.EchoResult == msg.EchoIn, "Bad Echo") + def test_dispatch_Echo_MIH_EPR(self): + epr = GED('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReference').pyclass() + epr.Address = 'urn:whatever' + loc = self.client_module.EchoWSAddr200403ServerLocator() + port = loc.getport(endPointReference=epr, **self.getPortKWArgs()) + + msg = self.client_module.EchoRequest() + msg.EchoIn = 1 + rsp = port.Echo(msg) + self.failUnless(rsp.EchoResult == msg.EchoIn, "Bad Echo") + + def test_dispatch_Echo_MIH_EPR2(self): + epr = GED('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReference').pyclass() + epr.Address = 'urn:whatever' + epr.ReferenceProperties = epr.new_ReferenceProperties() + + loc = self.client_module.EchoWSAddr200403ServerLocator() + port = loc.getport(endPointReference=epr, **self.getPortKWArgs()) + + msg = self.client_module.EchoRequest() + msg.EchoIn = 1 + rsp = port.Echo(msg) + self.failUnless(rsp.EchoResult == msg.EchoIn, "Bad Echo") + + def test_dispatch_Echo_MIH_EPR3_BadHeader(self): + """Unqualified element "mystr" in Header + """ + epr = GED('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReference').pyclass() + epr.Address = 'urn:whatever' + epr.ReferenceProperties = epr.new_ReferenceProperties() + class Xstr(str): + typecode = TC.String('mystr') + + epr.ReferenceProperties.Any = [Xstr('whatever'),] + + loc = self.client_module.EchoWSAddr200403ServerLocator() + self._setUpDispatch() + port = loc.getport(endPointReference=epr, **self.getPortKWArgs()) + + msg = self.client_module.EchoRequest() + self.failUnlessRaises(FaultException, port.Echo,msg) + + def test_dispatch_Echo_MIH_EPR3(self): + epr = GED('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReference').pyclass() + epr.Address = 'urn:whatever' + epr.ReferenceProperties = epr.new_ReferenceProperties() + class Xstr(str): + typecode = TC.String(('urn:josh','mystr')) + + epr.ReferenceProperties.Any = [Xstr('whatever'),] + + loc = self.client_module.EchoWSAddr200403ServerLocator() + self._setUpDispatch() + port = loc.getport(endPointReference=epr, **self.getPortKWArgs()) + + msg = self.client_module.EchoRequest() + epr2 = GTD('http://schemas.xmlsoap.org/ws/2004/03/addressing','EndpointReferenceType')(None).pyclass() + epr2.Address = epr.Address + epr2.ReferenceProperties = epr.ReferenceProperties + + msg.EchoIn = epr2 + rsp = port.Echo(msg) + self.failUnless(rsp.EchoResult.Address == msg.EchoIn.Address, "Bad Echo") + self.failUnless(rsp.EchoResult.ReferenceProperties.Any == msg.EchoIn.ReferenceProperties.Any, "Bad Echo") + + if __name__ == "__main__" : main() This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |