Я слышал слухи о плохих вещах, которые происходят с базами данных и почтовыми серверами, если вы меняете системное время во время их работы. Однако мне сложно найти какую-либо конкретную информацию о реальных рисках.
У меня есть сервер Postgres 9.3, работающий на хосте Debian Wheezy, и время отстает на 367 секунд. Могу ли я просто запустить ntpdate
или запустить openntp во время работы Postgres, или это может вызвать проблему? Если да, то какой более безопасный способ исправить время?
Есть ли другие службы, которые более чувствительны к изменению системного времени? Может быть, почтовые серверы (exim, sendmail и т. д.) или очереди сообщений (activemq, rabbitmq, zeromq и т. д.)?
решение1
Базы данных не любят обратных шагов во времени, поэтому вам не следует начинать с поведения по умолчанию, перескакивая время. Добавление опции -x
в командную строку изменит время, если смещение меньше 600 секунд (10 минут). При максимальной скорости изменения времени потребуется около полутора суток, чтобы скорректировать часы на минуту. Это медленный, но безопасный способ корректировки времени.
Перед запуском ntp
настройки времени вы можете начать ntp
с опции, например, -g 2
проверки того, насколько велико смещение, которое он обнаруживает. Это установит смещение паники на 2 секунды, что должно быть относительно безопасно.
Альтернативный вариант, который я использовал до того, как этот вариант стал доступен, заключался в написании цикла, который сбрасывал часы назад на часть секунды каждую минуту или около того. Если вы проверите, что сброс не изменит секунду, это, скорее всего, безопасно. Если вы интенсивно используете временные метки, у вас могут быть неупорядоченные записи.
Обычный вариант — выключить сервер на достаточно долгое время, чтобы не было обратного движения часов. ntp
или ntpdate
можно настроить так, чтобы часы перешли на правильное время при запуске. Это следует сделать до запуска базы данных.
решение2
Базы данных могут быть особенно уязвимы к изменениям системного времени, если они очень активны и имеют временные метки на внутренних записях. В общем, если ваше время отстает, у вас будет гораздо меньше проблем, если вы внезапно переместитесь вперед, чем если вы были впереди и внезапно переместились назад.
Как отмечает Джоффри, гораздо чаще проблемы с внезапными скачками времени возникают у приложения, чем у самой базы данных. Самый безопасный способ исправить время — закрыть приложение на N+1 минут (где N — количество минут, на которое ваши системные часы опережают), а затем синхронизировать время, запустить NTP и перезапустить приложение. Если вы не можете допустить такого длительного простоя в приложении, я могу только посоветовать вам сделать резервную копию базы данных перед синхронизацией времени, а затем предложить дохлую белку богу компьютерного мира и просто нажать на курок. Ладно, я немного шучу, но я не могу придумать никакого другого «безопасного» способа, кроме как допустить сбой приложения.
решение3
Обычно при мгновенном скачке времени не сервер базы данных подвержен ошибкам, а приложения, использующие время.
Обычно существует два способа отслеживания времени: отслеживание собственного времени или сравнение системного времени. Оба имеют некоторые положительные и отрицательные стороны.
Отслеживание собственного времени
Я вижу, как это используется в некоторых встроенных программах и системах, где точное время не так уж и критично. В основном цикле приложения заботится о способе отслеживания «тика». Это может быть сигнал тревоги, выдаваемый ядром, sleep или select, который дает указание на количество прошедшего времени. Когда вы знаете, сколько времени прошло, вы знаете, что можете добавить или вычесть это время из счетчика. Этот счетчик заставляет ваше приложение синхронизации работать. Например, если счетчик превышает 10 секунд, вы можете что-то отменить или вам нужно что-то сделать.
Если приложение не отслеживает время, счетчик не изменится. Это может быть желательно в зависимости от дизайна вашего приложения. Например, отслеживание того, сколько времени занимает длительный процесс, обрабатывается проще с помощью счетчика, чем списка временных меток начала/остановки.
За:
- Не зависит от системных часов
- Не сломается при большом перекосе
- Никаких дорогостоящих системных вызовов
- Маленькие счетчики будут занимать меньше памяти, чем полная временная метка.
Против:
- Время не очень точное.
- Изменение системного времени может сделать его еще более неточным.
- Время указывается относительно запуска приложения и не сохраняется.
Сравнение системного времени
Это система, которая используется чаще всего: хранить временную метку и сравнивать ее с временной меткой, используя вызов системного времени. Огромные перекосы в системном времени могут поставить под угрозу целостность вашего приложения, задача в несколько секунд может занять часы или завершиться немедленно в зависимости от направления часов.
За:
- Точное сравнение времени
- Сохраняется после перезагрузок и длительных отключений
Против:
- Выполняет системный вызов для получения новой временной метки для сравнения с другими временными метками.
- Приложение должно знать о перекосах, иначе оно может сломаться
Затронутые системы
Большинство приложений будут использовать временную метку для сравнения с задачами расписания. Для систем баз данных это могут быть очистки кэша.
Все приложения, которые используют базу данных и вызывают функции времени в языке запросов, будут затронуты перекосами, если приложение не обнаружит и не обработает их соответствующим образом. Приложения никогда не могут останавливаться или разрешать неопределенные периоды входа в зависимости от их цели.
Почтовые системы будут использовать временные метки и/или тайм-ауты для обработки устаревших или недоставленных писем. Рассогласование часов может повлиять на это, но с гораздо меньшим воздействием. Таймеры отсрочки, касающиеся повторного подключения к серверам, могут быть пропущены, что приведет к штрафам на подключающемся сервере.
Я не думаю (не исследовал), что сигналы тревоги ядра будут срабатывать при изменении системного времени. Системы, которые их используют, могут быть безопасными.
Решения
Аккуратно переместите время. Это можно найти в документации вашего любимого решения по времени.