Flask中sqlalchemy db.execute()的返回值?

时间:2018-08-07 15:57:01

标签: python sqlalchemy

我的Flask应用已连接到Heroku中的postgres数据库,如下所示:

from flask import Flask, render_template, session, request, url_for, redirect, flash
from flask_session import Session
from sqlalchemy import create_engine
from sqlalchemy.orm import scoped_session, sessionmaker
import os

app = Flask(__name__)

# Check for environment variable
if not os.getenv("DATABASE_URL"):
    raise RuntimeError("DATABASE_URL is not set")

# Configure session to use filesystem
app.config["SESSION_PERMANENT"] = False
app.config["SESSION_TYPE"] = "filesystem"
Session(app)

# Set up database
engine = create_engine(os.getenv("DATABASE_URL"))
db = scoped_session(sessionmaker(bind=engine))

我的Flask方法运行各种SQL语句。我使用的语法通常类似于bk = db.execute("SELECT * FROM books WHERE isbn=:isbn", {"isbn": isbn})

我认为这样的语句的返回值将是字典列表,但是,当我编写一种方法来检查len(bk)时,它说该对象没有长度,即使它应该有长度也是如此。

那么,我收到的返回值是多少,为什么它对Python似乎没有可识别的长度?在任何地方都找不到直接的答案。

2 个答案:

答案 0 :(得分:1)

sqlalchemy将返回懒惰的记录生成器。您不能使用len,但是可以对其进行迭代,它将逐个生成记录以节省内存。如果内存不足或表很小,并且想一次加载所有记录,则可以在其中调用list()

bk = list(bk)

答案 1 :(得分:1)

这是ResultProxy对象,如Session.execute()的文档中所述。它是可迭代的,但没有长度,因为通常不知道在获取所有行之前查询会生成多少行。您可以像在其他答案中一样将其传递给list(),也可以使用其提取方法fetchall()

各个行不是由dict实例表示,而是由RowProxy实例表示。不过,它们的确充当映射的角色,因此您可以将它们作为字典用于大多数目的(例如,序列化为JSON除外)。