Skip to content

Instantly share code, notes, and snippets.

@Icebreaker454
Last active January 12, 2021 12:10
Show Gist options
  • Save Icebreaker454/e22ca806f4b8427f5560277cc32735b7 to your computer and use it in GitHub Desktop.
Save Icebreaker454/e22ca806f4b8427f5560277cc32735b7 to your computer and use it in GitHub Desktop.
SQLAlchemy 1.4 test script
import asyncio
import sqlalchemy as sa
from sqlalchemy import select
from sqlalchemy.ext.declarative import declarative_base, declared_attr
from sqlalchemy.ext.asyncio import create_async_engine, AsyncSession
postgresql_url = "postgresql+asyncpg://localhost:5432/test_sqlalchemy_db"
engine = create_async_engine(postgresql_url, echo=True)
class CustomBase:
@declared_attr
def __tablename__(cls): # noqa
return cls.__name__.lower()
@declared_attr
def id(cls): # noqa
return sa.Column(sa.Integer, primary_key=True)
Base = declarative_base(cls=CustomBase)
class User(Base):
username = sa.Column(sa.String)
email = sa.Column(sa.String)
async def main():
async with engine.begin() as conn:
await conn.run_sync(Base.metadata.create_all)
async with AsyncSession(engine) as session:
async with session.begin():
user = User(username="john_smith")
session.add(user)
# Here we re-fetch the same user
stmt = select(User).filter_by(username="john_smith")
cursor = await session.execute(stmt)
user = cursor.scalar()
# Modify some attrs
user.email = "jsmith@gmail.com"
await session.commit()
# Here goes the greenlet_spawn issue
print(user.username)
async with engine.begin() as conn:
await conn.run_sync(Base.metadata.drop_all)
if __name__ == '__main__':
asyncio.run(main())
@Icebreaker454
Copy link
Author

Icebreaker454 commented Jan 12, 2021

Traceback after line 52:

 Traceback (most recent call last):
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/main.py", line 59, in <module>
    asyncio.run(main())
  File "/usr/local/Cellar/python@3.9/3.9.0_1/Frameworks/Python.framework/Versions/3.9/lib/python3.9/asyncio/runners.py", line 44, in run
    return loop.run_until_complete(main)
  File "/usr/local/Cellar/python@3.9/3.9.0_1/Frameworks/Python.framework/Versions/3.9/lib/python3.9/asyncio/base_events.py", line 642, in run_until_complete
    return future.result()
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/main.py", line 52, in main
    print(user.username)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/attributes.py", line 363, in __get__
    return self.impl.get(state, dict_)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/attributes.py", line 799, in get
    value = state._load_expired(state, passive)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/state.py", line 667, in _load_expired
    self.manager.expired_attribute_loader(self, toload, passive)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/loading.py", line 1397, in load_scalar_attributes
    result = load_on_ident(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/loading.py", line 360, in load_on_ident
    return load_on_pk_identity(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/loading.py", line 511, in load_on_pk_identity
    session.execute(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/orm/session.py", line 1530, in execute
    result = conn._execute_20(statement, params or {}, execution_options)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/base.py", line 1443, in _execute_20
    return meth(self, args_10style, kwargs_10style, execution_options)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/sql/elements.py", line 310, in _execute_on_connection
    return connection._execute_clauseelement(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/base.py", line 1312, in _execute_clauseelement
    ret = self._execute_context(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/base.py", line 1671, in _execute_context
    self._handle_dbapi_exception(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/base.py", line 1856, in _handle_dbapi_exception
    util.raise_(exc_info[1], with_traceback=exc_info[2])
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/util/compat.py", line 180, in raise_
    raise exception
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/base.py", line 1628, in _execute_context
    self.dialect.do_execute(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/engine/default.py", line 663, in do_execute
    cursor.execute(statement, parameters)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/dialects/postgresql/asyncpg.py", line 350, in execute
    self._handle_exception(error)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/dialects/postgresql/asyncpg.py", line 290, in _handle_exception
    self._adapt_connection._handle_exception(error)
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/dialects/postgresql/asyncpg.py", line 511, in _handle_exception
    raise error
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/dialects/postgresql/asyncpg.py", line 346, in execute
    self._adapt_connection.await_(
  File "/Users/icebreaker/Projects/Sandbox/SQLAlchemy1.4-greenlet-spawn-issue/lib/python3.9/site-packages/sqlalchemy/util/_concurrency_py3k.py", line 33, in await_only
    raise exc.InvalidRequestError(
sqlalchemy.exc.InvalidRequestError: greenlet_spawn has not been called; can't call await_() here.
sys:1: RuntimeWarning: coroutine 'AsyncAdapt_asyncpg_cursor._prepare_and_execute' was never awaited

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment