Skip to content
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

remove multierror #2891

Merged
merged 25 commits into from
Dec 21, 2023
Merged

remove multierror #2891

merged 25 commits into from
Dec 21, 2023

Conversation

jakkdl
Copy link
Member

@jakkdl jakkdl commented Nov 27, 2023

The companion to #2886, see #2785

  • Clean up comments and test names to not refer to multierror [in present tense]
  • update docs
  • add newsfragment
  • and probably some more tests in test_multierror that could be retired.
  • And files/directories referencing "multierror" to be renamed.

Copy link

codecov bot commented Nov 27, 2023

Codecov Report

All modified and coverable lines are covered by tests ✅

Comparison is base (d4ce2f9) 99.49% compared to head (3e485dc) 99.65%.

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #2891      +/-   ##
==========================================
+ Coverage   99.49%   99.65%   +0.16%     
==========================================
  Files         115      115              
  Lines       17704    17310     -394     
  Branches     3158     3110      -48     
==========================================
- Hits        17615    17251     -364     
+ Misses         70       40      -30     
  Partials       19       19              
Files Coverage Δ
src/trio/__init__.py 100.00% <100.00%> (ø)
src/trio/_core/_concat_tb.py 100.00% <100.00%> (ø)
src/trio/_core/_run.py 100.00% <100.00%> (ø)
src/trio/_core/_tests/test_exceptiongroup_gc.py 100.00% <100.00%> (ø)
src/trio/_core/_tests/test_run.py 100.00% <100.00%> (ø)
src/trio/_highlevel_open_tcp_stream.py 100.00% <100.00%> (ø)
src/trio/_tests/test_exports.py 99.60% <ø> (ø)

... and 3 files with indirect coverage changes

@jakkdl jakkdl marked this pull request as ready for review November 28, 2023 15:28
@jakkdl
Copy link
Member Author

jakkdl commented Nov 28, 2023

I experimented with removing the code that's supposedly there to fix test_MultiError_catch_doesnt_create_cyclic_garbage and it didn't seem to break it - but test_locals_destroyed_promptly_on_cancel did start failing.
@A5rocks are those workarounds still needed? Can the cyclic garbage test be retired? Should I change those comments to refer to the destroyed_promptly test instead?

@jakkdl
Copy link
Member Author

jakkdl commented Nov 28, 2023

do we want a newsfragment for now relying on exceptiongroup's apport excepthook monkeypatching?

@richardsheridan
Copy link
Contributor

I experimented with removing the code that's supposedly there to fix test_MultiError_catch_doesnt_create_cyclic_garbage and it didn't seem to break it - but test_locals_destroyed_promptly_on_cancel did start failing. @A5rocks are those workarounds still needed? Can the cyclic garbage test be retired? Should I change those comments to refer to the destroyed_promptly test instead?

Ya these cyclic gc tests have somewhat overlapping behavior, since we made them by tracking down cycles basically one-by-one in various scenarios. I'd say it's not trio's job to check if exception groups create garbage (anymore). The question is whether a similar test exists in the suite for exception groups in cpython or the backport.

@richardsheridan
Copy link
Contributor

Should I change those comments to refer to the destroyed_promptly test instead?

oh and yes please on this

@CoolCat467
Copy link
Member

I totally agree with using python's built in ExceptionGroups, but what about python versions pre-3.11? My worry is for one of my own projects, I support 3.9 and up, but ExceptionGroup doesn't exist pre-3.11.

My particular use case of MultiError:
Shim code:
https://github.com/CoolCat467/Scanner-Server/blob/0a64a32fee92a4b9e3d80ad46d9c9b7fcb595f65/src/sanescansrv/server.py#L68-L71
Main usage:
https://github.com/CoolCat467/Scanner-Server/blob/0a64a32fee92a4b9e3d80ad46d9c9b7fcb595f65/src/sanescansrv/server.py#L645-L657

If I were using 3.11 + I would just use except * but that's not a thing in older python versions.

@CoolCat467
Copy link
Member

I totally agree with using python's built in ExceptionGroups, but what about python versions pre-3.11? My worry is for one of my own projects, I support 3.9 and up, but ExceptionGroup doesn't exist pre-3.11.

My particular use case of MultiError: Shim code: https://github.com/CoolCat467/Scanner-Server/blob/0a64a32fee92a4b9e3d80ad46d9c9b7fcb595f65/src/sanescansrv/server.py#L68-L71 Main usage: https://github.com/CoolCat467/Scanner-Server/blob/0a64a32fee92a4b9e3d80ad46d9c9b7fcb595f65/src/sanescansrv/server.py#L645-L657

If I were using 3.11 + I would just use except * but that's not a thing in older python versions.

Oh I see, we can just use external exceptiongroup module. Sorry about that, I didn't know that was a thing.

Copy link
Member

@CoolCat467 CoolCat467 left a comment

Choose a reason for hiding this comment

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

Looks good other than a few small things I noticed.

src/trio/_core/_concat_tb.py Outdated Show resolved Hide resolved
if not self._strict_exception_groups and len(self._pending_excs) == 1:
return self._pending_excs[0]
return BaseExceptionGroup(
"collapsible" if not self._strict_exception_groups else "TODO",
Copy link
Member

Choose a reason for hiding this comment

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

What needs to be done in TODO here?

Copy link
Member Author

Choose a reason for hiding this comment

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

The exception requires specifying a message, so we probably want some informative message on the cause of the exception or something.

Copy link
Member Author

Choose a reason for hiding this comment

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

Made it a somewhat generic "Exceptions from Trio nursery". Am very open to suggestions for what else could be added.

@CoolCat467
Copy link
Member

Oh I see, we can just use external exceptiongroup module. Sorry about that, I didn't know that was a thing.

Fixed as of CoolCat467/Scanner-Server@9ad2774

@jakkdl
Copy link
Member Author

jakkdl commented Nov 29, 2023

Oh I see, we can just use external exceptiongroup module. Sorry about that, I didn't know that was a thing.

Fixed as of CoolCat467/Scanner-Server@9ad2774

trio also has an exceptiongroup dependency on <3.11

@jakkdl
Copy link
Member Author

jakkdl commented Nov 29, 2023

I experimented with removing the code that's supposedly there to fix test_MultiError_catch_doesnt_create_cyclic_garbage and it didn't seem to break it - but test_locals_destroyed_promptly_on_cancel did start failing. @A5rocks are those workarounds still needed? Can the cyclic garbage test be retired? Should I change those comments to refer to the destroyed_promptly test instead?

Ya these cyclic gc tests have somewhat overlapping behavior, since we made them by tracking down cycles basically one-by-one in various scenarios. I'd say it's not trio's job to check if exception groups create garbage (anymore). The question is whether a similar test exists in the suite for exception groups in cpython or the backport.

I'm not finding anything with a quick search in the backport @agronholm

I'm not familiar with the inner workings of gc and the implementation of multierror/exceptiongroup, but wouldn't the need for such tests depend on the manner of implementation? If the garbage was caused by hacky stuff that multierror needed to do in order to work, and cpython manages to sidestep that completely by implementing stuff """properly""", then there's no direct need for the tests on their side and/or they might have to look quite different.

@agronholm
Copy link
Contributor

I experimented with removing the code that's supposedly there to fix test_MultiError_catch_doesnt_create_cyclic_garbage and it didn't seem to break it - but test_locals_destroyed_promptly_on_cancel did start failing. @A5rocks are those workarounds still needed? Can the cyclic garbage test be retired? Should I change those comments to refer to the destroyed_promptly test instead?

Ya these cyclic gc tests have somewhat overlapping behavior, since we made them by tracking down cycles basically one-by-one in various scenarios. I'd say it's not trio's job to check if exception groups create garbage (anymore). The question is whether a similar test exists in the suite for exception groups in cpython or the backport.

I'm not finding anything with a quick search in the backport @agronholm

I'm not familiar with the inner workings of gc and the implementation of multierror/exceptiongroup, but wouldn't the need for such tests depend on the manner of implementation? If the garbage was caused by hacky stuff that multierror needed to do in order to work, and cpython manages to sidestep that completely by implementing stuff """properly""", then there's no direct need for the tests on their side and/or they might have to look quite different.

I'd add such tests to the backport only as regression tests if such a problem is detected there.

@jakkdl
Copy link
Member Author

jakkdl commented Nov 29, 2023

oh actually, I am getting cyclic garbage test fails in some cases. Will push a commit with updated comments.
EDIT: Ah, it's specifically test_cancel_scope_exit_doesnt_create_cyclic_garbage that can fail, haven't managed to trigger any of the others.

@jakkdl
Copy link
Member Author

jakkdl commented Nov 29, 2023

but test_locals_destroyed_promptly_on_cancel did start failing.

Strangely enough I'm not managing to make this test fail now

@richardsheridan
Copy link
Contributor

Just to be completely clear, every spooky del in the codebase removes a cycle or shortens the lifetime of a strong reference in a way that can be statically reasoned about. Some of these we were clever enough to also create regression tests. I did my best at the time to cross reference these, by going through each del of the PR and commenting out the fix and seeing which test failed, or putting a TODO where nothing failed.

Copy link
Contributor

@richardsheridan richardsheridan left a comment

Choose a reason for hiding this comment

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

I think all the cyclic garbage changes are making sense. Hanging on to test_simple_cancel_scope_usage_doesnt_create_cyclic_garbage even though it maybe can't fail currently is fine IMO since we want to cover outcome and protect future refactoring.

src/trio/_core/_run.py Outdated Show resolved Hide resolved
Copy link
Member

@Zac-HD Zac-HD left a comment

Choose a reason for hiding this comment

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

Two trivial nitpicks, but overall I think this is ready to merge.

I'd also be keen to ship a new version with this change ASAP, so that we can see it working in the wild before shipping #2886. That should reduce the risk of complications for everyone...

src/trio/_core/_tests/test_multierror.py Outdated Show resolved Hide resolved
src/trio/_core/_tests/test_run.py Show resolved Hide resolved
src/trio/_core/_run.py Outdated Show resolved Hide resolved
Copy link
Contributor

@A5rocks A5rocks left a comment

Choose a reason for hiding this comment

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

Sorry about the wait; essentially just nitpicks (even about code you just copied over from elsewhere instead of writing :-) and I paid less attention to the tests.

),
"NonBaseMultiError": _deprecate.DeprecatedAttribute(
value=_NonBaseMultiError,
version="0.22.0",
Copy link
Contributor

Choose a reason for hiding this comment

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

So I guess any release with these should be 0.24.0? Release preparation page says "two months or two releases, whichever is longer") and I assume it means minor releases.

Copy link
Member Author

Choose a reason for hiding this comment

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

makes sense to do major (or whatever 0.X releases are called) release on both this and on #2886 since they can break stuff.

Copy link
Contributor

Choose a reason for hiding this comment

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

I still don't get why Trio doesn't have a 1.0.0 release yet if compatibility guarantees are this stringent anyway.

Copy link
Member

Choose a reason for hiding this comment

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

I'd be inclined to go 1.0 when we've got this and strict-by-default in; I agree but it seems odd to make that release right before some substantial changes.

src/trio/_core/_concat_tb.py Outdated Show resolved Hide resolved
src/trio/_core/_concat_tb.py Outdated Show resolved Hide resolved
src/trio/_core/_concat_tb.py Outdated Show resolved Hide resolved
src/trio/_core/_concat_tb.py Outdated Show resolved Hide resolved
src/trio/_core/_run.py Outdated Show resolved Hide resolved
src/trio/_core/_run.py Outdated Show resolved Hide resolved
Comment on lines +76 to +77
# Unclear if this can still fail, removing the `del` from _concat_tb.copy_tb does not seem
# to trigger it (on a platform where the `del` is executed)
Copy link
Contributor

Choose a reason for hiding this comment

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

Huh, it might be a good idea to remove this test then and add a TODO to that del that it isn't tested for.

It seems like a good idea to try to remove unnecessary dels if things have improved!

Copy link
Member Author

Choose a reason for hiding this comment

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

see #2891 (comment) on removing unnecessary dels.
But copy_tb is possibly an exception since it no longer uses MultiError.

Comment on lines +2387 to +2388
# I don't know if this one can fail anymore, the `del` next to the comment that used to
# refer to this only seems to break test_cancel_scope_exit_doesnt_create_cyclic_garbage
Copy link
Contributor

Choose a reason for hiding this comment

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

Same opinion here as for my other comment. Maybe others have a differing opinion, but rationally I think removing tests is good (though emotionally, not so much :'( ).

Copy link
Member Author

Choose a reason for hiding this comment

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

@richardsheridan said in #2891 (review)

Hanging on to test_simple_cancel_scope_usage_doesnt_create_cyclic_garbage even though it maybe can't fail currently is fine IMO since we want to cover outcome and protect future refactoring.

I'd probably weakly be in favor of removing the test, but if not should probably update the comment to include sheridan's reasoning.

though concat_tb is only used for collapse_exception_group, which is only used for strict_exception_groups=False, which we might deprecate soonish. So not sure there's much future refactoring to consider.

Copy link
Contributor

Choose a reason for hiding this comment

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

Yeah updating the comment would be nice

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 oops, I mixed up the tests - the latter half of my previous comment pertains to test_ExceptionGroup_catch_doesnt_create_cyclic_garbage.
Updated the comment though.

@jakkdl jakkdl requested a review from A5rocks December 20, 2023 15:44
@jakkdl jakkdl merged commit 9fbcb38 into python-trio:master Dec 21, 2023
29 checks passed
@jakkdl jakkdl deleted the multierror_removal branch December 21, 2023 21:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants