无法从另一个存储例程中创建TRIGGER - 什么是另一个"存储例程"?

bat*_*man 2 mysql triggers phpmyadmin

我正在尝试使用PhpMyAdmin在MySQL中创建一个触发器.

CREATE TRIGGER Update_Last_Transit_Status AFTER INSERT ON Delivery 
FOR EACH ROW
BEGIN
UPDATE Transportation SET Status="Dispatched" WHERE 
EXISTS (SELECT * FROM Transit, Route WHERE Transit.ID=Route.Transit_ID and
        Route.Delivery_ID=Delivery.ID and 
        Transit.Transportation_ID=Transportation.ID) and
        Status="In Branch"
END
Run Code Online (Sandbox Code Playgroud)

它说:

MySQL said: #1303 - Can't create a TRIGGER from within another stored routine
Run Code Online (Sandbox Code Playgroud)

我知道之前已经解决了这个错误,但这根本不是我的意图.

这里的"另一个存储例程"在哪里?

我不打算错误消息说明什么.

编辑: 没有定义其他触发器.但是有一个预定义的程序:

begin
        select user() as first_col;
        select user() as first_col, now() as second_col;
        select user() as first_col, now() as second_col, now() as third_col;
        end
Run Code Online (Sandbox Code Playgroud)

我不知道它做了什么,或为什么它在那里,但它曾经存在过.

Bil*_*win 6

您在上面显示的触发器很好.

编辑:当您在phpMyAdmin的GUI中创建触发器时,您只需要在" 定义"窗格中输入触发器的主体,即零件BEGIN...END.

这是因为phpMyAdmin将尝试聪明并根据您输入的其他元素(名称,表,时间,事件)为您编写触发器头.

这是在phpMyAdmin中定义触发器的正确​​方法:

在此输入图像描述

如果你CREATE TRIGGER...在正文中写入标题,它会混淆MySQL,因为它会看到CREATE TRIGGER... CREATE TRIGGER... BEGIN...END.这使MySQL认为您正在定义一个第一个语句的触发器CREATE TRIGGER.


作为原始问题的一个侧面问题,我建议在触发器的主体中进行一些更改:

CREATE TRIGGER Update_Last_Transit_Status AFTER INSERT ON Delivery 
FOR EACH ROW
BEGIN
  UPDATE Transportation
    INNER JOIN Transit ON Transit.Transportation_ID = Transportation.ID
    INNER JOIN Route ON Transit.ID = Route.Transit_ID
  SET Transportation.Status = 'Dispatched'
  WHERE Route.Delivery_ID = NEW.ID
    AND Transportation.Status = 'In Branch';
END
Run Code Online (Sandbox Code Playgroud)

变化:

  • 参考NEW.ID而不是Delivery.ID.
  • 使用SQL-92 JOIN语法而不是SQL-89"逗号样式"连接.
  • 将多表UPDATE与联接一起使用,而不是EXISTS与相关子查询一起使用.
  • 对字符串使用单引号而不是双引号.
  • UPDATE用分号终止语句.