最小例子:
models.py
from flask_sqlalchemy import SQLAlchemy
db = SQLAlchemy()
class Patient(db.Model):
id = db.Column(db.Integer, primary_key=True)
notes = db.relationship("Note", backref=db.backref("patient", lazy=True))
class Note(db.Model):
id = db.Column(db.Integer, primary_key=True)
patient_id = db.Column(db.Integer, db.ForeignKey("patient.id"), nullable=False)
app.py
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
app = Flask(__name__)
app.secret_key = "super secret"
POSTGRES = {
"user": "postgres",
"pw": "password",
"db": "test_db",
"host": "localhost",
"port": "5432",
}
app.config["SQLALCHEMY_DATABASE_URI"] = "postgresql://%(user)s:%(pw)s@%(host)s:%(port)s/%(db)s" % POSTGRES
app.config["SQLALCHEMY_TRACK_MODIFICATIONS"] = False
app.config["DEBUG"] = True
from models import db
with app.app_context():
db.init_app(app)
run.py
from app import app, db
if __name__ == "__main__":
with app.app_context():
db.create_all()
app.run()
但是,我收到以下错误:
sqlalchemy.exc.ProgrammingError: (psycopg2.ProgrammingError) column "id" referenced in foreign key constraint does not exist
[SQL: '\nCREATE TABLE note (\n\tid SERIAL NOT NULL, \n\tpatient_id INTEGER NOT NULL, \n\tPRIMARY KEY (id), \n\tFOREIGN KEY(patient_id) REFERENCES patient (id)\n)\n\n'] (Background on this error at: http://sqlalche.me/e/f405)
当我在psql控制台中使用外键定义表时,它似乎有效。出了什么问题?
答案 0 :(得分:0)
我尝试了您的示例代码(我必须将应用初始化添加到 app.py ,以便您的代码按原样运行)。它按预期工作,并创建了note
和patient
表。
这告诉我你的问题是环保的。我愿意打赌,如果你在Postgres实例中创建了一个全新的测试数据库并运行了你的示例代码,它也适用于你。
因此,让我们关注您要连接的数据库的状态。
您获得的ProgrammingError
例外显示来自Postgres本身的错误。它说它无法创建notes
表,因为没有patient.id
这样的外键。这可能会让您失望,因为您知道 在patient.id
中定义了models.py
密钥。不幸的是,我没有从您发布的内容中获得足够的信息给您一个明确的答案,但我猜是这样的:
Postgres中的patient
表可能已经从之前的运行中创建,但具有不同的模式(例如,可能首先定义时没有id
列)。 create_all()
函数将创建目标数据库中不存在的表,但不会使用修改后的模式更新现有表。
去检查你的Postgres数据库并查看patient
表。它是否实际上有一个id
列被正确定义为主键?
如果您需要这些表格中没有数据,请尝试删除它们并再次运行您的应用程序。我的猜测是它会正确创建两个表并且不会抛出任何错误。