MySQL 错误1418 的缘由分析及解决方法

具体错误:
 使用mysql建立、调用存储过程,函数以及触发器的时候会有错误符号为1418错误。mysql

[Err] 1418 - This function has none of DETERMINISTIC, NO SQL, or READS SQL DATA in its declaration and binary logging is enabled (you *might* want to use the less safe log_bin_trust_function_creators variable)sql

查阅相关资料,意思是说binlog启用时,建立的函数没有声明类型,由于binlog在主从复制须要知道这个函数建立语句是什么类型,不然同步数据会有不一致现象。服务器

mysql开启了bin-log, 咱们就必须指定咱们的函数是不是哪一种类型: 
1 DETERMINISTIC 不肯定的 
2 NO SQL 没有SQl语句,固然也不会修改数据 
3 READS SQL DATA 只是读取数据,固然也不会修改数据 
4 MODIFIES SQL DATA 要修改数据 
5 CONTAINS SQL 包含了SQL语句less


为了解决这个问题,MySQL强制要求:
在主服务器上,除非子程序被声明为肯定性的或者不更改数据,不然建立或者替换子程序将被拒绝。这意味着当建立一个子程序的时候,必需要么声明它是肯定性的,要么它不改变数据。函数

声明方式有两种:
第一种:声明是不是肯定性的
DETERMINISTIC和NOT DETERMINISTIC指出一个子程序是否对给定的输入老是产生一样的结果。
若是没有给定任一特征,默认是NOT DETERMINISTIC,因此必须明确指定DETERMINISTIC来声明一个子程序是肯定性的。 
这里要说明的是:使用NOW() 函数(或它的同义)或者RAND() 函数不会使一个子程序变成非肯定性的。对NOW()而言,二进制日志包括时间戳并会被正确的执行。RAND()只要在一个子程序内被调用一次也能够被正确的复制。因此,能够认为时间戳和随机数种子是子程序的肯定性输入,它们在主服务器和从服务器上是同样的。
第二种:声明是否会改变数据  
CONTAINS SQL, NO SQL, READS SQL DATA, MODIFIES SQL用来指出子程序是读仍是写数据的。
不管NO SQL仍是READS SQL DATA都指出,子程序没有改变数据,可是必须明确地指定其中一个,由于若是任何指定,默认的指定是CONTAINS SQL。
默认状况下,若是容许CREATE PROCEDURE 或CREATE FUNCTION 语句被接受,就必须明确地指定DETERMINISTIC 或 NO SQL与READS SQL DATA 中的一个,不然就会产生1418错误。日志

解决办法也有两种:
第一种是在建立子程序(存储过程、函数、触发器)时,声明为DETERMINISTIC或NO SQL与READS SQL DATA中的一个,
例如:rem

DROP FUNCTION IF EXISTS `t_auto_increment`;
DELIMITER ;;
CREATE FUNCTION `t_auto_increment`(`seq_name` tinyint) RETURNS varchar(50) CHARSET utf8
DETERMINISTIC
BEGIN
declare v_prefix VARCHAR(20);
update t_auto_increment a set a.currentvalue=LAST_INSERT_ID(a.currentvalue+a.incrementBy) where a.autoKey=seq_name;
select prefix into v_prefix from t_auto_increment where autoKey=seq_name;
RETURN CONCAT(CASE WHEN v_prefix  is null THEN '' ELSE  v_prefix END,LAST_INSERT_ID());
END
;;
DELIMITER ;同步


第二种是信任子程序的建立者,禁止建立、修改子程序时对SUPER权限的要求,设置log_bin_trust_routine_creators全局系统变量为1。设置方法有三种:it

1.在客户端上执行SET GLOBAL log_bin_trust_function_creators = 1;
2.MySQL启动时,加上--log-bin-trust-function-creators选贤,参数设置为1
3.在MySQL配置文件my.ini或my.cnf中的[mysqld]段上加log-bin-trust-function-creators=1

io

相关文章
相关标签/搜索