Open
Description
Expected Behavior
When canceling query, connection should be released back into pool.
Actual Behavior
After canceling query (and catching errors in code) gino_startlette stills throws error asyncpg.exceptions.QueryCanceledError
when trying to release connection.
Steps to Reproduce the Problem
from asyncpg import QueryCanceledError
from fastapi import FastAPI
from gino_starlette import Gino
app = FastAPI()
db = Gino(
app,
kwargs=dict(server_settings=dict(statement_timeout="1")), # cancel query after 1 ms
)
@app.get("/")
async def root():
message = "success"
try:
await db.scalar("SELECT 1")
except QueryCanceledError:
message = "timeout"
return {"message": message}
When called, Endpoint will correctly return {"message": "timeout"}
but app will still throw QueryCanceledError
Traceback (most recent call last):
File "****/site-packages/uvicorn/protocols/http/httptools_impl.py", line 385, in run_asgi
result = await app(self.scope, self.receive, self.send)
File "****/site-packages/uvicorn/middleware/proxy_headers.py", line 45, in __call__
return await self.app(scope, receive, send)
File "****/site-packages/fastapi/applications.py", line 181, in __call__
await super().__call__(scope, receive, send)
File "****/site-packages/starlette/applications.py", line 102, in __call__
await self.middleware_stack(scope, receive, send)
File "****/site-packages/starlette/middleware/errors.py", line 181, in __call__
raise exc from None
File "****/site-packages/starlette/middleware/errors.py", line 159, in __call__
await self.app(scope, receive, _send)
File "****/site-packages/gino_starlette.py", line 83, in __call__
await conn.release()
File "****/site-packages/gino/engine.py", line 300, in release
await dbapi_conn.release(True)
File "****/site-packages/gino/engine.py", line 48, in release
return await self._release()
File "****/site-packages/gino/engine.py", line 84, in _release
await self._pool.release(conn)
File "****/site-packages/gino/dialects/asyncpg.py", line 280, in release
await self._pool.release(conn)
File "****/site-packages/asyncpg/pool.py", line 654, in release
return await asyncio.shield(ch.release(timeout))
File "****/site-packages/asyncpg/pool.py", line 216, in release
raise ex
File "****/site-packages/asyncpg/pool.py", line 206, in release
await self._con.reset(timeout=budget)
File "****/site-packages/asyncpg/connection.py", line 1137, in reset
await self.execute(reset_query, timeout=timeout)
File "****/site-packages/asyncpg/connection.py", line 295, in execute
return await self._protocol.query(query, timeout)
File "asyncpg/protocol/protocol.pyx", line 316, in query
asyncpg.exceptions.QueryCanceledError: canceling statement due to statement timeout
Specifications
- Python version: 3.8
- GINO version: 1.0.1
- Starlette version: 0.1.1
Workarounds
I can suppress the error message when replacing this line
https://github.com/python-gino/gino-starlette/blob/master/src/gino_starlette.py#L83
with this:
try:
await conn.release()
except QueryCanceledError:
pass
But I am not quite sure if this is the best approach
Metadata
Metadata
Assignees
Labels
No labels