在Python中执行原始SQL查询时出现问题:sqlalchemy.exc.programmingerror语法错误位于或接近

在Python中执行原始SQL查询时出现问题:sqlalchemy.exc.programmingerror语法错误位于或接近,python,postgresql,sqlalchemy,psycopg2,Python,Postgresql,Sqlalchemy,Psycopg2,我在python脚本中有一个查询,它在创建一些表之后创建一个物化视图 脚本是这样的: from sqlalchemy import create_engine, text sql = '''CREATE MATERIALIZED VIEW schema1.view1 AS         SELECT t1.a,          t1.b,          t1.c,          t2.x AS d        FR

我在python脚本中有一个查询,它在创建一些表之后创建一个物化视图

脚本是这样的:

    from sqlalchemy import create_engine, text

    sql = '''CREATE MATERIALIZED VIEW schema1.view1 AS 
            SELECT t1.a,
              t1.b,
              t1.c,
              t2.x AS d
            FROM schema1.t1 t1
            LEFT JOIN schema1.t2 t2 ON t1.f = t2.f
            UNION ALL
            SELECT t3.a, 
              t3.b, 
              t3.c, 
              t3.d
            FROM schema1.t3 t3;'''

    con=create_engine(db_conn)

    con.execute(sql)
当我直接在数据库上运行时,查询成功执行

postgres=# create schema schema;
CREATE TABLE
postgres=# create table schema.t1 (a varchar, b varchar, c varchar, f integer);
CREATE TABLE
postgres=# create table schema.t2 (x varchar, f integer);
CREATE TABLE
postgres=# create table schema.t3 (a varchar, b varchar, c varchar, d varchar);
CREATE TABLE
postgres=# commit;
但在python中运行脚本时,我得到一个错误:

sqlalchemy.exc.ProgrammingError: (psycopg2.errors.SyntaxError) syntax error at or near "CREATE MATERIALIZED VIEW schema"

我一辈子都搞不清楚它有什么问题-有什么想法吗?

我不知道SQLAlchemy是否支持MView创建,但它是否应该类似或使用特定的元数据函数()

文本函数是为数据库无关的DML而不是DDL设计的。也许它适用于DDL(我不知道SQLAlchemy),但从设计上看,语法与直接在数据库上执行时不同,因为SQLAlchemy将从用户那里提取数据库的细节

如果SQLAlchemy没有提供一些方便的方法,并且您仍然有充分的理由使用SQLAlchemy,那么您可以使用数据库后端能够理解的方言执行纯SQL语句,因此只需省略SQL语句的sqlalchemies
text
函数,如:

   from sqlalchemy import create_engine, text

    sql = '''CREATE MATERIALIZED VIEW schema.view1 AS 
            SELECT t1.a,
              t1.b,
              t1.c
              t2.x AS d
            FROM schema.t1 t1
            LEFT JOIN schema.t2 t2 ON t1.f = t2.f
            UNION ALL
            SELECT t3.a, 
              t3.b, 
              t3.c, 
              t3.d
            FROM schema.t3 t3;'''

    con=create_engine(db_conn)
    con.raw_connection().cursor().execute(sql)
(当然,您必须注意后端类型,而不是SQLAlchemy包装的语句。)


我直接使用psycopg2在我的pg服务器上测试,没有任何问题

postgres=# create schema schema;
CREATE TABLE
postgres=# create table schema.t1 (a varchar, b varchar, c varchar, f integer);
CREATE TABLE
postgres=# create table schema.t2 (x varchar, f integer);
CREATE TABLE
postgres=# create table schema.t3 (a varchar, b varchar, c varchar, d varchar);
CREATE TABLE
postgres=# commit;
使用以下脚本:

#!/usr/bin/python3
import psycopg2;

conn = psycopg2.connect("dbname=postgres")
cur = conn.cursor()
cur.execute("""
            CREATE MATERIALIZED VIEW schema.view1 AS
            SELECT t1.a,
              t1.b,
              t1.c,
              t2.x AS d
            FROM schema.t1 t1
            LEFT JOIN schema.t2 t2 ON t1.f = t2.f
            UNION ALL
            SELECT t3.a,
              t3.b,
              t3.c,
              t3.d
            FROM schema.t3 t3;
""")
conn.commit()
cur.close()
conn.close()
我使用python3.7/2.7的最新版本和psycopg2模块的最新版本以及pgdg的最新库(我有11.5 pg客户端和2.8.3 psycopg2)进行了测试,这些库安装在最近的linux上?你能像我一样直接在psycopg2上执行吗


此外,您是否确保您的点是纯ascii点,就像本例中语句中的所有其他字符一样?(还请记住,unicode中可能存在不可见的代码点,这可能会导致此类问题。)如果使用Python,您可以将字符串转换为ASCII二进制,然后再转换回unicode字符串。如果它没有在
.encode('ASCII')
上引发错误,它应该是干净的。

这是最奇怪的事情。我从另一个工具中复制了我的查询文本,我使用这个工具在我的pg DB中导航到VS代码中。@EOhm回答的最后一部分给了我一个想法,就是用VS代码键入整个内容,而不是复制/粘贴

一切顺利


即使粘贴的文本和我键入的内容在各个方面都是相同的。显然是一些不可见的格式导致了这个问题。

胡乱猜测-您是否尝试从查询的第一行删除
模式。
部分?我不确定是否有必要提供它。@Ilja没有,只是把我的实际查询概念化了。查询直接在PostgreSQL中成功完成,而不是通过Python/sqlalchemy。已更改为“schema1”以避免混淆。@Epion不认为这是问题所在。
t1.c
后缺少逗号,但我怀疑错误消息是否会指向如此远离error@JGH当我在这里输入时只是一个输入错误,如果我包含text()或不包含text(),则没有区别,因此将其从问题中删除。好的,尝试使用原始连接(请参见编辑的最后一行)。我自己从来没有使用过postgres/psycopg2 DBAPI,但如果这仍然不起作用,我至少可以在我这边检查一下(我不愿意学习SQLAlchemy,但无论如何,我很快就需要使用postgres驱动程序的python脚本)@KarlThanks-尝试了同样的错误。根据sqlalchemy上的文档,这实际上是一个DBAPI或psycopg2错误。请看我上面的答案-太奇怪了,感谢您在这方面的帮助。