Skip to content

apply warnings filter as soon as possible, and remove it as late as possible #13057

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 20 commits into from
Dec 18, 2024

Conversation

graingert
Copy link
Member

closes #10404

@@ -1112,9 +1112,7 @@ def add_cleanup(self, func: Callable[[], None]) -> None:
def _do_configure(self) -> None:
assert not self._configured
self._configured = True
with warnings.catch_warnings():
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not sure what this was for - it just disables the user specified warning filter during config. We don't want this.

@psf-chronographer psf-chronographer bot added the bot:chronographer:provided (automation) changelog entry is part of PR label Dec 13, 2024
@graingert graingert marked this pull request as ready for review December 13, 2024 10:30
@graingert graingert requested a review from jakkdl December 13, 2024 10:31
@jakkdl
Copy link
Member

jakkdl commented Dec 16, 2024

Wait, test_create_task_unraisable and test_create_task_unraisable_warning_filter has 100% the exact same behavior?

Would be nice with a test for unawaited coroutine, something like #10404 (comment)

Can perhaps also add a test that hits PytestFDWarning to get 100% patch coverage

@graingert
Copy link
Member Author

graingert commented Dec 16, 2024

Wait, test_create_task_unraisable and test_create_task_unraisable_warning_filter has 100% the exact same behavior?

No, test_create_task_unraisable relies on the warning filter set by the host test suite
In test_create_task_unraisable_warning_filter I disable the host pytest warning filter, and configure the child pytest warning filter

Would be nice with a test for unawaited coroutine, something like #10404 (comment)

I make my own object that behaves like an unawaited coro, I don't think it's needed

Can perhaps also add a test that hits PytestFDWarning to get 100% patch coverage

CI absolutely covers this case - without it CI fails. I suspect coverage isn't running on the lsof tests

@jakkdl
Copy link
Member

jakkdl commented Dec 17, 2024

Wait, test_create_task_unraisable and test_create_task_unraisable_warning_filter has 100% the exact same behavior?

No, test_create_task_unraisable relies on the warning filter set by the host test suite In test_create_task_unraisable_warning_filter I disable the host pytest warning filter, and configure the child pytest warning filter

The only line that differs is whether you do pytester.runpytest() vs pytester.runpytest('-Werror'), yeah? If so I think you should at least parametrize the test (or run a loop, or something). And a test with -Wdefault` or something where the outcome of the test changes.

Would be nice with a test for unawaited coroutine, something like #10404 (comment)

I make my own object that behaves like an unawaited coro, I don't think it's needed

It might just be me, but skimming at #10404 + the test I need to spend a minute to figure out how the test functions as a regression test for it. So IMO at least a comment, but would personally have a test that is more obviously equivalent to the issue.

Can perhaps also add a test that hits PytestFDWarning to get 100% patch coverage

CI absolutely covers this case - without it CI fails. I suspect coverage isn't running on the lsof tests

in this case it's not GitHub annotations lying, you don't have 100% patch coverage
https://app.codecov.io/gh/pytest-dev/pytest/pull/13057?dropdown=coverage&src=pr&el=h1
You'd only get a fail if it was lower than the target of 96.32%, and you have 97.14%.
If it's a case of tests not being run in CI then I suppose a # pragma: no cover?

@graingert
Copy link
Member Author

graingert commented Dec 17, 2024

Wait, test_create_task_unraisable and test_create_task_unraisable_warning_filter has 100% the exact same behavior?

No, test_create_task_unraisable relies on the warning filter set by the host test suite In test_create_task_unraisable_warning_filter I disable the host pytest warning filter, and configure the child pytest warning filter

The only line that differs is whether you do pytester.runpytest() vs pytester.runpytest('-Werror'), yeah? If so I think you should at least parametrize the test (or run a loop, or something). And a test with -Wdefault` or something where the outcome of the test changes.

This shouldn't be the case, the filterwarnings mark is also different - it disables the host pytest warning filter

Would be nice with a test for unawaited coroutine, something like #10404 (comment)

I make my own object that behaves like an unawaited coro, I don't think it's needed

It might just be me, but skimming at #10404 + the test I need to spend a minute to figure out how the test functions as a regression test for it. So IMO at least a comment, but would personally have a test that is more obviously equivalent to the issue.

Ok, I suppose it does makes sense to do a more obvious regression test

Can perhaps also add a test that hits PytestFDWarning to get 100% patch coverage

CI absolutely covers this case - without it CI fails. I suspect coverage isn't running on the lsof tests

app.codecov.io/gh/pytest-dev/pytest/pull/13057?dropdown=coverage&src=pr&el=h1

Yeah, what I mean to say is that CI fails without this change because the warning previously was issued too late and so wouldn't trigger an error. Now that it's correctly raised as an error CI fails unless I explicitly ignore it, hence giving it a new type

@jakkdl
Copy link
Member

jakkdl commented Dec 17, 2024

Uh, sorry for not doing a threaded convo as a review. Don't ask me why I didn't.

This shouldn't be the case, the filterwarnings mark is also different - it disables the host pytest warning filter

Ah, derp. I guess a comment or two explaining how they differ would help other people as blind as me.

Yeah, what I mean to say is that CI fails without this change because the warning previously was issued too late and so wouldn't trigger an error. Now that it's correctly raised as an error CI fails unless I explicitly ignore it, hence giving it a new type

right, yeah. Weird it doesn't show up as being covered then. Maybe only hit in a subprocess pytester invokation? If so we can perhaps add a more explicit test case for it

@graingert
Copy link
Member Author

@jakkdl ok I've pushed a new test and some comments

@graingert
Copy link
Member Author

@jakkdl also enabling coverage on lsof tests seems to fix the missing coverage

Copy link
Member

@jakkdl jakkdl left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would be nice if one test (or a separate test) doesn't run with -Werror, but otherwise looks great.

Comment on lines +306 to +313
with _disable_gc():
result = pytester.runpytest("-Werror")

# TODO: should be a test failure or error
assert result.ret == pytest.ExitCode.INTERNAL_ERROR

result.assert_outcomes(passed=1)
result.stderr.fnmatch_lines("RuntimeWarning: coroutine 'my_task' was never awaited")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we run this without -Werror we can check that normal warning functionality works.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah I broke it! Very good catch! I'll send a commit to fix it now

@graingert graingert requested a review from jakkdl December 18, 2024 06:48
Comment on lines -36 to -39
with warnings.catch_warnings(record=True) as log:
# mypy can't infer that record=True means log is not None; help it.
assert log is not None

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looking at typeshed I think the comment was previously incorrect and the assert wasn't needed https://github.com/python/typeshed/blob/54e1c6ad58961c1faebc6842698eec78f1298f92/stdlib/warnings.pyi#L82
But ye with current logic mypy can't infer if record -> log is not None later in the func

@graingert graingert requested a review from jakkdl December 18, 2024 09:52
@jakkdl jakkdl requested a review from nicoddemus December 18, 2024 10:58
@graingert graingert merged commit 868e1d2 into main Dec 18, 2024
28 checks passed
@graingert graingert deleted the apply-warnings-filter-asap-remove-alap branch December 18, 2024 11:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bot:chronographer:provided (automation) changelog entry is part of PR
Projects
None yet
Development

Successfully merging this pull request may close these issues.

pytest.raises swallows warning about unawaited coroutine
2 participants