更新语句级别触发器后,PostgreSQL OLD 无法正常工作
PostgreSQL OLD not working in after update statement level trigger
我正在尝试通过课程的课程分数总和来更新课程分数。
如果我像这样 select 特定课程 ID,它会完美地工作:
BEGIN
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = 7)
WHERE "course"."id" = 7;
RETURN NULL;
END;
但不适用于更新实例 OLD。我想更新正在更新的课程的积分。
BEGIN
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
END;
我正在使用 django-pgtriggers:https://pypi.org/project/django-pgtrigger/
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
level=pgtrigger.Statement,
when=pgtrigger.After,
operation=pgtrigger.Update,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
"""
)
)
OLD
和 NEW
在 Statement level
的情况下总是 NULL
。
将level=pgtrigger.Statement
替换为level=pgtrigger.Row
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
level=pgtrigger.Row,
when=pgtrigger.After,
operation=pgtrigger.Update,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
"""
)
)
或者添加referencing=pgtrigger.Referencing(old='old_table_name')
然后修改你的函数。
我已经注册了 2 个触发器。第一个是 before update 触发插入课程。第二个是 after update 触发更新和删除的课程。 课程分数 增加 或 减少 总和 课分毕竟。
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
operation=pgtrigger.Insert,
level=pgtrigger.Row,
when=pgtrigger.Before,
func=f"""
UPDATE course
SET points = (points + NEW.points)
WHERE "course"."id" = NEW.course_id;
RETURN NEW;
""",
),
pgtrigger.Trigger(
name="update_course_point",
operation=(pgtrigger.Update | pgtrigger.Delete),
level=pgtrigger.Row,
when=pgtrigger.After,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD.course_id)
WHERE "course"."id" = OLD.course_id;
RETURN NULL;
""",
),
)
我正在尝试通过课程的课程分数总和来更新课程分数。 如果我像这样 select 特定课程 ID,它会完美地工作:
BEGIN
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = 7)
WHERE "course"."id" = 7;
RETURN NULL;
END;
但不适用于更新实例 OLD。我想更新正在更新的课程的积分。
BEGIN
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
END;
我正在使用 django-pgtriggers:https://pypi.org/project/django-pgtrigger/
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
level=pgtrigger.Statement,
when=pgtrigger.After,
operation=pgtrigger.Update,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
"""
)
)
OLD
和 NEW
在 Statement level
的情况下总是 NULL
。
将level=pgtrigger.Statement
替换为level=pgtrigger.Row
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
level=pgtrigger.Row,
when=pgtrigger.After,
operation=pgtrigger.Update,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD."course_id")
WHERE "course"."id" = OLD."course_id";
RETURN NULL;
"""
)
)
或者添加referencing=pgtrigger.Referencing(old='old_table_name')
然后修改你的函数。
我已经注册了 2 个触发器。第一个是 before update 触发插入课程。第二个是 after update 触发更新和删除的课程。 课程分数 增加 或 减少 总和 课分毕竟。
@pgtrigger.register(
pgtrigger.Trigger(
name="add_course_point",
operation=pgtrigger.Insert,
level=pgtrigger.Row,
when=pgtrigger.Before,
func=f"""
UPDATE course
SET points = (points + NEW.points)
WHERE "course"."id" = NEW.course_id;
RETURN NEW;
""",
),
pgtrigger.Trigger(
name="update_course_point",
operation=(pgtrigger.Update | pgtrigger.Delete),
level=pgtrigger.Row,
when=pgtrigger.After,
func=f"""
UPDATE course
SET points = (SELECT COALESCE(SUM("lesson"."points"), 0) AS "sum_points" FROM "course" LEFT OUTER JOIN "lesson" ON ("course"."id" = "lesson"."course_id") WHERE "course"."id" = OLD.course_id)
WHERE "course"."id" = OLD.course_id;
RETURN NULL;
""",
),
)