MySQL JDBC Driver 5.1.33 - Випуск часової зони


359

Деякі відомості:

У мене на веб-сайті Java 1.6 працює Tomcat 7. База даних - MySQL 5.5. Раніше я використовував драйвер Mysql JDBC 5.1.23 для підключення до БД. Все працювало. Нещодавно я оновив драйвер Mysql JDBC 5.1.33. Після оновлення Tomcat видасть цю помилку під час запуску програми.

WARNING: Unexpected exception resolving reference
java.sql.SQLException: The server timezone value 'UTC' is unrecognized or represents more than one timezone. You must configure either the server or JDBC driver (via the serverTimezone configuration property) to use a more specifc timezone value if you want to utilize timezone support.

Чому це відбувається?


1
Як виглядає ваша URL-адреса JDBC?
Девід Левеск

Перевірте мою відповідь stackoverflow.com/a/44720416/4592448 . Я думаю, його найкраща відповідь)
Фортран

Відповіді:


673

Мабуть, щоб отримати версію 5.1.33 драйвера MySQL JDBC для роботи з часовим поясом UTC, потрібно serverTimezoneчітко вказати в рядку з'єднання.

jdbc:mysql://localhost/db?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC

4
Згідно з документами useJDBCCompliantTimezoneShift не впливає при використанні useLegacyDatetimeCode = false. Тому він там не потрібен ...
matof

24
Це вирішує мою помилку. Додаткова примітка: уникнути & & & amp; у файлі persistent.xml: <властивість = = javax.persistence.jdbc.url "value =" jdbc: mysql: // localhost / test? useUnicode = true & amp; useJDBCCompliantTimezoneShift = true & amp; useLegacyDatetimeCode = false & amp; server> Timezone UTC = "
pdem

5
Це не правильно. Точка useLegacyDatetimeCode = false не вказує serverTimezone, тому клієнт виправляє параметри часового поясу. Це помилка у цій версії клієнта MySQL.
antgar9

2
Це рішення руйнує часовий пояс, крім GMT. Я думаю, що правильне рішення недооцінене нижче
DuncanSungWKim

1
розчин працює з 8.0.17. Сталося зі свіжою установкою MySQL. Не можу повірити, що ця помилка не була виправлена ​​через стільки років.
Tilman Hausherr

101

Я вирішив цю проблему, налаштувавши MySQL.

SET GLOBAL time_zone = '+3:00';


6
якщо ви використовуєте ММС часовий пояс це +3, то ви можете використовувати folowing в якості адреси БД: jdbc:mysql://localhost/db?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=Europe/Moscow. Схоже, mysql-з'єднувач не розуміє коротких назв часових поясів.
бабай

2
Що ви робите, коли літній час змінює годинник?
isapir

3
За допомогою mysql 8.0 ви можете зателефонувати "set persist time_zone = '+00: 00';" встановити його на UTC постійно, без необхідності редагувати my.cnf або перезавантажувати сервер. Дивіться mysqlserverteam.com/…
ccleve

Якщо ви встановлюєте це за допомогою унікального ручного запиту SQL, це налаштування повернеться до того, яким було початкове значення після перезавантаження БД.
CBA110

чи працює - не забудьте змінити локальний рядок часового поясу замість +3 SET GLOBAL time_zone = '+3: 00';
Правін

61

Прочитавши кілька публікацій на цю тему, протестувавши різні конфігурації та виходячи з деякої інформації з цієї теми помилки mysql , ось що я зрозумів:

  • часовий пояс сервера важливий, зокрема, для перетворення дат, що зберігаються в базі даних, у часовий пояс сервера додатків. Є й інші наслідки, але це найбільш помітне
  • GMT x UTC часові пояси. GMT був задуманий в кінці 19 століття і може бути зміщений між стандартним та літнім часом. ця властивість може призвести до ситуації, коли сервер бази даних переходить на літній час, а додаток цього не помічає (можливо, є інші ускладнення, але я не досліджував далі). UTC не змінюється за часом (він завжди знаходиться приблизно в межах 1 секунди середнього сонячного часу при довжині 0 °).
  • Визначення serverTimeZone було введено в mysql jdbc роз'єми версії 5.1 вперед. до версії 8 її можна було ігнорувати useLegacyDatetimeCode=true, що в поєднанні з цим useJDBCCompliantTimezoneShift=trueпримушує програму отримати часовий пояс бази даних при кожному з'єднанні. У цьому режимі часові пояси GMT, такі як "Британський літній час", будуть перетворені на внутрішній формат java / JDBC. Нові часові пояси можна визначити у файлі .properties, такому як цей
  • Починаючи з драйвера jdbc версії 8, автоматичне узгодження часу ( useJDBCCompliantTimezoneShift) та застарілий формат часу ( useLegacyDatetimeCode) було вилучено ( див. Журнал змін файлів mysql jdbc ). тому встановлення цих двох параметрів не впливає, оскільки вони повністю ігноруються (новий за замовчуванням useLegacyDateTimeCode=false)
  • Таким чином, налаштування serverTimezoneстало обов'язковим, якщо жоден із часових поясів (сервери додатків / баз даних) не має формату "UTC + xx" або "GMT + xx"
  • Настроювання часу сервера на UTC не впливає (наприклад jdbc:mysql://localhost:3306/myschema?serverTimezone=UTC, навіть якщо ваші сервери додатків / баз даних не перебувають у цьому часовому поясі. Важливо, щоб рядок з'єднання додатків + база даних синхронізувались з тим самим часовим поясом. Різними словами , просто встановлення serverTimezone = UTC з іншим часовим поясом на сервері баз даних змістить усі дати, вилучені з бази даних
  • Часовий пояс MySQL за замовчуванням можна встановити на UTC + 0 за допомогою файлів my.ini або my.cnf (windows / linux відповідно), додавши рядок default-time-zone='+00:00'(детальніше у цій публікації StackOverflow )
  • Базам даних, налаштованим на AWS (веб-сервіси Amazon), автоматично призначається UTC + 0 за замовчуванням ( див. Сторінку довідки AWS тут )

1
Гарна відповідь, дякую. Всі кулі корисні. Я пішов із пропозицією помістити файл default-time-zone = '+00:00'у домашню мову /usr/local/etc/my.cnf. Здається, що пробіли навколо =важливі, хоча ви можете відредагувати цю кульку, щоб включити їх.
Марк Едінгтон

51

Якщо ви використовуєте Maven, ви можете просто встановити іншу версію роз'єму MySQL (у мене була така ж помилка, тому я змінив з 6.0.2 на 5.1.39) у pom.xml:

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.39</version>
</dependency>

Як повідомляється в інших відповідях, ця проблема була виправлена ​​у версіях 6.0.3 або вище, тож ви можете використовувати оновлену версію:

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>6.0.3</version>
</dependency>

Maven автоматично відновить ваш проект після збереження pom.xmlфайлу.


2
Для тих, хто завантажив mysql-connector-java / 6 ->, просто завантажте, наприклад, mysql-connector-java / 5.1.20, і він повинен працювати. Дякую!
Поєднайте

6
слід уникати зниження рівня пониження. Крім того, він не зафіксований 6.0.6нерухомим. краще скористатися вищевказаним рішенням
phil294

я отримую таку ж помилку навіть із останньою jar [mysql-connector-java-6.0.5.jar: 6.0.5]
user2478236

18
Я маю це навіть у 8.0.12
Роберт Неєстрой

13
8.0.13 дає ту саму помилку. 5.1.47 працює для мене.
localhost

36

Рядок підключення слід встановити так:

jdbc:mysql://localhost/db?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC

Якщо ви визначаєте з'єднання у xmlфайлі (наприклад persistence.xml, standalone-full.xmlі т. Д.), Замість нього &слід використовувати &amp;або використовувати CDATAблок.


1
Це не правильно. Точка useLegacyDatetimeCode = false не вказує serverTimezone, тому клієнт виправляє параметри часового поясу.
antgar9

Це працювало для мене підключенням до MySQL 5.7 з phpStorm 2019.1.4.
moult86

29

Це помилка в mysql-connector-java від версії 5.1.33 до 5.1.37. Я повідомив про це тут: http://bugs.mysql.com/bug.php?id=79343

Відредаговано: Це було виправлено з mysql-connector-java 5.1.39

Це був помилка в класі TimeUtil у методі loadTimeZoneMappings, який викликає локалізацію /com/mysql/jdbc/TimeZoneMapping.properties файлу NPE. Якщо ви подивитеся на код, файл повинен знаходитися в завантажувачі класу TimeUtil, а не в TimeZone:

TimeUtil.class.getResourceAsStream(TIME_ZONE_MAPPINGS_RESOURCE);

Параметр useLegacyDatetimeCode дозволяє автоматично виправити різницю між часовими поясами клієнта та сервера при використанні дат. Тож вам точно допомагає не вказувати часові пояси в кожній частині. Якщо все-таки використовувати параметр serverTimeZone - це вирішення проблеми, а тим часом виправлення виправлення, ви можете спробувати краще виправити код, як і я.

  • Якщо це автономна програма, ви можете спробувати просто додати виправлений клас com / mysql / jdbc / TimeUtil до свого коду та бути обережним із порядком завантаження банку. Це може допомогти: https://owenou.com/2010/07/20/patching-with-class-shadowing-and-maven.html

  • Якщо це веб-додаток, простіше рішення - створити власний mysql-connector-java-5.1.37-patched.jar, замінивши .class безпосередньо в оригінальний jar.


Мило, дякую за повідомлення про це. Радий, що хтось зміг усунути помилку. Чи знаєте ви, коли виправлення вийде?
bluecollarcoder

Рішення, яке ви пропонуєте, є чудовим, але я думаю, що зміна джерела драйвера та управління залежністю від Maven, мабуть, занадто дратує для більшості людей.
bluecollarcoder

4
@Gili Це не виправлено станом на випуск 6.0.6
Imme22009

6
Помилка присутня в 8.0.11
Джон Маленький

3
@JohnLittle У мене ця проблема теж в 8.0.15, але помилка її більше не викликає. Часові зони завантажуються правильно, але CET та CEST (ці часові пояси викликають у мене проблеми) не включаються ні в TimeZone.getAvailableIDs()ні, ні в TimeZoneMapping.propertiesце, тому це рішення тут не допоможе. Рішення, ймовірно, може бути встановлене на кшталтserverTimezone=Europe/Berlin
JPT

29

Я вирішив поставити рядок з'єднання нижче в URL

jdbc:mysql://localhost:3306/db?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC

1
Це не правильно. Точка useLegacyDatetimeCode = false не вказує serverTimezone, тому клієнт виправляє параметри часового поясу.
antgar9

25

Він працював для мене лише додавши serverTimeZone = UTC у application.properties.
spring.datasource.url=jdbc:mysql://localhost/db?serverTimezone=UTC


22
  1. Я додав у конфігураційний файл mysql у розділі [mysqld]

    default_time_zone='+03:00'
  2. І перезапустіть сервер mysql:

    sudo service mysql restart

Де +03: 00 мій часовий пояс UTC.

Шлях до конфігураційного файлу на моєму ОС ubuntu 16.04:

/etc/mysql/mysql.conf.d/mysqld.cnf

ПОПЕРЕДЖЕННЯ: ЯКЩО ВІД ЧАСОВОЇ ЗОНИ ВІД ЛІТА ТА ЗИМО ЧАС. ВИ МОЖЕТЕ ЗМЕНИТИ UTC В КОНФІГУВАННІ, ЯКЩО ЗМІНУЙТЕ ЧАС. Двічі за рік (звичайно) або встановити CRONTAB з SUDO.

Моє URL-з'єднання jdbc:

"jdbc:mysql://localhost/java"

1
Потрібно перезапустити Mysql в основному нестартер майже в усіх випадках використання виробництва. Це стає ще більшою проблемою, коли задіяні реплікації.
bluecollarcoder

@bluecollarcoder Потрібно додати лише в розділі [mysqld]. Або додайте розділ [mysqld], якщо в ньому немає розділу. Приклад моєї конфігурації pastebin.com/j4F7t2KS
Fortran

1
Я оновив / etc / localtime мій сервер Linux з / usr / share / zoneinfo / US / Pacific до / usr / share / zoneinfo / America / Los_Angeles, потім перезапустив службу mysql, і це вирішило проблему для мене.
vinnyjames

У моєму випадку для наданого синтаксису сталася помилка при перезапуску, а правильний синтаксис: default-time-zone='+03:00'натомість відповідно до цієї відповіді . Також походить від DBeaver.
wscourge

це не підходить, якщо вам доведеться повідомити всім розробникам вашої компанії про зміну їх конфігурації MySQL :)
pheromix

16

У мене є та ж проблема, і я вирішив її, додавши до мого рядкового з'єднання лише "? ServerTimezone = UTC".

#

моя проблема:

java.sql.SQLException: Значення часового поясу сервера 'CEST' не розпізнається або являє собою більше одного часового поясу. Ви повинні налаштувати або сервер, або драйвер JDBC (через властивість конфігурації serverTimezone), щоб використовувати більш конкретне значення часового поясу, якщо ви хочете використовувати підтримку часового поясу.

my dbDriver = com.mysql.jdbc.Driver

my jar = mysql-connector-java-8.0.12.jar

my java = 1.8

my tomcat = Apache Tomcat Version 8.5.32

my MySql server = MySql ver.8.0.12 

14

Вищеописана програма призведе до помилки часового поясу.

Після того, як ваше ім'я бази даних потрібно додати наступне: ?useTimezone=true&serverTimezone=UTC. Після того, як ви зробите свій код, він справно працює.

Удачі :)



13

Все, що нам потрібно для вирішення проблеми serverTimezone:

String url = "jdbc:mysql://localhost:3306/db?serverTimezone=" + TimeZone.getDefault().getID()

Зі мною трапилось і з останньою версією 5.4.15. Але виправлено це: додаючи "? ServerTimezone =" + TimeZone.getDefault (). GetID () "прямо біля бази даних ур, вирішує проблеми.
Тес

10

Ви можете використовувати роз'єм MySQL в залежності від Maven,

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>8.0.14</version>
</dependency>

Тоді вам потрібно встановити потрібні параметри у application.propertiesфайлі,

spring.datasource.url=jdbc:mysql://localhost:3306/UserReward?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC
spring.datasource.username=testuser
spring.datasource.password=testpassword
# MySQL driver
spring.datasource.driverClassName=com.mysql.jdbc.Driver
spring.jpa.database-platform=org.hibernate.dialect.MySQL5Dialect

9

Я використовую mysql-connector-java-8.0.13 і в мене була така ж проблема. Я створив свою базу даних на консолі командного рядка і вирішив цю проблему, використовуючи рішення @Dimitry Rud у командному рядку:

SET GLOBAL time_zone = '-6:00';

Мені нічого не потрібно було перезавантажувати, встановлювати час і негайно запускати свій код у затемнення, це пов’язано без проблем.

Помилка повинна бути виправлена ​​у більш старій версії, але, думаю, я помилився, оскільки після створення бази даних у консолі я цього не встановив. Я не використовую робочий стіл або інший додаток для управління цим, а не консоллю.


6

З робочої версії mysql запустіть такі заяви sql:

  1. SET @@ global.time_zone = '+00: 00';
  2. SET @@ session.time_zone = '+00: 00';

за допомогою наступних операторів sql перевірте, чи були встановлені значення:

SELECT @@ global.time_zone, @@ session.time_zone;


2
Це спрацювало для мене, коли виникла помилка під час спроби встановити з'єднання з IntelliJ IDEA.
Faheem Hassan Zunjani

6

Це працювало для мене.

в DBeaver 6.0: Перейдіть у Налаштування з'єднання> Властивості драйвера> Часова зона сервера> Встановіть UTC.

Також у навесні config boot довелося встановити нижче властивість.

jdbc: mysql: // localhost: /? serverTimezone = UTC


5

Мабуть, щоб отримати версію 5.1.33 драйвера MySQL JDBC для роботи з часовим поясом UTC, потрібно чітко вказати serverTimezone у рядку з'єднання.

spring.datasource.url = jdbc:mysql://localhost:3306/quartz_demo?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC

3

У мене також була та сама проблема в LibreOffice Base. Тому я щойно вказав не "часовий пояс літнього часу" у рядку з'єднання.
** сюди введіть опис зображення **

Я спробував без "& serverTimezone = MST", але це теж не вдалося.

Я також спробував "& serverTimezone = MDT", і це не вдалося, тому чомусь це не любить літній час!


3

У мене була така ж проблема, коли я намагався працювати з проектом завантаження весни на windows.

URL-адреса джерела даних має бути:

spring.datasource.url=jdbc:mysql://localhost/database?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC


3

Виконайте нижче запиту до mysql DB, щоб вирішити помилку

MariaDB [xxx> SET @@global.time_zone = '+00:00';
Query OK, 0 rows affected (0.062 sec)

MariaDB [xxx]> SET @@session.time_zone = '+00:00';
Query OK, 0 rows affected (0.000 sec)

MariaDB [xxx]> SELECT @@global.time_zone, @@session.time_zone;

3

я отримав помилку, аналогічну вашій, але моє значення часового поясу сервера - 'афр. centralle Ouest ', тому я зробив наступні кроки:

MyError (у IntelliJ IDEA Community Edition):

    InvalidConnectionAttributeException: The server time zone value 'Afr. centrale Ouest' is unrecognized or represents more than one time zone. You must configure either the server or JDBC driver (via the 'serverTimezone' configuration property) to use a more specifc time zone value if you want to u....

Я зіткнувся з цією проблемою, коли оновив мій сервер mysql до SQL Server 8.0 (MYSQL80).

Найпростіше рішення цієї проблеми - просто записати нижче команду у свій робочий стіл MYSQL -

  SET GLOBAL time_zone = '+1:00'

Значення після часового поясу буде дорівнює GMT +/- Різниця у вашому часовому поясі. Наведений вище приклад стосується Північної Африки (GMT + 1: 00) / або для Індії (GMT + 5: 30). Це вирішить питання.

Введіть наступний код у вашому Mysql Workbench та виконайте запитання

[посилання на джерело для питання / проблеми]

[посилання на джерело для відповіді]

[Екран рішення рішення]


2
Connection con = DriverManager.getConnection("jdbc:mysql://localhost:3306/resultout? useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC","root",""))

Це фактично рішення цієї проблеми, але не просто копіюйте та вставляйте її у свою програму. Якщо ви просто прочитали рядок, ви знайдете 'resultout', це назва моєї бази даних, і ви повинні написати свою.

Є три рядкові компоненти, перший - URL, другий - ім'я користувача, а третій - пароль. У верхньому абзаці ми очистили, URL. Другий і третій рядкові компоненти, як було вказано ваше ім'я користувача та пароль, потрібно змінити відповідно.

Дякую


1

Я вирішив це питання без жодної зміни коду. просто перейдіть у налаштування часу та встановіть часовий пояс. У моєму випадку часовим поясом за замовчуванням був UTC, який я змінив на свій місцевий часовий пояс. Після того як я перезапустив усі сервіси, все працювало на мене.


1

Я запізнююсь, але якщо ви намагаєтеся через наступну помилку та використовуєте джерело даних (javax.sql.DataSource):

The server time zone value 'CEST' is unrecognized or represents more than one time zone.

Встановіть наступний рядок, щоб позбутися від помилки:

MysqlDataSource dataSource = new MysqlDataSource();
dataSource.setServerTimezone("UTC");

1

У моєму випадку це було тестове середовище, і мені довелося зробити існуючий додаток для роботи без будь-яких змін конфігурації, а якщо можливо, без будь-яких змін конфігурації MySQL. Я зміг виправити цю проблему, дотримуючись пропозиції @vinnyjames та змінивши часовий пояс сервера на UTC :

ln -sf /usr/share/zoneinfo/UTC /etc/localtime
service mysqld restart

Це мені було достатньо для вирішення питання.


1

Я додав у свій /etc/mysql/my.cnfфайл такий рядок :

default_time_zone='+00:00'

Перезапустив сервер MySQL:

systemctl restart mysql

І це працює як шарм.


0

Погодьтеся з відповіддю @bluecollarcoder, але краще використовувати TimeZone.getDefault().getID();в кінці рядка з'єднання:

"jdbc:mysql://localhost/db?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=" + TimeZone.getDefault().getID();  

У цьому випадку Timezoneпараметр автоматично оновлюється залежно від часового поясу локальної машини.


Це не правильно. Точка useLegacyDatetimeCode = false не вказує serverTimezone, тому клієнт виправляє параметри часового поясу.
antgar9

0

Просто змініть рядок з'єднання за допомогою наступного коду у файлі application.properties.


spring.datasource.url=jdbc:mysql://localhost:3301/Db?
   useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=
   false&serverTimezone=UTC

0

Немає впливу на встановлення часу сервера як UTC (наприклад, з jdbc:mysql://localhost:3306/myschema?serverTimezone=UTC , навіть якщо ваші сервери додатків / баз даних не перебувають у цьому часовому поясі. Важливо, щоб рядок з'єднання додатків + база даних синхронізувались з тим самим часовим поясом.

Іншими словами, просто встановлення serverTimezone=UTCіншого часового поясу на сервері бази даних змістить будь-які дати, вилучені з бази даних

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.