Package logilab :: Package common :: Module xmlrpcutils
[frames] | no frames]

Source Code for Module logilab.common.xmlrpcutils

  1  """XML-RPC utilities. 
  2   
  3  :copyright: 2003-2008 LOGILAB S.A. (Paris, FRANCE), all rights reserved. 
  4  :contact: http://www.logilab.fr/ -- mailto:contact@logilab.fr 
  5  :license: General Public License version 2 - http://www.gnu.org/licenses 
  6  """ 
  7  __docformat__ = "restructuredtext en" 
  8   
  9  import xmlrpclib 
 10  from base64 import encodestring 
 11  #from cStringIO import StringIO 
 12   
 13  ProtocolError = xmlrpclib.ProtocolError 
 14   
 15  ## class BasicAuthTransport(xmlrpclib.Transport): 
 16  ##     def __init__(self, username=None, password=None): 
 17  ##         self.username = username 
 18  ##         self.password = password 
 19  ##         self.verbose = None 
 20  ##         self.has_ssl = httplib.__dict__.has_key("HTTPConnection") 
 21   
 22  ##     def request(self, host, handler, request_body, verbose=None): 
 23  ##         # issue XML-RPC request 
 24  ##         if self.has_ssl: 
 25  ##             if host.startswith("https:"): h = httplib.HTTPSConnection(host) 
 26  ##             else: h = httplib.HTTPConnection(host) 
 27  ##         else: h = httplib.HTTP(host) 
 28   
 29  ##         h.putrequest("POST", handler) 
 30   
 31  ##         # required by HTTP/1.1 
 32  ##         if not self.has_ssl: # HTTPConnection already does 1.1 
 33  ##             h.putheader("Host", host) 
 34  ##         h.putheader("Connection", "close") 
 35   
 36  ##         if request_body: h.send(request_body) 
 37  ##         if self.has_ssl: 
 38  ##             response = h.getresponse() 
 39  ##             if response.status != 200: 
 40  ##                 raise xmlrpclib.ProtocolError(host + handler, 
 41  ##                                               response.status, 
 42  ##                                               response.reason, 
 43  ##                                               response.msg) 
 44  ##             file = response.fp 
 45  ##         else: 
 46  ##             errcode, errmsg, headers = h.getreply() 
 47  ##             if errcode != 200: 
 48  ##                 raise xmlrpclib.ProtocolError(host + handler, errcode, 
 49  ##                                               errmsg, headers) 
 50   
 51  ##             file = h.getfile() 
 52   
 53  ##         return self.parse_response(file) 
 54   
 55   
 56   
57 -class AuthMixin:
58 """basic http authentication mixin for xmlrpc transports""" 59
60 - def __init__(self, username, password, encoding):
61 self.verbose = 0 62 self.username = username 63 self.password = password 64 self.encoding = encoding
65
66 - def request(self, host, handler, request_body, verbose=0):
67 """issue XML-RPC request""" 68 h = self.make_connection(host) 69 h.putrequest("POST", handler) 70 # required by XML-RPC 71 h.putheader("User-Agent", self.user_agent) 72 h.putheader("Content-Type", "text/xml") 73 h.putheader("Content-Length", str(len(request_body))) 74 h.putheader("Host", host) 75 h.putheader("Connection", "close") 76 # basic auth 77 if self.username is not None and self.password is not None: 78 h.putheader("AUTHORIZATION", "Basic %s" % encodestring( 79 "%s:%s" % (self.username, self.password)).replace("\012", "")) 80 h.endheaders() 81 # send body 82 if request_body: 83 h.send(request_body) 84 # get and check reply 85 errcode, errmsg, headers = h.getreply() 86 if errcode != 200: 87 raise ProtocolError(host + handler, errcode, errmsg, headers) 88 file = h.getfile() 89 ## # FIXME: encoding ??? iirc, this fix a bug in xmlrpclib but... 90 ## data = h.getfile().read() 91 ## if self.encoding != 'UTF-8': 92 ## data = data.replace("version='1.0'", 93 ## "version='1.0' encoding='%s'" % self.encoding) 94 ## result = StringIO() 95 ## result.write(data) 96 ## result.seek(0) 97 ## return self.parse_response(result) 98 return self.parse_response(file)
99
100 -class BasicAuthTransport(AuthMixin, xmlrpclib.Transport):
101 """basic http authentication transport"""
102
103 -class BasicAuthSafeTransport(AuthMixin, xmlrpclib.SafeTransport):
104 """basic https authentication transport"""
105 106
107 -def connect(url, user=None, passwd=None, encoding='ISO-8859-1'):
108 """return an xml rpc server on <url>, using user / password if specified 109 """ 110 if user or passwd: 111 assert user and passwd is not None 112 if url.startswith('https://'): 113 transport = BasicAuthSafeTransport(user, passwd, encoding) 114 else: 115 transport = BasicAuthTransport(user, passwd, encoding) 116 else: 117 transport = None 118 server = xmlrpclib.ServerProxy(url, transport, encoding=encoding) 119 return server
120