mysql触发器:列不是更新的一部分不为null

时间:2016-09-07 09:42:25

标签: mysql triggers

mysql V 5.6

嗨,我在UPFATE之前遇到了触发器的问题:在桌子上,我有一个标志defiend作为tinyint,而不是null,默认值为1。我有一个更新前触发器,只要行更新,就会将此标志设置为1。但是,我还需要在一个进程中将标志显式设置为0,所以我尝试了

create trigger t BEFORE UPDATE on table for each row
BEGIN
IF new.flag is NULL THEN  
    set new.flag = 1
 END IF;

问题: new.flag永远不会为空。使用

进行检查
IF new.flag is NULL THEN  
    set new.flag = 1
ELSEIF new.flag = 0 THEN
    set new.flag = 3
END IF;
每当我更新表而不在更新查询中包含标志时,

将列设置为3。更糟糕的是,我无法检查空字符串以将标志置为1,因为选择('' = 0)返回true,如果使用:

IF new.flag is NULL OR new.flag = '' THEN  
    set new.flag = 1
END IF;

我永远不能将标志显式设置为0。不属于更新的列不应该在NEW中为空吗?我该怎么办,是否需要更改mysql配置?

由于

1 个答案:

答案 0 :(得分:1)

NEW包含更新后该行所有列的值,而不仅仅是您在更新查询中明确使用的值。

要告诉触发器您要显式重置该值,您可以使用其他未使用(但有效)的值来标记该信息,然后在触发器中相应地执行操作,例如,在您的触发器中,使用(假设已签名) TINYINT)

IF new.flag = -1 THEN  
  set new.flag = 0;
ELSE
  set new.flag = 1;
END IF;

然后在update查询中

update table set flag = -1;

会将值设置为0,任何其他值,或者根本不在查询中使用该列,将其设置为1

有一种替代且更常见的方法,没有触发器,它的作用类似于你的旗帜。您可以使用列

last_update datetime default null on update current_timestamp;
此列中的

nullflag = 0具有相同的含义,任何其他值与flag = 1具有相同的含义。它们是自动设置的。如果您想重置"标记",您只需使用

即可
update table set last_update = null;

你的触发方法当然会完美无缺。只需确保在某处记录该行为。