By default Python urllib library don’t support connection via local unix socket, because http.client library, which is used by urllib set IPPROTO_TCP socket type.

In this blog post I will explain how to use local unix socket for your urllib connection.

Why would we need it? In situation you connect to remote host via Ansible using SSH, and later using authenticated sockets. So it’s a way of using secure connection via SSH and not exposing the password via HTTP. The reason we had to use it, was for suds SOAP client for SAP management. SAP administrators are not used to use passwords for SOAP, but are rather used to SSH to SAP machine and execute the specific command, which is levaraing the local unix socket.


Extending the urllib

urllib has handler mechanism. You can write custom handler to handle the connections. We will create the custom handler which will use the local unix socket instead of the TCP socket.

Urllib handler

import http.client
import socket
import urllib.request


class LocalHttpConnection(http.client.HTTPConnection):
    def __init__(self, host, port=None, timeout=socket._GLOBAL_DEFAULT_TIMEOUT,
                 source_address=None, socketpath=None):
        super().__init__(host, port, timeout, source_address)
        self.sock = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
        self.sock.connect(socketpath)


class ExtendedHandler(urllib.request.HTTPHandler):

    def __init__(self, debuglevel=0, socketpath=None):
        self._debuglevel = debuglevel
        self._socketpath = socketpath

    def http_open(self, req):
        return self.do_open(LocalHttpConnection, req, self._socketpath)

suds client

The suds client is a simple SOAP client. The suds client support custom transport method. To use our custom handler in the suds client, just pass the our handler in the suds contructor.

Final code


<
Blog Archive
Archive of all previous blog posts
>
Next Post
A plugin to support SAP authentication in Python Requests