【问题标题】:DETERMINISTIC, NO SQL, or READS SQL DATA in its declaration and binary logging is enabledDETERMINISTIC、NO SQL 或 READS SQL DATA 在其声明和二进制日志记录已启用
【发布时间】:2014-11-18 20:15:24
【问题描述】:

在mysql中导入数据库时​​,出现以下错误:

1418 (HY000) at line 10185: 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)

我不知道我需要更改哪些内容。谁能帮我解决这个问题?

【问题讨论】:

    标签: mysql


    【解决方案1】:

    有两种方法可以解决这个问题:

    1. 在 MySQL 控制台中执行以下命令:

      SET GLOBAL log_bin_trust_function_creators = 1;

    2. 将以下内容添加到 mysql.ini 配置文件中:

      log_bin_trust_function_creators = 1;

    该设置放宽了对非确定性函数的检查。非确定性函数是修改数据的函数(即具有更新、插入或删除语句)。如需更多信息,请参阅here

    请注意,如果未启用二进制日志记录,则此设置不适用。

    Binary Logging of Stored Programs

    如果未启用二进制日志记录,则 log_bin_trust_function_creators 会启用 不适用。

    log_bin_trust_function_creators

    此变量在启用二进制日志记录时适用。

    最好的方法是更好地理解和使用存储函数的确定性声明。 MySQL 使用这些声明来优化复制,仔细选择它们以获得健康的复制是一件好事。

    确定性 如果例程总是为相同的输入参数产生相同的结果,则认为例程是“确定性的”,否则为 NOT DETERMINISTIC。 这主要用于字符串或数学处理,但不限于此。

    不确定 与“确定性”相反。 “如果例程定义中既没有给出 DETERMINISTIC 也没有给出 NOT DETERMINISTIC,则默认为 NOT DETERMINISTIC。要声明函数是确定性的,您必须明确指定 DETERMINISTIC。”。 所以似乎如果没有声明,MySQl 会将函数视为“NOT DETERMINISTIC”。 手册中的这一陈述与手册另一个领域的其他陈述相矛盾,该陈述表明: " 当你创建一个存储函数时,你必须声明它是确定性的,或者它不会修改数据。否则,它可能对数据恢复或复制不安全。 默认情况下,要接受 CREATE FUNCTION 语句,必须显式指定 DETERMINISTIC、NO SQL 或 READS SQL DATA 中的至少一个。否则会出错"

    如果没有声明,我个人在 MySQL 5.5 中会出错,所以我总是至少声明一个“DETERMINISTIC”、“NOT DETERMINISTIC”、“NO SQL”或“READS SQL DATA”,不管我可能有其他声明.

    读取 SQL 数据 这明确告诉 MySQL 该函数将只从数据库中读取数据,因此,它不包含修改数据的指令,但它包含读取数据的 SQL 指令(例如 SELECT)。

    修改 SQL 数据 这表明例程包含可能写入数据的语句(例如,它包含 UPDATE、INSERT、DELETE 或 ALTER 指令)。

    无 SQL 这表明该例程不包含 SQL 语句。

    包含 SQL 这表明例程包含 SQL 指令,但不包含读取或写入数据的语句。如果没有明确给出这些特征,则这是默认设置。此类语句的示例是 SELECT NOW()、SELECT 10+@b、SET @x = 1 或 DO RELEASE_LOCK('abc'),它们执行但既不读取也不写入数据。

    注意有一些MySQL函数不是确定性安全的,比如:NOW()、UUID()等,在不同的机器上很可能会产生不同的结果,所以必须声明一个包含此类指令的用户函数作为不确定的。 此外,从非复制模式中读取数据的函数显然是非确定性的。 *

    对例行程序性质的评估是基于“诚实”的 创建者:MySQL 不检查声明 DETERMINISTIC 的例程是否为 没有产生不确定结果的陈述。然而, 错误地声明例程可能会影响结果或影响性能。 将不确定的例程声明为 DETERMINISTIC 可能会导致 导致优化器不正确的意外结果 执行计划选择。将确定性例程声明为 NONDETERMINISTIC 可能会通过导致可用 不使用优化。

    【讨论】:

    • 你能解释一下后台发生了什么吗?
    • 我怀疑数据库有修改数据的功能(里面有更新、插入或删除语句)。有关更多信息,请参阅此处:dev.mysql.com/doc/refman/5.0/en/stored-programs-logging.html
    • 您应该始终进行备份
    • 它需要超级权限!
    • 谢谢它对我有用。
    【解决方案2】:
    • 创建存储函数时,必须声明它是 确定性或它不会修改数据。否则,可能会 数据恢复或复制不安全。

    • 默认情况下,要接受 CREATE FUNCTION 语句,至少 必须指定 DETERMINISTIC、NO SQL 或 READS SQL DATA 之一 明确地。否则会报错:

    要解决此问题,请在 Return 和 Before Begin 语句之后添加以下行:

    READS SQL DATA
    DETERMINISTIC
    

    例如:

    CREATE FUNCTION f2()
    RETURNS CHAR(36) CHARACTER SET utf8
    /*ADD HERE */
    READS SQL DATA
    DETERMINISTIC
    BEGIN
    

    有关此问题的更多详细信息,请阅读Here

    【讨论】:

    • 这是可行的,因为设置READS SQL DATA 是三者中限制最少的。如果您的函数属于NO SQLDETERMINISTIC 类别,您可以通过修改函数来提高性能。另一方面,设置READS SQL DATA 也是最不容易出错的。因此,如果您错误地使用NO SQLDETERMINISTIC,您可能会得到错误的结果。
    • @SunnyS.M,很棒的解释就像 READS SQL DATA DETERMINISTIC。要解决此问题,请在 Return 和 Begin 语句之前添加以下行:
    • 请注意 MySQL 手册指出 “对函数性质的评估基于创建者的诚实。MySQL 不会检查声明为 DETERMINISTIC 的函数是否不含产生不确定性的语句结果”
    • 我只是想知道为什么我不能使用modifies sql data not deterministic 在我有一个非确定性函数时让它运行?
    【解决方案3】:

    当您的函数是确定性的时,您可以安全地将其声明为确定性。 “DETERMINISTIC”关键字的位置如下。

    【讨论】:

      【解决方案4】:

      我在 ubuntu 上使用这个命令:

      mysql -u root -p
      

      并输入mysql server error并在mysql中执行这个命令:

      SET GLOBAL log_bin_trust_function_creators = 1;
      

      【讨论】:

      • 这不是已经给出了吗?请不要重复
      【解决方案5】:

      根据唐纳德的评论:

      此变量在启用二进制日志记录时适用。

      我所要做的就是:

      1. 在 my.cnf (#log_bin) 中禁用 log_bin
      2. 重启mysql
      3. 导入数据库
      4. 启用 log_bin
      5. 重启mysql

      这一步解决了导入问题。

      (然后我会审查程序员的代码以提出改进建议)

      【讨论】:

        【解决方案6】:

        在 Windows 10 上,

        我刚刚通过执行以下操作解决了这个问题。

        1. 转到 my.ini 并在 [mysqld]

          下添加这两行
          skip-log-bin
          log_bin_trust_function_creators = 1
          
        2. 重启 MySQL 服务

        【讨论】:

        • 执行此操作后,我在 slave 上遇到错误 - Got fatal error 1236 from master when reading data from binary log: 'Binary log is not open'
        【解决方案7】:

        尝试设置函数的定义器!

        所以不是

        CREATE FUNCTION get_pet_owner

        你会写一些类似于

        的东西

        CREATE DEFINER=procadmin@% FUNCTION get_pet_owner

        如果用户 prodacmin 有权创建函数/程序,这应该可以工作。

        在我的情况下,该函数在通过 MySQL Workbench 生成时有效,但在直接作为 SQL 脚本运行时无效。进行上述更改即可解决问题。

        【讨论】:

          猜你喜欢
          • 2011-06-22
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2018-06-07
          • 1970-01-01
          • 2013-02-15
          • 2017-01-10
          • 1970-01-01
          相关资源
          最近更新 更多