NOT YET WORKING python3
authorThierry Parmentelat <thierry.parmentelat@inria.fr>
Tue, 16 Apr 2019 13:42:46 +0000 (15:42 +0200)
committerThierry Parmentelat <thierry.parmentelat@inria.fr>
Tue, 16 Apr 2019 13:42:46 +0000 (15:42 +0200)
running out of time to complete transition to python3
I commit this as-is although it won't work

Makefile
sfa/client/sfaserverproxy.py
sfa/server/threadedserver.py
sfa/util/ssl.py

index 90e70de..2c4308c 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -180,7 +180,7 @@ BINS =      ./config/sfa-config-tty ./systemd/sfa-setup.sh \
        $(CLIENTS)
 
 synclib: synccheck
-       +$(RSYNC) --relative ./sfa/ --exclude migrations $(SSHURL)/usr/lib\*/python3.\*/site-packages/
+       +$(RSYNC) --relative ./sfa/ --exclude migrations $(SSHURL)/usr/lib/python3.\*/site-packages/
 syncmigrations:
        +$(RSYNC) ./sfa/storage/migrations/versions/*.py $(SSHURL)/usr/share/sfa/migrations/versions/
 syncbin: synccheck
index 6c11ee0..d1d0910 100644 (file)
@@ -1,7 +1,6 @@
 # XMLRPC-specific code for SFA Client
 
-from sfa.util.ssl import simple_ssl_context
-
+import ssl
 import xmlrpc.client
 import http.client
 
@@ -38,6 +37,15 @@ class ExceptionUnmarshaller(xmlrpc.client.Unmarshaller):
 # targetting only python-2.7 we can get rid of some older code
 
 
+def sfa_client_ssl_context():
+    ssl_context = ssl.SSLContext(ssl.PROTOCOL_TLS)
+    ssl_context.verify_mode = ssl.CERT_NONE
+    ssl_context.check_hostname = False
+#    with open("root.gid") as root:
+#        ssl_context.load_verify_locations(cadata=root.read())
+    return ssl_context
+
+
 class XMLRPCTransport(xmlrpc.client.Transport):
 
     def __init__(self, key_file=None, cert_file=None, timeout=None):
@@ -51,26 +59,31 @@ class XMLRPCTransport(xmlrpc.client.Transport):
         # host may be a string, or a (host, x509-dict) tuple
         host, extra_headers, x509 = self.get_host_info(host)
         conn = http.client.HTTPSConnection(
-            host, None, key_file=self.key_file,
-            cert_file=self.cert_file, context=simple_ssl_context())
-
-        # Some logic to deal with timeouts. It appears that some (or all) versions
-        # of python don't set the timeout after the socket is created. We'll do it
-        # ourselves by forcing the connection to connect, finding the socket, and
-        # calling settimeout() on it. (tested with python 2.6)
-        if self.timeout:
-            if hasattr(conn, 'set_timeout'):
-                conn.set_timeout(self.timeout)
-
-            if hasattr(conn, "_conn"):
-                # HTTPS is a wrapper around HTTPSConnection
-                real_conn = conn._conn
-            else:
-                real_conn = conn
-            conn.connect()
-            if hasattr(real_conn, "sock") and hasattr(real_conn.sock, "settimeout"):
-                real_conn.sock.settimeout(float(self.timeout))
-
+            host, port=None,
+            key_file=self.key_file,
+            cert_file=self.cert_file,
+            timeout=self.timeout,
+            context=sfa_client_ssl_context(),
+            check_hostname=False,
+            )
+
+#        # Some logic to deal with timeouts. It appears that some (or all) versions
+#        # of python don't set the timeout after the socket is created. We'll do it
+#        # ourselves by forcing the connection to connect, finding the socket, and
+#        # calling settimeout() on it. (tested with python 2.6)
+#        if self.timeout:
+#            if hasattr(conn, 'set_timeout'):
+#                conn.set_timeout(self.timeout)
+#
+#            if hasattr(conn, "_conn"):
+#                # HTTPS is a wrapper around HTTPSConnection
+#                real_conn = conn._conn
+#            else:
+#                real_conn = conn
+#            conn.connect()
+#            if hasattr(real_conn, "sock") and hasattr(real_conn.sock, "settimeout"):
+#                real_conn.sock.settimeout(float(self.timeout))
+#
         return conn
 
     def getparser(self):
@@ -87,7 +100,7 @@ class XMLRPCServerProxy(xmlrpc.client.ServerProxy):
         self.url = url
         xmlrpc.client.ServerProxy.__init__(
             self, url, transport, allow_none=allow_none,
-            context=simple_ssl_context(), verbose=verbose)
+            context=sfa_client_ssl_context(), verbose=verbose)
 
     def __getattr__(self, attr):
         logger.debug("xml-rpc %s method:%s" % (self.url, attr))
index 4be1aff..282d632 100644 (file)
@@ -154,6 +154,7 @@ class SecureXMLRpcRequestHandler(xmlrpc.server.SimpleXMLRPCRequestHandler):
 # Taken from the web (XXX find reference). Implements an HTTPS xmlrpc server
 
 
+# xxx should probably use instead http.server.ThreadingHTTPServer
 class SecureXMLRPCServer(http.server.HTTPServer,
                          xmlrpc.server.SimpleXMLRPCDispatcher):
 
@@ -175,13 +176,18 @@ class SecureXMLRPCServer(http.server.HTTPServer,
         self.method_map = {}
         # add cache to the request handler
         HandlerClass.cache = Cache()
+
+        # initialize base classes
+        http.server.HTTPServer.__init__(self, server_address, HandlerClass)
         xmlrpc.server.SimpleXMLRPCDispatcher.__init__(self, True, None)
-        socketserver.BaseServer.__init__(self, server_address, HandlerClass)
+
+        # define SSL context:
+        # require client certificate
         ssl_context = ssl.create_default_context(purpose=ssl.Purpose.CLIENT_AUTH)
+        ssl_context.verify_mode = ssl.CERT_REQUIRED
+        # set local certificate/private key
         ssl_context.load_cert_chain(cert_file, key_file)
-        # If you wanted to verify certs against known CAs..
-        # this is how you would do it
-        # ssl_context.load_verify_locations('/etc/sfa/trusted_roots/plc.gpo.gid')
+        # define trusted roots as CAs
         config = Config()
         trusted_cert_files = TrustedRoots(
             config.get_trustedroots_dir()).get_file_list()
@@ -190,6 +196,7 @@ class SecureXMLRPCServer(http.server.HTTPServer,
             with open(cert_file) as cafile:
                 cadata += cafile.read()
         ssl_context.load_verify_locations(cadata=cadata)
+
 #        ctx.set_verify(SSL.VERIFY_PEER |
 #                       SSL.VERIFY_FAIL_IF_NO_PEER_CERT, verify_callback)
 #        ctx.set_verify_depth(5)
index 6ecf8d4..bb24823 100644 (file)
@@ -3,6 +3,10 @@ import ssl
 def simple_ssl_context():
     """
     an SSL context that turns off server verification
+    this is intended for clients that need to talk
+    to parts of the infra that are known to not have
+    a proper certificate in place, like typically
+    MyPLC and manifold services
     """
     ssl_context = ssl.SSLContext(ssl.PROTOCOL_TLS)
     ssl_context.verify_mode = ssl.CERT_NONE