从PHP代码创建触发器时出现语法错误

问题描述:

我想从以下PHP代码创建触发器。从PHP代码创建触发器时出现语法错误

$sql = 'delimiter $$'; 
    $pdo->exec($sql); 
    $sql = 'create trigger avoid_empty_employee_insert before insert on `employee` 
      for each row begin 
      if name = "" then set name = null; end if; 
      end$$'; 
    $pdo->exec($sql); 
    $sql = 'delimiter ;'; 
    $pdo->exec($sql); 

当我运行代码MySQL它的工作原理和触发器创建。

PHP显示以下错误。

SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'delimiter $$' at line 1

我该如何解决?

绝对不要试图去改变,当你通过API执行该语句的分隔符。 DELIMITERmysql client built-in command,它不被MySQL服务器端解析器识别。

反正你不需要它。 DELIMITER的目的是消除可能出现在触发器或存储程序体内的分号的不明确性。由于API一次只能执行一条语句,因此不存在歧义。无论如何,SQL解析器只是将整个字符串视为一个语句。

同样,不要以$$结束创建触发器语句。您不需要任何语句终结符,但SQL解析器接受;作为可选语句终止符,因为即使不需要,许多人也将它放在那里。

接下来的问题是,你当你在一个触发器使用的列名,您有一定NEW.OLD.它们添加前缀 - INSERT触发器中,你只能使用NEW.如果没有前缀列, MySQL假设你打算设置一个系统变量,如tmpdirslow_query_log

如果你仍然得到1193错误,我建议你不改变NEW.name引用到name列。

我使用PHP 5.4.24和MySQL 5.6测试了以下内容。20,和它的工作:

$sql = "create trigger avoid_empty_employee_insert before insert on `employee` 
     for each row begin 
      if NEW.name = '' then set NEW.name = null; end if; 
     end"; 
$pdo->exec($sql); 

你不需要分隔的name列名,因为它不是一个MySQL的保留字。 The set of reserved words is documented.

尝试:

$sql = 'create trigger avoid_empty_employee_insert before insert on `employee` 
     for each row begin 
     if name = "" then set name = null; end if; END;'; 
    $pdo->exec($sql); 
+0

'SQLSTATE [HY000]:常规错误:1193未知的系统变量 '名'' – xralf 2014-09-13 18:04:43

+0

你在你的员工表名? – 2014-09-13 18:10:27

+0

是“name varchar(255)not null”... btw。该代码在MySQL中工作。 – xralf 2014-09-13 18:14:43

由于您使用的代码创建触发器,你可能不需要设置/重置DELIMITER。更改DELIMITER对于CLI很重要。

只是忽略那些改变它们的代码。

你的代码只变为:

$sql = 'create trigger `avoid_empty_employee_insert` before insert 
     on `employee` 
     for each row 
     begin 
      if `name` = "" then set `name` = null; end if; 
     end'; 
$pdo->exec($sql); 
+0

'SQLSTATE [HY000]:一般错误:1193未知系统变量'名称' – xralf 2014-09-13 18:12:00

由于您使用的代码创建触发器,你可能不会需要设置/重置DELIMITER

只是忽略那些改变它们的代码。

你的代码只变为:

$sql = 'create trigger avoid_empty_employee_insert before insert on `employee` 
      for each row begin 
      if NEW.`name` = "" then set NEW.`name` = null; end if; 
      end$$'; 
$pdo->exec($sql); 
+0

'SQLSTATE [HY000]:一般错误:1193未知系统变量'名称' – xralf 2014-09-13 18:10:24

+0

请参阅编辑。 – Peter 2014-09-13 18:11:11

+0

你有什么改变? – xralf 2014-09-13 18:12:56

Mayby这有助于:

$sql = "delimiter //\n"; 
$pdo->exec($sql); 
$sql = "create trigger avoid_empty_employee_insert before insert on employee\n 
     for each row\n 
     begin\n 
     if new.name = '' then\n 
     set new.name = null;\n 
     end if;\n 
     end//\n"; 
$pdo->exec($sql); 
$sql = 'delimiter ;'; 
$pdo->exec($sql);