From 48648eedda50a84f5518ac2055286e1fde22fa00 Mon Sep 17 00:00:00 2001 From: Mike Bayer Date: Thu, 10 May 2007 15:56:31 +0000 Subject: [PATCH] propigated detach() and invalidate() methods to Connection. --- CHANGES | 6 ++++-- lib/sqlalchemy/engine/base.py | 24 ++++++++++++++++++++++++ lib/sqlalchemy/pool.py | 13 +++++++++++++ 3 files changed, 41 insertions(+), 2 deletions(-) diff --git a/CHANGES b/CHANGES index 2e4862d1df..3526f74864 100644 --- a/CHANGES +++ b/CHANGES @@ -1,6 +1,8 @@ - engines - - connections can be detached from their pool, closing on dereference - instead of returning to the pool for reuse + - added detach() to Connection, allows underlying DBAPI connection to be detached + from its pool, closing on dereference/close() instead of being reused by the pool. + - added invalidate() to Connection, immediately invalidates the Connection and its + underlying DBAPI connection. - sql - _Label class overrides compare_self to return its ultimate object. meaning, if you say someexpr.label('foo') == 5, it produces diff --git a/lib/sqlalchemy/engine/base.py b/lib/sqlalchemy/engine/base.py index b3ba657a83..1dfe829347 100644 --- a/lib/sqlalchemy/engine/base.py +++ b/lib/sqlalchemy/engine/base.py @@ -427,6 +427,30 @@ class Connection(Connectable): """contextual_connect() is implemented to return self so that an incoming Engine or Connection object can be treated similarly.""" return self + def invalidate(self): + """invalidate the underying DBAPI connection and immediately close this Connection. + + The underlying DBAPI connection is literally closed (if possible), and is discarded. + Its source connection pool will typically create a new connection to replace it, once + requested. + """ + + self.__connection.invalidate() + self.__connection = None + + def detach(self): + """detach the underlying DBAPI connection from its connection pool. + + This Connection instance will remain useable. When closed, the + DBAPI connection will be literally closed and not returned to its pool. + The pool will typically create a new connection to replace it, once requested. + + This method can be used to insulate the rest of an application from a modified + state on a connection (such as a transaction isolation level or similar). + """ + + self.__connection.detach() + def begin(self): if self.__transaction is None: self.__transaction = self._create_transaction(None) diff --git a/lib/sqlalchemy/pool.py b/lib/sqlalchemy/pool.py index 6ad560e5b3..8915b8098d 100644 --- a/lib/sqlalchemy/pool.py +++ b/lib/sqlalchemy/pool.py @@ -258,6 +258,11 @@ class _ConnectionFairy(object): is_valid = property(lambda self:self.connection is not None) def invalidate(self, e=None): + """Mark this connection as invalidated. + + The connection will be immediately closed. The + containing ConnectionRecord will create a new connection when next used. + """ if self.connection is None: raise exceptions.InvalidRequestError("This connection is closed") if self._connection_record is not None: @@ -284,6 +289,14 @@ class _ConnectionFairy(object): return self def detach(self): + """Separate this Connection from its Pool. + + This means that the connection will no longer be returned to the + pool when closed, and will instead be literally closed. The + containing ConnectionRecord is separated from the DBAPI connection, and + will create a new connection when next used. + """ + if self._connection_record is not None: self._connection_record.connection = None self._pool.do_return_conn(self._connection_record) -- 2.47.2