-
Notifications
You must be signed in to change notification settings - Fork 26
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
Exception group stage1 (by @iritkatriel) #20
Conversation
… can double up as a traceback group (avoids the need for subclassing it for the demo)
…m TBG and EG - we take it from the __traceback__ which is set when the EG is raised
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also for @1st1 to review.
Lib/types.py
Outdated
@@ -300,4 +300,81 @@ def wrapped(*args, **kwargs): | |||
NoneType = type(None) | |||
NotImplementedType = type(NotImplemented) | |||
|
|||
class TracebackGroup: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All this new code (TbGroup and ExGroup) should probably live in a separate file, don't you think? types.py should not have actual class definitions (it must be importable blindingly fast).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And also - do we want to keep the names ExceptionGroup and TracebackGroup?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let’s keep these for now.
PS. I’ll be AFK the rest of the day and much of the rest of the week.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK thanks. We'll try to make progress. Unit tests and the like.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Try to make a context manager to handle exceptions, to exercise the join.
Lib/types.py
Outdated
self.__traceback_group__ = TracebackGroup(self.excs, self.frame) | ||
|
||
def split(self, E): | ||
''' returns two new ExceptionGroups: match, rest |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I might as well bring up now that PEP 8 recommends a different style for docstrings (one line summary, blank line, then more text as needed -- or just a one line summary; and always using """
).
Lib/asyncio/taskgroup.py
Outdated
@@ -0,0 +1,282 @@ | |||
# | |||
# This source file is part of the EdgeDB open source project. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm... @1st1, does all this need to stay in the file in case we copy it into the stdlib?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No, I'll contribute it in a clean way under PSFL.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also, FWIW, the current code still doesn't work with EGs properly. If an EG contains a CancelledError, the TaskGroup would propagate the CancelledError, not the EG (thus discarding all other errors). To fix this we'll need to fix the asyncio itself to recognize CancelledErrors wrapped in a EG. I'll do that as soon as we have some basic high-level API.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Which makes me think that taskgroup.py doesn’t belong in this PR.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You're right, I copied it over from the previous branch but will remove.
Lib/types.py
Outdated
def __str__(self): | ||
return f"ExceptionGroup({self.excs})" | ||
|
||
def __repr__(self): | ||
return str(self) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you define just __repr__
, the other will default to that.
Lib/types.py
Outdated
self.__traceback__ = types.TracebackType(None, self.frame, 0, 0) | ||
self.__traceback_group__ = TracebackGroup(self.excs, self.frame) | ||
|
||
def split(self, E): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Now that we have split()
, what do you think join()
will look like? A class method? I was also thinking perhaps it can be spelled as +
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need join? Or do we just make a new list of exceptions (some of which can be EGs) and construct a new EG (which takes care or creating the new TBG)?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure, but if you split and then join, the pieces the result should be the original EG no matter how the split turned out.
output.txt
Outdated
@@ -0,0 +1,112 @@ | |||
Running Release|Win32 interpreter... |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: Do we need this file? They typically go quickly out of sync with the code.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure, I'll remove it and the test script as soon as we have unit tests. Which should be.. soon
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a good start I think.
…pare the whole structure. Added stubs for split tests
…checking tracebacks yet)
…was not raised yet)
…le exception from the group. Use it to simplify the tests
…erging of new and old exceptions
The tests are a bit of a mess still, but their coverage is decent now. |
Not sure we're talking about the same thing. In my version it will be in the traceback unless it returns "naked raise", which makes the catcher return False (as under the current |
Hm, if the handler creates a fresh exception and returns that, IIUC its frame won't be in the traceback; only Basically, don't pay attention to me, I am just talking to myself here. :-) |
I'm talking to myself too, it's called 'conversation'. :) |
At the end of |
I don't see why not. That's a clever trick, doing this in the |
The trick doesn't seem to work for traceback.
Output (I expected f() to not be there):
|
… original exception.
Yeah, I discovered the same thing. Not sure why, possibly it has to do with the separation of exception type, value and traceback (maybe the tb is saved on the thread state while the finally block is running and restored from there, overwriting |
Lib/exception_group.py
Outdated
match, _ = self.project(lambda e: e in keep) | ||
return match | ||
|
||
def extract_traceback(self, exc): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure we need this as part of the API. It's used in the tests and can move there.
Hey all, I've been distracted away from this. I'd like to make sure we don't lose momentum -- I don't want this to just sit here and get stale until the next sprint. So... How are things going here? What should our next step be? How close is this to the proposal Yury wrote up immediately after the sprint? |
I think what we have here implements stage1 of the plan in python/exceptiongroups#9. The next phase of the plan is to integrate the rendering from here into traceback.py. I can try to do that on another branch, unless we think that's premature at this point. |
This PR is stale because it has been open for 30 days with no activity. |
I think we can close this PR - we have a more advanced version of the python-only implementation here: iritkatriel#3 |
Agreed. This is really coming together -- thanks for plowing through! |
This PR is just so I can more easily comment...