[connection] move security control logic on Connection
authorPierre-Yves David <pierre-yves.david@logilab.fr>
Mon, 27 May 2013 17:50:55 +0200
changeset 9027 b6b96d61e055
parent 9026 84c5b01ebb3e
child 9028 c88261b641a9
[connection] move security control logic on Connection The _security_enabled context manager now operate on connection. We have to keep a specific entry point in Session to ensure Connection object are properly cleaned up when using session to "manage" Connection live cycle. Related to #2503918
server/session.py
--- a/server/session.py	Fri Jun 14 12:11:42 2013 +0200
+++ b/server/session.py	Mon May 27 17:50:55 2013 +0200
@@ -149,7 +149,7 @@
 class _session_hooks_control(_hooks_control):
     """hook control context manager for session
 
-    Necessary To handle some unholy transaction scope logic."""
+    Necessary to handle some unholy transaction scope logic."""
 
 
     def __init__(self, session, mode, *categories):
@@ -174,9 +174,8 @@
     By default security is disabled on queries executed on the repository
     side.
     """
-    def __init__(self, session, read=None, write=None):
-        self.session = session
-        self.cnx = session._cnx
+    def __init__(self, cnx, read=None, write=None):
+        self.cnx = cnx
         self.read = read
         self.write = write
         self.oldread = None
@@ -197,13 +196,28 @@
 
     def __exit__(self, exctype, exc, traceback):
         self.cnx.ctx_count -= 1
+        if self.oldread is not None:
+            self.cnx.read_security = self.oldread
+        if self.oldwrite is not None:
+            self.cnx.write_security = self.oldwrite
+
+class _session_security_enabled(_security_enabled):
+    """hook security context manager for session
+
+    Necessary To handle some unholy transaction scope logic."""
+
+
+    def __init__(self, session, read=None, write=None):
+        self.session = session
+        super_init = super(_session_security_enabled, self).__init__
+        return super_init(session._cnx, read=read, write=write)
+
+    def __exit__(self, exctype, exc, traceback):
+        super_exit = super(_session_security_enabled, self).__exit__
+        ret = super_exit(exctype, exc, traceback)
         if self.cnx.ctx_count == 0:
             self.session._clear_thread_storage(self.cnx)
-        else:
-            if self.oldread is not None:
-                self.cnx.read_security = self.oldread
-            if self.oldwrite is not None:
-                self.cnx.write_security = self.oldwrite
+        return ret
 
 HOOKS_ALLOW_ALL = object()
 HOOKS_DENY_ALL = object()
@@ -626,6 +640,10 @@
         return self.is_hook_category_activated(hook.category)
 
     # Security management #####################################################
+
+    def security_enabled(self, read=None, write=None):
+        return _security_enabled(self, read=read, write=write)
+
     @property
     def read_security(self):
         return self._read_security
@@ -1058,7 +1076,7 @@
 
 
     def security_enabled(self, read=None, write=None):
-        return _security_enabled(self, read=read, write=write)
+        return _session_security_enabled(self, read=read, write=write)
 
     read_security = cnx_attr('read_security', writable=True)
     write_security = cnx_attr('write_security', writable=True)