MySQL CONVERT_TZ () - PullRequest
       30

MySQL CONVERT_TZ ()

37 голосов
/ 26 марта 2010

Я пытаюсь настроить базу данных, в которой хранится ежедневное время оповещения, указанное пользователями. Например, пользователь хочет получать оповещение, если какой-либо критерий выполняется каждый день с 7:00 до 7:30. В попытке реализовать это мне нужно учесть летнее время. Вот мое попытанное решение:

  1. Храните информацию о местном часовом поясе пользователей (в полной форме, например, «США / Восток») в одной таблице (например, userInfo), а время срабатывания будильника - в другой таблице (например, userAlarms).
  2. При запросе к таблице userAlarms, конвертируйте время UTC в местное время пользователя, как указано в столбце tz, хранящемся в таблице userInfo, через CONVERT_TZ(UTC_TIME(), 'UTC', userInfo.tz).

Вопрос 1. Насколько я понимаю, указание названия часового пояса (например, США / Восточный регион) должно учитывать летнее время. Например, вызов CONVERT_TZ('00:00:00', 'UTC', 'US/EASTERN') 1 января должен дать '19: 00: 00', но 1 июля вызов должен дать '20: 00: 00'. Я прав?

Вопрос 2. Если Q1 правильный, мне нужно постоянно обновлять таблицу часовых поясов MySQL, чтобы поддерживать смещения UTC часового пояса в актуальном состоянии?

Вопрос 3. Пример, приведенный в документации MySQL SELECT CONVERT_TZ('2004-01-01 12:00:00','GMT','MET'), выдает «NULL» при запуске на моем сервере. Может ли это быть вызвано отсутствием настройки таблиц часовых поясов?

Как я могу это проверить?

Ответы [ 3 ]

26 голосов
/ 27 мая 2011

Если это дает ноль, то таблицы TZ не были установлены:

SELECT CONVERT_TZ(now(),'US/Eastern','US/Central');

Если у вас не настроены таблицы часовых поясов, вы можете обновить час смещение в пользовательской таблице и затем выполните:

select utc_timezone() - interval user_timezone_offset_in_hours hour
from userinfo a
where user_id = 999;

Однако вам все равно нужен способ обновить часовой пояс пользователя.

Если вы пишете это для веб-приложения, вы можете получить часовой пояс с помощью javascript, вот статья , в которой описывается, как (не пробовал, но, похоже, это будет работать). 1011 *

Небольшое объяснение относительно "интервала" выше ...

Одной из наиболее хитростей в MySQL является использование INTERVAL ключевое слово, лучше всего показанное на примере (числовое значение может быть выражением или значением поля)

select now() today, now() - interval 1 day yesterday;
+---------------------+---------------------+
| today               | yesterday           |
+---------------------+---------------------+
| 2011-05-26 13:20:55 | 2011-05-25 13:20:55 |
+---------------------+---------------------+

Вы можете добавлять их и вычитать их так, как вам нравится, поэтому я никогда возиться с функцией добавления / вычитания / преобразования даты / времени

select now() a, now() - interval 1 day + interval 4 hour + interval 8 minute b;
+---------------------+---------------------+
| a                   | b                   |
+---------------------+---------------------+
| 2011-05-26 13:24:16 | 2011-05-25 17:32:16 |
+---------------------+---------------------+

Вы можете использовать отрицательные числа (должно быть хорошо для отрицательных смещений часового пояса) это одно и то же:

select now() - interval 1 month a, now() + interval -1 month b;
+---------------------+---------------------+
| a                   | b                   |
+---------------------+---------------------+
| 2011-04-26 13:38:05 | 2011-04-26 13:38:05 |
+---------------------+---------------------+
24 голосов
/ 16 марта 2011

Я нашел эту ветку полезной и решил поделиться страницей с документами для импорта этой информации. Я сделал именно так, как указано ниже, в CentOS и RHEL, и это сработало безупречно. Теперь я могу использовать функцию CONVERT_TZ с такими аргументами, как «GMT» и «US / Eastern».

Из документации MySQL это как импортировать информацию таблицы часовых поясов MySQL:

http://dev.mysql.com/tech-resources/articles/4.1/time.html


Для всех пользователей, работающих под управлением MySQL 4.1.3 или новее в системе на основе Unix (напомним, это еще не работает в системах Windows):

Заполните таблицы часовых поясов.

Для этого запустите программу mysql_tzinfo_to_sql, поставляемую с дистрибутивом MySQL. mysql_tzinfo_to_sql читает файлы часовых поясов операционной системы и генерирует из них операторы SQL. Затем операторы SQL обрабатываются mysql для загрузки таблиц часовых поясов.

Для успешного запуска mysql_tzinfo_to_sql необходимо знать, где хранятся файлы часовых поясов операционной системы на сервере; проверьте каталог с именем, похожим на /usr/share/zoneinfo. Передайте имя каталога в командной строке на mysql_tzinfo_to_sql и отправьте вывод в программу mysql. Вот пример.

shell> mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root mysql

Примечание. Приведенная выше команда предполагает, что "mysql_tzinfo_to_sql" и "mysql" находятся на вашем пути. Если это не так, вам нужно будет указать полный путь к обоим при запуске команды или переключиться в папку bin mysql и использовать такую ​​команду:

shell> ./mysql_tzinfo_to_sql /usr/share/zoneinfo | ./mysql -u root mysql
19 голосов
/ 13 сентября 2010

Q1: Да, CONVERT_TZ учитывает переход на летнее время. Эта информация и время начала / окончания летнего времени для каждого часового пояса хранятся в таблицах time_zone_ *.

Q2: Да, как указано в документации MySQL, информация о часовом поясе меняется в зависимости от политики каждой области. Вам придется обновлять таблицы time_zone_ * каждый раз, когда происходит изменение. Отстой, чтобы быть ЭТОМ иногда, это один из них.

Q3: это 5 таблиц часовых поясов, запросите их, чтобы узнать, есть ли в них что-то:

select * from mysql.time_zone_transition_type;
select * from mysql.time_zone_transition;
select * from mysql.time_zone_name;
select * from mysql.time_zone_leap_second;
select * from mysql.time_zone;
...