使用 AsyncEngine 执行任何 SQL 查询时出现 ObjectNotExecutableError

qew*_*jhb 47 python sqlalchemy python-3.x python-asyncio asyncpg

我正在使用 async_engine。当我尝试执行任何操作时:

async with self.async_engine.connect() as con:
    query = "SELECT id, name FROM item LIMIT 50;"
    result = await con.execute(f"{query}")
Run Code Online (Sandbox Code Playgroud)

我越来越:

Exception has occurred: ObjectNotExecutableError
Not an executable object: 'SELECT id, name FROM item LIMIT 50;'
Run Code Online (Sandbox Code Playgroud)

这个问题之前由用户@stilmaniac提出过,但现在已从SO 中删除

我在谷歌搜索缓存中找到了它,这里是副本

我有同样的问题,所以我重新询问它,但原始版本如下:


我正在尝试从元数据创建表,如下所示:

Base = declarative_base()

properties = Table(
    'properties', Base.metadata,
    # ...
    Column('geolocation', Geography(geometry_type='POINT', srid=4326)),
    # ... 
)

engine = create_async_engine("postgresql+asyncpg://user:password@postgres/")
async with engine.begin() as conn:
    await conn.run_sync(Base.metadata.create_all)
Run Code Online (Sandbox Code Playgroud)

给我以下错误:

sqlalchemy.exc.ObjectNotExecutableError: Not an executable object: 'CREATE INDEX "idx_properties_geolocation" ON "properties" USING GIST ("geolocation")'
Run Code Online (Sandbox Code Playgroud)

考虑这个文档

版本:

  • 操作系统:macOS 11.4 ARM
  • SQLAlchemy:1.4.22
  • 蟒蛇:3.6

sna*_*erb 110

正如异常消息所示,它str 'SELECT id, name FROM item LIMIT 50;'不是可执行对象。要使其可执行,请用sqlalchemy.text包装它。

from sqlalchemy import text

async with self.async_engine.connect() as con:
    query = "SELECT id, name FROM item LIMIT 50;"
    result = await con.execute(text(query))
Run Code Online (Sandbox Code Playgroud)

async.connection.execute要求其语句参数

[...] 始终是 ClauseElement 和 Executable 层次结构中的对象,包括:

  • 选择

  • 插入、更新、删除

  • TextClause 和 TextualSelect

  • DDL 和继承自 DDLElement 的对象

同步connection.execute方法允许原始字符串,但这在v1.4中已被弃用,并已在SQLAlchemy 2.0中删除。


小智 6

这是由于 sqlalchemy 将查询视为字符串,以下解决方法有效

from sqlalchemy import text
query = 'insert into table_name values(1,2,3)'
 with pool.connect() as db_conn:
     db_conn.execute(text(query))
Run Code Online (Sandbox Code Playgroud)