Подтвердить что ты не робот

Ошибка в mysql при установке значения по умолчанию для DATE или DATETIME

Я запускаю 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 docs:

Тип DATE используется для значений с частью даты, но без временной части. MySQL извлекает и отображает значения DATE в формате "YYYY-MM-DD". Поддерживаемый диапазон - от "1000-01-01" до "9999-12-31".

даже если они также говорят:

Недействительные значения DATE, DATETIME или TIMESTAMP преобразуются в нулевое значение соответствующего типа ('0000-00-00' или '0000-00-00 00:00:00').

Также учитывая вторую цитату из документации mysql, может ли кто-нибудь сообщить мне, почему она дает эту ошибку?

4b9b3361

Ответ 1

Ошибка возникает из-за режима sql, который может быть строгим в соответствии с последней документацией MYSQL 5.7.

Документация MySQL 5.7 говорит:

Строгий режим влияет на то, разрешает ли серверу "0000-00-00" в качестве действительной даты: Если строгий режим не включен, допускается "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, вы должны отключить режим STRICT_TRANS_TABLES в файле конфигурации mysql или командой

По команде

SET sql_mode = '';

или

SET GLOBAL sql_mode = '';

Использование ключевого слова GLOBAL требует суперпревалирования и влияет на операции, с которыми все клиенты соединяются с этого времени на

если выше не работает, чем перейти к /etc/mysql/my.cnf (согласно ubuntu) и прокомментировать STRICT_TRANS_TABLES

Кроме того, если вы хотите окончательно установить режим sql при запуске сервера, включите SET sql_mode='' в my.cnf в Linux или MacOS. Для окон это должно быть сделано в файле my.ini.

Примечание

Однако строгий режим не включен по умолчанию в MYSQL 5.6. Следовательно, он не создает ошибку в соответствии с документацией MYSQL 6, в которой говорится

MySQL позволяет вам хранить "нулевое" значение "0000-00-00" в качестве "фиктивной даты". Это в некоторых случаях более удобно, чем использование значений NULL, и использует меньше пространства данных и индексов. Чтобы запретить "0000-00-00" , включите режим NO_ZERO_DATE SQL.

UPDATE

Что касается вопроса об ошибке, как сказал @Dylan-Su:

Я не думаю, что это ошибка, так как MYSQL развивается за время, из-за чего некоторые вещи меняются в зависимости от дальнейшего улучшения продукта.

Однако у меня есть еще один связанный отчет об ошибке в отношении функции NOW()

Поле Datetime не принимает значение по умолчанию NOW()

Другая полезная нота. Автоматическая инициализация и обновление для TIMESTAMP и DATETIME]

Начиная с MySQL 5.6.5, столбцы TIMESTAMP и DATETIME могут быть автоматически инициализированы и обновлены до текущей даты и времени (то есть текущей метки времени). До 5.6.5 это верно только для TIMESTAMP и не более одного столбца TIMESTAMP для каждой таблицы. Следующие примечания сначала описывают автоматическую инициализацию и обновление для MySQL 5.6.5 и выше, затем различия для версий, предшествующих 5.6.5.

Обновление в отношении NO_ZERO_DATE

В MySQL с 5.7.4 этот режим устарел. Для предыдущей версии вы должны прокомментировать соответствующую строку в файле конфигурации. Обратитесь Документация MySQL 5.7 по NO_ZERO_DATE

Ответ 2

У меня была эта ошибка с WAMP 3.0.6 с MySql 5.7.14.

Решение:

измените строку 70 (если ваш INI файл нетронутым) в файле c:\wamp\bin\mysql\mysql5.7.14\my.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 или с STRICT_ALL_TABLES. Документация гласит:

"Режим SQL по умолчанию в MySQL 5.7 включает в себя следующие режимы: ONLY_FULL_GROUP_BY, STRICT_TRANS_TABLES, NO_ZERO_IN_DATE, NO_ZERO_DATE, ERROR_FOR_DIVISION_BY_ZERO, NO_AUTO_CREATE_USER и NO_ENGEN.

Ответ 3

Я попал в ситуацию, когда данные смешивались между NULL и 0000-00-00 для поля даты. Но я не знал, как обновить "0000-00-00" до NULL, потому что

 update my_table set my_date_field=NULL where my_date_field='0000-00-00'

больше не разрешено Мой обходной путь был довольно прост:

update my_table set my_date_field=NULL where my_date_field<'1000-01-01'

потому что все неправильные значения my_date_field (правильные даты или нет) были до этой даты.

Ответ 4

Проблема с синтаксисом конфигурации

В некоторых версиях MYSQL (проверенных 5.7. *) в системах * nix вы должны использовать этот синтаксис:

[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"

Более полный обзор конфигурационных значений и sql-режима:

Как установить постоянные флаги режима Sql

Ответ 5

Просто добавьте строку: sql_mode = "NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"

внутри файла: /etc/mysql/mysql.conf.d/mysqld.cnf

то sudo service mysql restart

Ответ 6

Сначала выберите текущий сеанс 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

а затем установите sql_mode без 'NO_ZERO_DATE':

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 = '...';

Ответ 7

Он работает для 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)

Вы можете создать SQLFiddle для воссоздания вашей проблемы.

http://sqlfiddle.com/

Если он работает для MySQL 5.6 и 5.7.8, но не работает 5.7.11. Тогда это, вероятно, будет ошибкой регрессии для 5.7.11.

Ответ 8

Этот ответ это только для MySQL 5.7:

На самом деле, лучше всего не указывать значение sql_mode, а использовать в PHP переменную сеанса с:

SET SESSION sql_mode= 'ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION'

Так что, по крайней мере, вы сохраняете другие значения по умолчанию.

Это безумие, что документация mysql не ясна, вам нужно удалить значения по умолчанию в sql_mode:

NO_ZERO_IN_DATE, NO_ZERO_DATE, я понимаю, но в будущих версиях это будет прекращено.

STRICT_ALL_TABLES, с этим, до того, как параметры будут игнорироваться, поэтому вам нужно удалить его тоже.

Наконец, тоже TRADITIONAL, но документация говорит об этом параметре: "выдавать ошибку вместо предупреждения" при вставке неверного значения в столбец ", с этим параметром даты с нулевыми значениями не вставляются, но без да.

MySQL не очень организован с этими параметрами и комбинациями.

Ответ 9

Чтобы решить проблему с MySQL Workbench (после применения решения на стороне сервера):

Удалите SQL_MODE в TRADITIONAL на панели настроек.

введите описание изображения здесь

Ответ 10

Комбинации опций для 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

Мои настройки в /etc/mysql/my.cnf на Ubuntu:

[mysqld]
sql_mode = "STRICT_TRANS_TABLES,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"

Ответ 11

set global sql_mode = 'STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION';