Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/62.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用触发器的MySQL递归更新_Mysql_Triggers - Fatal编程技术网

使用触发器的MySQL递归更新

使用触发器的MySQL递归更新,mysql,triggers,Mysql,Triggers,我的目标是在不允许用户删除任何行的情况下设计一个模式,为此,我为每个表设置了一个“非活动”列 问题是我有一个这样设计的表格列表 sales_offers (so) -> sales_offers_items (soi) -> sales_offers_items_requisites (soir) -> sales_offers_items_labor (soil) soir和soi

我的目标是在不允许用户删除任何行的情况下设计一个模式,为此,我为每个表设置了一个“非活动”列

问题是我有一个这样设计的表格列表

sales_offers (so) -> sales_offers_items (soi) -> sales_offers_items_requisites (soir)
                                              -> sales_offers_items_labor (soil)
  • soir
    soil
    参考
    soi
    带列
    idparent
  • soi
    refenrences
    so
    带列
    idparent
表的简要说明:

  • so
    -销售优惠的标题
  • soi
    -包含提供的项目
  • soir
    -包含构建上述项目所需的项目列表(
    soi
  • soil
    -包含每个车间的人工成本列表
我在
soir
soil
上都有触发器,它们对其父表
soi
进行更新。此更新汇总了每个表中的值,并将其汇总到父表中,以便我可以使用这些汇总进行一些计算

我的问题是这个。当我设置
so.inactive=1
时,我希望递归地设置
soi.inactive=1;soir.inactive=1;土壤。非活性=1

据我所知,MySQL不允许您以这种方式设计触发器,以避免执行无限循环

我唯一的解决方案是使用另一个表进行聚合,类似于
sales\u offers\u items\u totals
soit

这个解决方案太耗时了,我尝试使用复合外键,如果我想停用每个子表,它可以工作,但是如果我只想停用子表的一行,我会得到一个约束错误

如果有人有比额外的聚合表更好的解决方案,我将不胜感激。

演示:

所以,我是不活跃的 ----: | -------: 11 | 1 111 | 0 soi|u id |不活动| so|u id -----: | -------: | ----: 22 | 1 | 11 222 | 0 | 111 soir|U id |非活动| soi|U id ------: | -------: | -----: 33 | 1 | 22 333 | 0 | 222 soi|U id | so|id |不活动|不活动| soi|U id |不活动 -----: | ----: | -------: | -------: | ------: | -------: 22 | 11 | 1 | 1 | 33 | 1 222 | 111 | 0 | 0 | 333 | 0
dbfiddle

嗨,Akina,谢谢你的回答。这一切都是我做的。问题在于soir在“value”列上有一个触发器,该触发器对soi.total_值进行更新。当我更新soi.inactive并启动触发器时,mysql表示我无法更新此表,因为它正在另一个触发器/函数中使用。
CREATE TABLE so (so_id INT PRIMARY KEY, 
                 inactive  boolean);
CREATE TABLE soi (soi_id INT PRIMARY KEY, 
                  inactive  boolean, 
                  so_id INT, 
                  FOREIGN KEY (so_id) REFERENCES so (so_id));
CREATE TABLE soir (soir_id INT PRIMARY KEY, 
                   inactive  boolean, 
                   soi_id INT, 
                   FOREIGN KEY (soi_id) REFERENCES soi (soi_id));
INSERT INTO so VALUES (11, 0), (111, 0);
INSERT INTO soi VALUES (22, 0, 11), (222, 0, 111);
INSERT INTO soir VALUES (33, 0, 22), (333, 0, 222);
CREATE TRIGGER tr_au_so
AFTER UPDATE
ON so
FOR EACH ROW
UPDATE soi SET inactive = NEW.inactive WHERE so_id = NEW.so_id;
CREATE TRIGGER tr_au_soi
AFTER UPDATE
ON soi
FOR EACH ROW
UPDATE soir SET inactive = NEW.inactive WHERE soi_id = NEW.soi_id;
SELECT * FROM so;
SELECT * FROM soi;
SELECT * FROM soir;
SELECT * 
FROM so
JOIN soi USING (so_id)
JOIN soir USING (soi_id);
so_id | inactive ----: | -------: 11 | 0 111 | 0 soi_id | inactive | so_id -----: | -------: | ----: 22 | 0 | 11 222 | 0 | 111 soir_id | inactive | soi_id ------: | -------: | -----: 33 | 0 | 22 333 | 0 | 222 soi_id | so_id | inactive | inactive | soir_id | inactive -----: | ----: | -------: | -------: | ------: | -------: 22 | 11 | 0 | 0 | 33 | 0 222 | 111 | 0 | 0 | 333 | 0
UPDATE so SET inactive = 1 WHERE so_id = 11;
SELECT * FROM so;
SELECT * FROM soi;
SELECT * FROM soir;
SELECT * 
FROM so
JOIN soi USING (so_id)
JOIN soir USING (soi_id);
so_id | inactive ----: | -------: 11 | 1 111 | 0 soi_id | inactive | so_id -----: | -------: | ----: 22 | 1 | 11 222 | 0 | 111 soir_id | inactive | soi_id ------: | -------: | -----: 33 | 1 | 22 333 | 0 | 222 soi_id | so_id | inactive | inactive | soir_id | inactive -----: | ----: | -------: | -------: | ------: | -------: 22 | 11 | 1 | 1 | 33 | 1 222 | 111 | 0 | 0 | 333 | 0