-
Notifications
You must be signed in to change notification settings - Fork 419
How to do more than one cleanup task in cancelled state? #772
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
Comments
good news magicstack, I found the issue on our end where we were catching an Exception rather than a BaseException, which is as you know where CancelledError derives. /me drives off in his clown car |
although FTR I am still not following yet where "c2" above goes and why it is seemingly not garbage collected. |
Hi Mike! That is a very interesting issue. I think the reason is that, there is no In short, |
@fantix if you run the above program, it runs out of connections. There are like hundreds that are all opened. Where are they ? c2 only points to one of them at a time. does asyncpg have some kind of strong-referencing of connections that aren't closed going on or otherwise some logic that doesn't end the socket when the connection is de-referenced? |
Ah I see what you mean. Looks like without the cancellation, the connection will be recycled properly. 🤔 Looking into it now Hmm no, as soon as the the connection is used, it's not recycled without an explicit |
Aha, looks like there is an asyncio timer handle (300s) to clear some statement cache ( |
The connection will now terminate itself immediately if there is no external reference to it. Refs MagicStack#772
The connection will now terminate itself immediately if there is no external reference to it. Refs #772
the issue with a local PostgreSQL install?: no/ yes
uvloop?: have only tested w/ asyncio directly
We have a user illustrating the case that a task being cancelled will allow us to reach a finally: block where we can at most run only one awaitable cleanup task on asyncpg in order to close out the connection. if we have more than one thing to await, such as emitting a ROLLBACK or anything else, we don't get the chance to close() the connection. It then seems to go into some place where we no longer have any reference to this connection yet asyncpg still leaves it opened; our own GC handlers that are supposed to take care of this are never called.
One way to illustrate it is the use case in such a way that indicates how I'm looking for "how to solve this problem?", of having two separate asycnpg connections that suppose we are doing some kind of work on separately in the same awaitable. if a cancel() is called, I can reach the finally: block, and I can then close at most one of the connections, but not both. in the real case, we are using only one connection but we are trying to emit a ROLLBACK and also do other awaitable things before we get to the .close().
What I dont understand is why gc isn't collecting these connections or why they aren't getting closed.
the stack trace is that we've run out of connections:
The text was updated successfully, but these errors were encountered: