在为DATE或DATETIME设置默认值时在mysql中出错
我正在运行MySql Server 5.7.11和这句话:
updated datetime NOT NULL DEFAULT '0000-00-00 00:00:00'
不工作。 给出错误:
ERROR 1067 (42000): Invalid default value for 'updated'
但以下几点:
updated datetime NOT NULL DEFAULT '1000-01-01 00:00:00'
只是工作 。
DATE的情况相同。
作为旁注 ,它在mysql文档中提到:
DATEtypes用于具有date部分但不包含时间部分的值。 MySQL以'YYYY-MM-DD'格式检索并显示DATE值。 支持的范围是“1000-01-01”到“9999-12-31”。
即使他们也说:
无效的DATE,DATETIME或TIMESTAMP值将转换为相应types(“0000-00-00”或“0000-00-00 00:00:00”)的“零”值。
考虑到mysql文档的第二个引用,谁能让我知道为什么它给出了这个错误?
错误是因为sql模式可能是严格的模式按照最新的MYSQL 5.7文档
MySQL文档5.7说 :
严格模式会影响服务器是否允许“0000-00-00”作为有效date:如果未启用严格模式,则允许“0000-00-00”,并且插入不会产生警告。 如果启用严格模式,则不允许使用“0000-00-00”,除非给出IGNORE,否则插入会产生错误。 对于INSERT IGNORE和UPDATE IGNORE,“0000-00-00”是允许的,插入会产生警告。
检查MYSQL模式
SELECT @@GLOBAL.sql_mode global, @@SESSION.sql_mode session
禁用STRICT_TRANS_TABLES模式
但是,要允许格式为“ 0000-00-00 00:00:00
,则必须在mysqlconfiguration文件或命令中禁用STRICT_TRANS_TABLES模式
通过命令
SET sql_mode = '';
要么
SET GLOBAL sql_mode = '';
使用关键字GLOBAL
需要超级previliges,它会影响所有客户端从那时起连接的操作
如果上面的不工作比去/etc/mysql/my.cnf
(根据Ubuntu的)和注释掉STRICT_TRANS_TABLES
另外,如果你想在服务器启动时永久设置sql模式,那么在Linux或MacOS上的my.cnf
包含SET sql_mode=''
。 对于windows,这个必须在my.ini
文件中完成。
注意
但是MYSQL 5.6默认情况下严格模式是不启用的。 因此,它不会产生错误,根据MYSQL 6文档说
MySQL允许您将“0000-00-00”的“零”值存储为“虚拟date”。这在某些情况下比使用NULL值更方便,并且使用更less的数据和索引空间。 要禁止“0000-00-00”,请启用NO_ZERO_DATE SQL模式。
UPDATE
关于@Dylan-Su所说的错误问题:
我不认为这是MYSQL随着时间的推移发展而来的错误,因为有些东西是根据产品的进一步改进而改变的。
不过,我有另一个有关NOW()
函数的相关错误报告
date时间字段不接受默认NOW()
另一个有用的注意事项 [请参阅自动初始化和更新TIMESTAMP和DATETIME ]
从MySQL 5.6.5开始,TIMESTAMP和DATETIME列可以自动初始化并更新为当前date和时间(即当前时间戳)。 在5.6.5之前,这仅适用于TIMESTAMP,每个表最多只有一个TIMESTAMP列。 以下注释首先描述了MySQL 5.6.5及更高版本的自动初始化和更新,然后介绍了5.6.5之前版本的差异。
关于NO_ZERO_DATE的更新
从5.7.4开始,MySQL不推荐使用这种模式。 对于以前的版本,您必须在configuration文件中注释掉相应的行。 请参阅NO_ZERO_DATE上的MySQL 5.7文档
WAMP 3.0.6与MySql 5.7.14我有这个错误。
解答 :
在c:\wamp\bin\mysql\mysql5.7.14\my.ini
文件中更改第70行(如果您的ini文件未触及)
sql-mode= "STRICT_ALL_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_ZERO_DATE,NO_ZERO_IN_DATE,NO_AUTO_CREATE_USER"
至
sql-mode="ERROR_FOR_DIVISION_BY_ZERO,NO_ZERO_DATE,NO_ZERO_IN_DATE,NO_AUTO_CREATE_USER"
并重新启动所有服务。
这将禁用严格模式。 根据文档,“严格模式”是指启用了STRICT_TRANS_TABLES
或STRICT_ALL_TABLES
一个或两个的模式。 该文件说:
“MySQL 5.7中的默认SQL模式包括以下模式:ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER和NO_ENGINE_SUBSTITUTION。
configuration语法问题
在* nix系统下的某些版本的MYSQL(testing5.7。*)中,应该使用以下语法:
[mysqld] sql-mode="NO_BACKSLASH_ESCAPES,STRICT_TRANS_TABLE,NO_ENGINE_SUBSTITUTION"
这些将不起作用:
没有引号
sql-mode=NO_ENGINE_SUBSTITUTION
下划线没有引号
sql_mode=NO_ENGINE_SUBSTITUTION
下划线和引号
sql_mode="NO_ENGINE_SUBSTITUTION"
configuration值和sql-mode的更全面的回顾:
如何设置永久的Sql模式标志
它适用于5.7.8:
mysql> create table t1(updated datetime NOT NULL DEFAULT '0000-00-00 00:00:00'); Query OK, 0 rows affected (0.01 sec) mysql> show create table t1; +-------+-------------------------------------------------------------------------------------------------------------------------+ | Table | Create Table | +-------+-------------------------------------------------------------------------------------------------------------------------+ | t1 | CREATE TABLE `t1` ( `updated` datetime NOT NULL DEFAULT '0000-00-00 00:00:00' ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 | +-------+-------------------------------------------------------------------------------------------------------------------------+ 1 row in set (0.00 sec) mysql> select version(); +-----------+ | version() | +-----------+ | 5.7.8-rc | +-----------+ 1 row in set (0.00 sec)
您可以创build一个SQLFiddle来重新创build您的问题。
如果它适用于MySQL 5.6和5.7.8,但在5.7.11上失败。 那么它可能是一个5.7.11的回归bug。
这个答案只适用于MySQL 5.7:
最好不是真的在空白的sql_mode中设置,而是在php中使用一个会话variables:
SET SESSION sql_mode= 'ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION'
所以至less你保留了另一个默认值
mysql文档不清楚,这是疯狂的,你需要在sql_mode中删除这个转义值:
NO_ZERO_IN_DATE,NO_ZERO_DATE,据我所知,但在未来的版本中,这将被停用。
STRICT_ALL_TABLES,在这之前,参数将被忽略,所以你也需要删除它。
最后也是TRADITIONAL,但是文档中提到了这个参数:“当给列插入一个不正确的值时给出一个错误而不是一个警告”,用这个参数,没有插入零值的date,但是没有
mysql并不是真的用这些参数和组合来组织的。
解决MySQL Workbench的问题(在服务器端应用解决scheme之后):
在首选项面板中将SQL_MODE移除到TRADITIONAL。
适用于mysql Ver 14.14 Distrib 5.7.18, for Linux (x86_64)
选项组合mysql Ver 14.14 Distrib 5.7.18, for Linux (x86_64)
。
不扔:
STRICT_TRANS_TABLES
+ NO_ZERO_DATE
抛出:
STRICT_TRANS_TABLES
+ NO_ZERO_IN_DATE
我在Ubuntu的/etc/mysql/my.cnf
设置:
[mysqld] sql_mode = "STRICT_TRANS_TABLES,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
首先select当前会话sql_mode
:
SELECT @@SESSION.sql_mode;
那么你会得到这样的默认值 :
'ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION'
然后在没有'NO_ZERO_DATE'
情况下设置sql_mode
:
SET SESSION sql_mode = 'ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION';
如果您有资助,您也可以为GLOBAL
:
SELECT @@GLOBAL.sql_mode; SET GLOBAL sql_mode = '...';