[英]Insert Data in PostgreSQL with plpgsql functions using sqlAlchemy and python
我是数据库和 sqlAlchemy 的新手,这可能是一个简单或愚蠢的问题。 但我找不到任何解决方案。
我有一个现有项目,我正在尝试更改当前实现以使用 SQLAlchemy。
我的问题是代码运行时没有错误,我收到了一个唯一的作业 ID,我在返回的数据中看到了它。 但是我在数据库中没有条目。 因为我使用无连接执行,所以我认为我可以这样调用函数。
现有的 .sql 文件:
CREATE TYPE job_status_type AS ENUM (
'SCHEDULED', 'SUCCESS', 'ERROR', 'CANCELLED', 'MISSED'
);
CREATE TABLE job (
id SERIAL PRIMARY KEY,
user_id INTEGER REFERENCES user(id),
param_id TEXT REFERENCES param(id),
proc_name TEXT,
status job_status_type DEFAULT 'SCHEDULED',
run_date TIMESTAMPTZ DEFAULT current_timestamp
);
CREATE OR REPLACE FUNCTION check_job_run_date() RETURNS TRIGGER AS $check_job_run_date$
BEGIN
if NEW.run_date < (current_timestamp - INTERVAL '1 second') THEN
RAISE 'job_run_date_in_past';
END IF;
RETURN NEW;
END;
$check_job_run_date$ LANGUAGE plpgsql;
CREATE TRIGGER check_job_run_date BEFORE INSERT ON job
FOR EACH ROW EXECUTE PROCEDURE check_job_run_date();
CREATE OR REPLACE FUNCTION add_job(INTEGER, TEXT, TEXT, TIMESTAMPTZ) RETURNS SETOF job AS $$
DECLARE
new_id INTEGER;
BEGIN
INSERT INTO job (user_id, param_id, proc_name, run_date)
VALUES ($1, $2, $3, $4) RETURNING id INTO new_id;
RETURN QUERY SELECT * FROM job WHERE id = new_id;
END;
旧实现,已成功运行:
def insert_job(db, user_id: int, param_id: str, proc_name: str, run_date: datetime) -> Job:
try:
db.execute('SELECT * FROM add_job(%s, %s, %s, %s)', (user_id, param_id, proc_name, run_date))
except RaiseException as e:
raise
db.commit()
job = db.fetchone()
return job
新实施:
def insert_job(db, user_id: int, param_id: str, proc_name: str, run_date: datetime) -> Job:
query = select([func.add_job(user_id, param_id, proc_name, run_date)])
try:
result = engine.execute(query).fetchone()
except RaiseException as e:
raise
return result
自从我使用 SQLAlchemy 以来已经有很长时间了,但在过去,您需要为要在 DB 端提交的事务发出提交。 如果这是问题所在,它肯定会出现您所看到的症状。 尝试将新实现更改为:
def insert_job(db, user_id: int, param_id: str, proc_name: str, run_date: datetime) -> Job:
query = select([func.add_job(user_id, param_id, proc_name, run_date)])
with engine.begin() as conn:
result = conn.execute(query).fetchone()
return result
( with
块只是建立一个事务并在块完成时提交它,无一例外)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.