簡體   English   中英

Flask SQLAlchemy:多對多關系錯誤

[英]Flask SQLAlchemy: many to many relationship error

我正在嘗試在 SQLAlchemy 中建立多對多關系,但出現錯誤:

from shopapp import db
db.create_all()

sqlalchemy.exc.NoReferencedTableError: Foreign key associated with column 'shoppinglists_products.shoppinglist_id_v2' could not find table 'shoppinglist' with which to generate a foreign key to target column 'id'

我的代碼:

from sqlalchemy import ForeignKey
from shopapp import db


shoppinglists_products = db.Table("shoppinglists_products",
                                  db.Column("shoppinglist_id", db.Integer, ForeignKey("shoppinglist.id")),
                                  db.Column("product_id", db.Integer, ForeignKey("product.id")))

class ShoppingList(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(20), unique=True, nullable=False)
    products = db.relationship('Product', back_populates="shoppinglists", secondary="shoppinglists_products")


class Product(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(20), unique=True, nullable=False)

問題出在哪里?

似乎 Flask-SQLAlchemy 在查找外鍵引用表時遇到問題。 根據您的代碼,您可以通過以下兩種方法解決此問題:

1) 修復shoppinglists_products表:

Flask-SQLAlchemy 經常將CamelCased模型名稱轉換成類似於這樣的語法: camel_cased 在您的情況下, ShoppingList將被稱為shopping_list 因此,將ForeignKey("shoppinglist.id")更改為ForeignKey("shopping_list.id")就可以了。

shoppinglists_products = db.Table("shoppinglists_products",
             db.Column("shoppinglist_id", db.Integer, ForeignKey("shopping_list.id")), # <-- fixed
                                  

2)更改模型名稱:

如果您願意,您可以繼續將模型名稱從ShoppingList更改為Shopping ,稍后將其稱為shopping 這將防止任何混淆進一步渲染。 通常,開發人員不會經常使用由兩個單詞組合而成的類名,尤其是對於 ORM 案例。 這是因為各種框架有不同的方式來解釋類名來創建表。

擴展@P0intMaN 的答案 - 顯式提供帶有 __tablename__ = "ShoppingList" 的 SQL Alchemy 表名(例如)讓您可以使用您喜歡的案例樣式,並防止 SQLAlchemy 通過更改某種重要的名稱而不告訴您來“幫助”您.

class ShoppingList(db.Model):
    __tablename__ = "ShoppingList"
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(20), unique=True, nullable=False)
    products = db.relationship('Product', back_populates="shoppinglists", secondary="shoppinglists_products")

在許多/大多數 Flask 教程和書籍中,使用了簡單的表名(例如帖子、評論、用戶),從而避免了這個問題。 因此,對於我們這些堅持有意義的 CamelCased 類名的人來說,一個陷阱等待着我們。 此處的文檔中有些隨意地提到了這一點: https ://flask-sqlalchemy.palletsprojects.com/en/2.x/models/

SQLAlchemy 中需要的一些部分在 Flask-SQLAlchemy 中是可選的。 例如,除非被覆蓋,否則會自動為您設置表名。 它派生自轉換為小寫的類名,並將“CamelCase”轉換為“camel_case”。 要覆蓋表名,請設置tablename類屬性。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM