创建一个触发器来更新另一个 table (Postgresql) 的列
Create a trigger that updates the columns of another table (Postgresql)
我有两个 table 的“books”和“bookOrder”,它们看起来像这样:
bookOrder
orderID
book name
required
availability
1
Harry Potter
9
yes
2
Twilight
8
yes
3
Bible
8
yes
书籍
book name
quantity
Harry Potter
10
Twilight
5
Bible
8
我想创建一个触发器,每次更新图书 table 时,它都会根据 图书更新 bookorder 可用性列 数量列。
我已经创建了一个查询来满足我的需要:
UPDATE bookOrder bo
SET avalability = CASE WHEN b.quantity < bo.required THEN 'NO' ELSE 'YES' END
FROM books b
WHERE b.bookName = bo.bookName
但是,如果这是自动的会更好,所以触发器是我的第一个想法。要创建触发器,我需要一个函数来执行。这是我在创建函数时遇到的麻烦。我的尝试如下:
CREATE OR REPLACE FUNCTION update_books() RETURNS TRIGGER AS $$
BEGIN
UPDATE bookOrder bo
SET avalability = CASE WHEN b.quantity < bo.required THEN 'NO' ELSE 'YES' END
FROM books b
WHERE b.bookName = bo.bookName
END
$$ LANGUAGE plpgsql;
为什么我在 ($$) 所在的最后一行出现错误?
WHERE子句后加分号后编译的程序。
而且它还必须return一些东西。
但是更新不需要更新目标中的每一行 table 每当书籍更新时。
CREATE OR REPLACE FUNCTION update_bookorder_availability()
RETURNS TRIGGER
AS $$
BEGIN
UPDATE bookOrder bo
SET availability = CASE
WHEN bo.required <= NEW.quantity THEN 'yes'
ELSE 'no'
END
WHERE bo.bookName = NEW.bookName;
RETURN NEW;
END
$$ LANGUAGE plpgsql;
CREATE TRIGGER bookorder_availability_changes
AFTER UPDATE
ON books
FOR EACH ROW
EXECUTE PROCEDURE update_bookorder_availability();
-- before update
select * from books;
select * from bookOrder;
bookname | quantity
:----------- | -------:
Harry Potter | 10
Twilight | 5
Bible | 8
orderid | bookname | required | availability
------: | :----------- | -------: | :-----------
1 | Harry Potter | 9 | yes
2 | Twilight | 8 | yes
3 | Bible | 8 | yes
update books set quantity = quantity;
3 rows affected
-- after update
select * from books;
select * from bookOrder;
bookname | quantity
:----------- | -------:
Harry Potter | 10
Twilight | 5
Bible | 8
orderid | bookname | required | availability
------: | :----------- | -------: | :-----------
1 | Harry Potter | 9 | yes
2 | Twilight | 8 | no
3 | Bible | 8 | yes
在 db<>fiddle here
上测试
我有两个 table 的“books”和“bookOrder”,它们看起来像这样:
bookOrder
orderID | book name | required | availability |
---|---|---|---|
1 | Harry Potter | 9 | yes |
2 | Twilight | 8 | yes |
3 | Bible | 8 | yes |
书籍
book name | quantity |
---|---|
Harry Potter | 10 |
Twilight | 5 |
Bible | 8 |
我想创建一个触发器,每次更新图书 table 时,它都会根据 图书更新 bookorder 可用性列 数量列。
我已经创建了一个查询来满足我的需要:
UPDATE bookOrder bo
SET avalability = CASE WHEN b.quantity < bo.required THEN 'NO' ELSE 'YES' END
FROM books b
WHERE b.bookName = bo.bookName
但是,如果这是自动的会更好,所以触发器是我的第一个想法。要创建触发器,我需要一个函数来执行。这是我在创建函数时遇到的麻烦。我的尝试如下:
CREATE OR REPLACE FUNCTION update_books() RETURNS TRIGGER AS $$
BEGIN
UPDATE bookOrder bo
SET avalability = CASE WHEN b.quantity < bo.required THEN 'NO' ELSE 'YES' END
FROM books b
WHERE b.bookName = bo.bookName
END
$$ LANGUAGE plpgsql;
为什么我在 ($$) 所在的最后一行出现错误?
WHERE子句后加分号后编译的程序。
而且它还必须return一些东西。
但是更新不需要更新目标中的每一行 table 每当书籍更新时。
CREATE OR REPLACE FUNCTION update_bookorder_availability() RETURNS TRIGGER AS $$ BEGIN UPDATE bookOrder bo SET availability = CASE WHEN bo.required <= NEW.quantity THEN 'yes' ELSE 'no' END WHERE bo.bookName = NEW.bookName; RETURN NEW; END $$ LANGUAGE plpgsql;
CREATE TRIGGER bookorder_availability_changes AFTER UPDATE ON books FOR EACH ROW EXECUTE PROCEDURE update_bookorder_availability();
-- before update select * from books; select * from bookOrder;
bookname | quantity :----------- | -------: Harry Potter | 10 Twilight | 5 Bible | 8 orderid | bookname | required | availability ------: | :----------- | -------: | :----------- 1 | Harry Potter | 9 | yes 2 | Twilight | 8 | yes 3 | Bible | 8 | yes
update books set quantity = quantity;
3 rows affected
-- after update select * from books; select * from bookOrder;
bookname | quantity :----------- | -------: Harry Potter | 10 Twilight | 5 Bible | 8 orderid | bookname | required | availability ------: | :----------- | -------: | :----------- 1 | Harry Potter | 9 | yes 2 | Twilight | 8 | no 3 | Bible | 8 | yes
在 db<>fiddle here
上测试