Use opened connections as much as possible
authorSylvain Thénault <sylvain.thenault@logilab.fr>
Tue, 28 Jun 2016 11:03:20 +0200
changeset 11629 0459094d9728
parent 11628 0f12ee84f30a
child 11630 1400aee10df4
Use opened connections as much as possible instead of opening a new internal connection to set the session cookie or retrieve the session data, which may exhaust the connection pools.
pyramid_cubicweb/session.py
--- a/pyramid_cubicweb/session.py	Wed Jun 01 17:27:29 2016 +0200
+++ b/pyramid_cubicweb/session.py	Tue Jun 28 11:03:20 2016 +0200
@@ -1,5 +1,6 @@
 import warnings
 import logging
+from contextlib import contextmanager
 
 from pyramid.compat import pickle
 from pyramid.session import SignedCookieSessionFactory
@@ -21,6 +22,22 @@
     return wrap
 
 
+@contextmanager
+def unsafe_cnx_context_manager(request):
+    """Return a connection for use as a context manager, with security disabled
+
+    If request has an attached connection, its security will be deactived in the context manager's
+    scope, else a new internal connection is returned.
+    """
+    cnx = request.cw_cnx
+    if cnx is None:
+        with request.registry['cubicweb.repository'].internal_cnx() as cnx:
+            yield cnx
+    else:
+        with cnx.security_enabled(read=False, write=False):
+            yield cnx
+
+
 def CWSessionFactory(
         secret,
         cookie_name='session',
@@ -95,7 +112,7 @@
             if self._loaded:
                 return
 
-            with self.repo.internal_cnx() as cnx:
+            with unsafe_cnx_context_manager(self.request) as cnx:
                 value_rset = cnx.execute('Any D WHERE X eid %(x)s, X cwsessiondata D',
                                          {'x': self.sessioneid})
                 value = value_rset[0][0]
@@ -117,7 +134,7 @@
             data = Binary(pickle.dumps(dict(self)))
             sessioneid = self.sessioneid
 
-            with self.repo.internal_cnx() as cnx:
+            with unsafe_cnx_context_manager(self.request) as cnx:
                 if not sessioneid:
                     session = cnx.create_entity(
                         'CWSession', cwsessiondata=data)