【问题标题】:Join query in PostgreSQL using Python Flask sqlalchemy orm使用 Python Flask sqlalchemy orm 在 PostgreSQL 中加入查询
【发布时间】:2019-05-18 04:24:36
【问题描述】:

我有两张桌子 X 和 Y。

X 有两列 id 和 name, Y 有三列 id, city, country

我需要进行连接查询,并使用 id 获取与其名称对应的城市和国家/地区值。 id 是外键。

我直接在 PostgreSQL 中尝试了这个查询,

select * from x inner join y on x.name = 'xyz'

它给出了准确的结果。但是,虽然在 Python 烧瓶应用程序中使用 sqlalchemy orm 尝试相同的查询,但事实并非如此。我是 Python 和 Flask 框架的新手。我不知道如何实现它。

我在我的模型目录中的一个单独的 python 文件中声明了表定义和序列化函数。

在我的 main.py 文件中,我正在导入该模型并尝试了这种查询,但它不起作用。

from models import x, y

response = x.query.join(y).filter_by(name=name).all()

我收到这样的错误消息,

sqlalchemy.exc.InvalidRequestError

InvalidRequestError:找不到要从中加入的 FROM 子句。尝试加入 <class 'models.y'>,但得到:找不到 'x' 和 'y' 之间的任何外键关系。

【问题讨论】:

标签: python postgresql join flask sqlalchemy


【解决方案1】:

虽然可以像 Elliot 的示例一样完全避免 ORM,但如果数据库很小,ORM 确实有其优势。解决问题最方便的方法是添加relationship。然后,您可以通过以下方式查询结果:

tree = db.session.query(Tree).first()
for leaf in tree.leaves:
    print(leaf.id)

如果您无法创建关系,则连接的正确语法如下:

db.session.query(Leaf).join(Tree,Leaf.tree_id==Tree.id)

【讨论】:

    【解决方案2】:

    如果您更喜欢写出常规的 SQL 语句,那么为什么不使用 SQLAlchemy 来做到这一点。不需要使用joinfilter_by 等链式方法来查询数据库。

    为了回答这个问题,我需要对您的 models 文件中的内容做出一些假设。我假设它是这样的:

    from flask_sqlalchemy import SQLAlchemy
    import datetime
    
    db = SQLAlchemy()
    
    class BaseModel(db.Model):
        """Base data model for all objects"""
        # more code here
    
    class x(BaseModel, db.Model):
        # more table setup code here
    
    class y(BaseModel, db.Model):
        # more table setup code here
    

    如果是这种情况,那么您可以执行以下操作来执行普通的旧参数化 SQL 语句::

    from flask import Flask
    from models import db
    import json
    
    app = Flask(__name__)
    
    app.config['SQLALCHEMY_DATABASE_URI'] = 'your_database_connection_string'
    db.init_app(app)
    
    result = db.session.execute("select * from x inner join y on x.name = :name", {"name":"xyz"})
    
    # If no rows were returned in the result, return an empty list
    if result.returns_rows == False:
        response = []
    
    # Convert the response to a plain list of dicts
    else:
        response = [dict(row.items()) for row in result]
    
    # Output the query result as JSON
    print(json.dumps(response))
    

    我发现这种使用 SQLAlchemy 在 Flash 中运行 SQL 查询的方法比尝试使用您在原始帖子中尝试的所有不同方法链接更容易理解和理解。

    【讨论】:

    • 请注意,result.returns_rows 对于SELECT 始终为真,因此测试是多余的。
    • 这个想法是您也可以使用相同的模式进行插入、更新和删除。
    猜你喜欢
    • 1970-01-01
    • 2021-09-21
    • 1970-01-01
    • 2015-04-13
    • 1970-01-01
    • 2016-12-09
    • 1970-01-01
    • 1970-01-01
    • 2013-07-24
    相关资源
    最近更新 更多