# HG changeset patch # User Jim Hague # Date 2012-01-11 16:54:29 # Node ID f4c859293ed43b6348d4462493863dd0319807b4 # Parent 012b285cf643db07c52c694db0df82f51d8e4d27 bugzilla: make XMLRPC interface support http and https access Inadvertently support is currently only for https. For some reason I thought xmlrpclib.SafeTransport did http and https, but it is https only. So create http and https XMLRPC transports that retain cookies. Decide which to use by inspecting the Bugzilla URL. diff --git a/hgext/bugzilla.py b/hgext/bugzilla.py --- a/hgext/bugzilla.py +++ b/hgext/bugzilla.py @@ -255,7 +255,7 @@ All the above add a comment to the Bugzi from mercurial.i18n import _ from mercurial.node import short from mercurial import cmdutil, mail, templater, util -import re, time, xmlrpclib +import re, time, urlparse, xmlrpclib class bzaccess(object): '''Base class for access to Bugzilla.''' @@ -473,17 +473,16 @@ class bzmysql_3_0(bzmysql_2_18): # Buzgilla via XMLRPC interface. -class CookieSafeTransport(xmlrpclib.SafeTransport): - """A SafeTransport that retains cookies over its lifetime. +class cookietransportrequest(object): + """A Transport request method that retains cookies over its lifetime. The regular xmlrpclib transports ignore cookies. Which causes a bit of a problem when you need a cookie-based login, as with the Bugzilla XMLRPC interface. - So this is a SafeTransport which looks for cookies being set - in responses and saves them to add to all future requests. - It appears a SafeTransport can do both HTTP and HTTPS sessions, - which saves us having to do a CookieTransport too. + So this is a helper for defining a Transport which looks for + cookies being set in responses and saves them to add to all future + requests. """ # Inspiration drawn from @@ -537,6 +536,18 @@ class CookieSafeTransport(xmlrpclib.Safe return unmarshaller.close() +# The explicit calls to the underlying xmlrpclib __init__() methods are +# necessary. The xmlrpclib.Transport classes are old-style classes, and +# it turns out their __init__() doesn't get called when doing multiple +# inheritance with a new-style class. +class cookietransport(cookietransportrequest, xmlrpclib.Transport): + def __init__(self, use_datetime=0): + xmlrpclib.Transport.__init__(self, use_datetime) + +class cookiesafetransport(cookietransportrequest, xmlrpclib.SafeTransport): + def __init__(self, use_datetime=0): + xmlrpclib.SafeTransport.__init__(self, use_datetime) + class bzxmlrpc(bzaccess): """Support for access to Bugzilla via the Bugzilla XMLRPC API. @@ -553,9 +564,15 @@ class bzxmlrpc(bzaccess): user = self.ui.config('bugzilla', 'user', 'bugs') passwd = self.ui.config('bugzilla', 'password') - self.bzproxy = xmlrpclib.ServerProxy(bzweb, CookieSafeTransport()) + self.bzproxy = xmlrpclib.ServerProxy(bzweb, self.transport(bzweb)) self.bzproxy.User.login(dict(login=user, password=passwd)) + def transport(self, uri): + if urlparse.urlparse(uri, "http")[0] == "https": + return cookiesafetransport() + else: + return cookietransport() + def get_bug_comments(self, id): """Return a string with all comment text for a bug.""" c = self.bzproxy.Bug.comments(dict(ids=[id]))