00001
00002
00003
00004
00005
00006 from ZSI import _get_element_nsuri_name, SoapWriter, ParsedSoap
00007 from interfaces import HandlerChainInterface
00008 from zope.interface import classProvides, implements, Interface
00009
00010
00011 class DataHandler:
00012 """ str --> ps, sw --> str
00013 class variables:
00014 readerClass -- factory class to create reader for ParsedSoap instances.
00015 """
00016 classProvides(HandlerChainInterface)
00017 readerClass = None
00018
00019 @classmethod
00020 def processRequest(cls, input, **kw):
00021 return ParsedSoap(input, readerclass=cls.readerClass)
00022
00023 @classmethod
00024 def processResponse(cls, sw, **kw):
00025 return str(sw)
00026
00027
00028 class CallbackHandler:
00029 """ ps --> pyobj, pyobj --> sw
00030 class variables:
00031 writerClass -- ElementProxy implementation to use for SoapWriter instances.
00032 """
00033 classProvides(HandlerChainInterface)
00034 writerClass = None
00035
00036 @classmethod
00037 def processRequest(cls, ps, **kw):
00038 """invokes callback that should return a (request,response) tuple.
00039 representing the SOAP request and response respectively.
00040 ps -- ParsedSoap instance representing HTTP Body.
00041 request -- twisted.web.server.Request
00042 """
00043 resource = kw['resource']
00044 request = kw['request']
00045 method = getattr(resource, 'soap_%s' %
00046 _get_element_nsuri_name(ps.body_root)[-1])
00047
00048 try:
00049 req,rsp = method(ps, request=request)
00050 except Exception, ex:
00051 raise
00052
00053 return rsp
00054
00055 @classmethod
00056 def processResponse(cls, output, **kw):
00057 sw = SoapWriter(outputclass=cls.writerClass)
00058 sw.serialize(output)
00059 return sw
00060
00061
00062 class ReverseHandlerChain:
00063
00064 def __init__(self, *handlers):
00065 self.in_handlers = handlers
00066 handlers = list(handlers); handlers.reverse()
00067 self.out_handlers = tuple(handlers)
00068
00069 def processRequest(self, arg, **kw):
00070 for h in self.in_handlers:
00071 arg = h.processRequest(arg, **kw)
00072
00073 return arg
00074
00075 def processResponse(self, arg, **kw):
00076 if arg is None:
00077 return
00078
00079 for h in self.out_handlers:
00080 arg = h.processResponse(arg, **kw)
00081
00082 return arg
00083
00084
00085 class ReverseHandlerChainFactory:
00086 protocol = ReverseHandlerChain
00087
00088 @classmethod
00089 def newInstance(cls):
00090 return cls.protocol(DataHandler, CallbackHandler)
00091