]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commit
soft close cursor for Query direct iterator interrupted
authorMike Bayer <mike_mp@zzzcomputing.com>
Tue, 1 Nov 2022 19:09:25 +0000 (15:09 -0400)
committerMike Bayer <mike_mp@zzzcomputing.com>
Thu, 3 Nov 2022 19:56:59 +0000 (15:56 -0400)
commita333d1c3a51099447fab47d3d0d03b3b61c268e4
tree61ff075271cb60d9f5b3cfc798df82678d0922bb
parent996063e5a87f64b4536d441eaa12ba2f8b765a44
soft close cursor for Query direct iterator interrupted

Fixed issue where the underlying DBAPI cursor would not be closed when
using :class:`_orm.Query` and direct iteration, if a user-defined exception
case were raised within the iteration process, interrupting the iterator
which otherwise is not possible to re-use in this context. When using
:meth:`_orm.Query.yield_per` to create server-side cursors, this would lead
to the usual MySQL-related issues with server side cursors out of sync.

To resolve, a catch for ``GeneratorExit`` is applied within the default
iterator, which applies only in those cases where the interpreter is
calling ``.close()`` on the iterator in any case.

A similar scenario can occur when using :term:`2.x` executions with direct
use of :class:`.Result`, in that case the end-user code has access to the
:class:`.Result` itself and should call :meth:`.Result.close` directly.
Version 2.0 will feature context-manager calling patterns to address this
use case.  However within the 1.4 scope, ensured that ``.close()`` methods
are available on all :class:`.Result` implementations including
:class:`.ScalarResult`, :class:`.MappingResult`.

Fixes: #8710
Change-Id: I3166328bfd3900957eb33cbf1061d0495c9df670
doc/build/changelog/unreleased_14/8710.rst [new file with mode: 0644]
lib/sqlalchemy/engine/result.py
lib/sqlalchemy/orm/query.py
test/base/test_result.py
test/orm/test_loading.py
test/orm/test_query.py
test/sql/test_resultset.py