我试图创建一个beforedelete
触发器,因此,如果用户输入了错误的内容id
,他将收到一条错误消息。
我用下面的代码...
CREATE TRIGGER pos_id
BEFORE DELETE ON CLIENTS
FOR EACH ROW
BEGIN
DECLARE TOTAL INT;
SET TOTAL = ( SELECT COUNT( * ) FROM CLIENTS ) ;
IF( old.id <0 OR old.id > total )
THEN SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = 'Error. Client doesn't exist';
END IF ;
END
此外,它不起作用。该消息未出现,并且触发器似乎不起作用。当我在互联网上寻找解决问题的方法时,我了解了很多有趣的东西,而不是触发器。
但是当我尝试...
CREATE TRIGGER pos_id
INSTEAD OF DELETE ON CLIENTS
BEGIN
(...)
或者...
CREATE TRIGGER pos_id
ON CLIENTS
INSTEAD OF DELETE
BEGIN
(...)
我得到一个syntax error
。所以我真的有两个问题:
1º为什么我的删除前触发器不起作用?我真的想念什么吗?
2º与删除触发器相关的语法错误是什么?
太感谢了。
您不能通过触发器来做到这一点。触发器将仅针对至少匹配一行的删除操作而触发,因此,如果用户尝试删除不存在的客户端而不是得到您的自定义错误,则他们只会得到以下信息:
mysql > delete from clients where id = -1;
Query OK, 0 rows affected (0.00 sec)
此外,您应该显式检查行的存在,而不是依赖于输入是小于零还是大于表中的行数,依此类推。此外,您还需要在错误消息中转义撇号。
您可以使用存储过程来完成此操作。如果可以让用户使用存储过程删除行,而不是对客户端表执行显式删除,则可以引发自定义错误。
例如(我不知道id列的数据类型。我假设是int,但是您应该更改它以匹配表中的实际数据类型):
delimiter $$
drop procedure if exists delete_client $$
create procedure delete_client (p_client_id int)
begin
declare v_client_exists int default 0;
select count(*)
into v_client_exists
from clients
where id = p_client_id;
if (v_client_exists = 0)
then
SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = 'Error. Client doesn''t exist';
else
delete from clients where id = p_client_id;
end if;
end $$
delimiter ;
然后像这样删除:
mysql > call delete_client(-1);
ERROR 1644 (45000): Error. Client doesn't exist
mysql > call delete_client(2);
Query OK, 1 row affected (0.00 sec)
mysql > call delete_client(2);
ERROR 1644 (45000): Error. Client doesn't exist
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句