Горячее обновление кода не нужно?

6 марта 2013

Как вам хорошо известно, некоторые языки программирования, например, Erlang, поддерживают горячее обновление кода, то есть, обновление кода программы без ее остановки. Часто эта способность преподносится в качестве существенного преимущества языка программирования, который ею обладает, над языками, в которых горячего обновления кода нет. Однако чем больше я думаю о горячем обновлением кода, тем больше склоняюсь к мысли, что на практике оно никому не нужно. И вот почему.

Начнем с того, что даже гуру Erlang’а рекомендуют вовсе не использовать обновление кода «на лету», или использовать, но только при крайней необходимости и только в stateless процессах. Дело в том, что если процесс обладает некоторым состоянием и при обновлении представление этого состояния изменяется, то на программиста ложится ответственность по корректному преобразованию состояния из старого представления в новое. Также требуется написать и протестировать обратное преобразования на случай, если в новой версии приложения будет обнаружена ошибка и обновление придется откатывать. А ведь помимо состояния также может изменить интерфейс процесса и тп.

Вообще, в каких ситуациях нужно это самое горячее обновление? В десктопных и мобильных приложениях оно явно не нужно. Устанавливаем новую версию, перезагружаем программу, работаем дальше. Никаких проблем. Как на счет веб-приложений? В 99% случаев здесь обновление «на лету» также не нужно. Если ваш сайтик с 1000 посетителями в сутки будет несколько секунд недоступен, скорее всего, никто ничего не заметит. А как же крупные веб-проекты типа Яндекса, Google и тп? Там тоже нет никакого горячего обновления. В этих проектах используются Perl, Python, PHP, Java, C++ и прочий мейнстрим, никакого Erlang’а.

Делается очень просто. Новая версия приложения деплоится в новый каталог, правится конфиг веб-сервера, после чего веб-серверу шлется сигнал перечитать конфиг. Незавершенные запросы обрабатываются старой версией приложения, новые обрабатываются уже новой. Пользователь ничего не замечает и при необходимости можно быстро откатиться к предыдущей версии приложения. Иногда используются менее удачные схемы, при которых часть пользователей может увидеть страницу с сообщением об ошибке (все вспомнили Twitter, да?) или даже пятисотку. В таких ситуациях апдейты обычно катятся, когда число пользователей онлайн минимально.

Чаты. Jabber, Skype, ICQ и так далее. Казалось бы, тут все серьезнее, но в действительности — ничего подобного. Если ваш разговор в Скайпе прервется (или, скажем, притупит секунд на десять), от этого абсолютно никто не пострадает. На самом деле, эти звонки по Скайпу и так постоянно рвутся и всем на это пофиг. С Jabber, ICQ и прочими чатиками все еще проще. Если клиентское приложение видит, что соединение разорвалось, оно просто устанавливает новое, с другим фронтом.

Телефония. Тут несколько сложнее, чем с чатиками, потому что от звонка по мобильному или городскому телефону может зависит жизнь человека, если это вызов скорой помощи или пожарных. Одно из возможных решений следующее. Когда на узел (сервер, свич — на что там катят обновления Билайны?) приходит апдейт, новые звонки переадресовываются на другие узлы. С активными звонками поступаем так. Если звонок длится более десяти минут, вряд ли это вызов скорой помощи. Такие звонки можно смело обрывать. Ждем завершения всех звонков, обновляемся, принимаем новые звонки. В действительности, мобильная связь также часто бывает недоступна и всем на это пофиг. Пробовали позвонить родным в полночь 31-го декабря или сразу после теракта в московском метро? Или просто из Замкадья?

Примечание: По поводу телефонии. Автор осознает, что рассуждать о предметной области, в которой он ничего не понимает, грешновато (не менее, чем говорить о себе в третьем лице), однако не может удержаться. Также он припас кое-какие «хардварные» аргументы, которые будут озвучены чуть ниже, компенсирующие этот косяк.

Торговля ценными бумагами. Осуществляется далеко не круглосуточно. У бирж есть часы работы, а также выходные дни. Катим обновления по субботам, и все счастливы. Медецинское оборудование. Ни один нормальный человек не покатит апдейт на работающий аппарат исскуственного дыхания. ПО для орбитальных станций, марсаходов и тп. Насколько мне известно, все равно пишутся на Си.

И даже если вы написали супер крутое Erlang-приложение, которое никогда не лежит, а также обновляете ядро ОС без перезагрузки с помощью Ksplice или некого альтернативного механизма, все равно у вас есть какой-нибудь PostgreSQL, который тоже нужно иногда обновлять и который для этого требуется останавливать. А еще Амазоны все равно падают (хотя, казалось бы, облачный хостинг) и железо все равно дохнет. Если ваш сервис имеет много пользователей и должен быть доступен 24/7, то выход из строя нескольких серверов должен считаться абсолютно штатной ситуацией. Не важно, связана ли остановка со смертью железа или обновлением софта. Если от временной недоступности одного сервера ваш бизнес несет огромные невосполнимые потери, лучше поскорее выйти из бизнеса.

В общем, я не могу придумать ни одной ситуации, где действительно стоило бы использовать горячее обновление кода и, соответственно, иметь дело со всеми присущими ему сложностями. А вы?

Дополнение: Все же, в паре случаев горячее обновление кода может быть довольно удобным

Метки: , , , .


Вы можете прислать свой комментарий мне на почту, или воспользоваться комментариями в Telegram-группе.