diff --git a/shotgun_api3/shotgun.py b/shotgun_api3/shotgun.py index 7c968c4b8..5525f4409 100755 --- a/shotgun_api3/shotgun.py +++ b/shotgun_api3/shotgun.py @@ -46,6 +46,8 @@ import urllib2 # used for image upload import urlparse import shutil # used for attachment download +import httplib # used for secure file upload +import socket # use relative import for versions >=2.5 and package import for python versions <2.5 if (sys.version_info[0] > 2) or (sys.version_info[0] == 2 and sys.version_info[1] >= 6): @@ -93,6 +95,33 @@ # Version __version__ = "3.0.35" +# ---------------------------------------------------------------------------- +# Self signed certificate connection class + +class ShotgunHTTPSConnection(httplib.HTTPConnection): + "This class allows communication via SSL." + + default_port = httplib.HTTPS_PORT + source_address = None + + def __init__(self, *args, **kwargs): + httplib.HTTPConnection.__init__(self, *args, **kwargs) + self.CERT_FILE = os.environ.get('SHOTGUN_API_CACERTS', None) + + def connect(self): + "Connect to a host on a given (SSL) port." + sock = socket.create_connection((self.host, self.port), + self.timeout, self.source_address) + if self._tunnel_host: + self.sock = sock + self._tunnel() + if not self.CERT_FILE: + self.sock = ssl.wrap_socket(sock) + else: + self.sock = ssl.wrap_socket(sock, + ca_certs=self.CERT_FILE, + cert_reqs=ssl.CERT_REQUIRED) + # ---------------------------------------------------------------------------- # Errors @@ -2486,7 +2515,7 @@ def download_attachment(self, attachment=False, file_path=None, attachment_id=No try: request = urllib2.Request(url) request.add_header('user-agent', "; ".join(self._user_agents)) - req = urllib2.urlopen(request) + req = urllib2.urlopen(request, cafile=os.environ.get('SHOTGUN_API_CACERTS', None)) if file_path: shutil.copyfileobj(req, fp) else: @@ -3801,7 +3830,7 @@ def _send_form(self, url, params): # Helpers from the previous API, left as is. # Based on http://code.activestate.com/recipes/146306/ -class FormPostHandler(urllib2.BaseHandler): +class FormPostHandler(urllib2.HTTPSHandler): """ Handler for multipart form data """ @@ -3855,6 +3884,9 @@ def encode(self, params, files, boundary=None, buffer=None): def https_request(self, request): return self.http_request(request) + def https_open(self, req): + return self.do_open(ShotgunHTTPSConnection, req) + def _translate_filters(filters, filter_operator): """