Conversation
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Fix two defects that caused
request.addfinalizer()finalizers to be silently skipped when fixture setup is interrupted by aBaseExceptionsuch asKeyboardInterrupt:src/_pytest/runner.py—runtestprotocol()now runs the item teardown phase in afinallyblock, so teardown (and therefore fixture finalizers) executes even when setup or call re-raises an interruptible exception. Previously theKeyboardInterruptpropagated out of the setup phase and teardown never ran.src/_pytest/fixtures.py—FixtureDef.finish()only short-circuits when the fixture has no cached result and no registered finalizers. A setup interrupted by aBaseExceptionhas no cached result but may still hold pending finalizers; those must run and be cleared instead of being skipped and leaked.Why
Per the documented behavior of
request.addfinalizer(), a finalizer registered during setup must run at teardown no matter how setup completes. Repro:Running this test previously aborted the session with
!!!!!!!! KeyboardInterrupt !!!!!!!!!!!and leftmarker.txtmissing. The finalizers are now executed ([#15067]).Changes
src/_pytest/runner.py: teardown call moved into afinally(keeping the existing#11706behavior for session fail/stop),reportsinitialized before thetry.src/_pytest/fixtures.py:finish()guard nowif self.cached_result is None and not self._finalizers.testing/python/fixtures.py: regression testtest_finalizer_runs_when_setup_interrupted_by_keyboard_interruptasserting the finalizer marker is written afterruntestprotocolre-raisesKeyboardInterrupt.changelog/15067.bugfix.rst.Verified against
pytest's own suite:testing/test_runner.py+testing/python/fixtures.py(312 tests) pass with no new failures.