Хабрахабр

Анатомия инцидента, или как работать над уменьшением downtime

Для каких-то сервисов на начальном этапе важнее скорость разработки фич, в этот момент и команда не сформирована полностью, и технологии выбираются не особо тщательно. Рано или поздно в любом проекте настает время работать над стабильность/доступностью вашего сервиса. Но допустим, что момент X все-таки настал и вас начало волновать, сколько времени в отчетный период "лежит" ваш сервис. Для других сервисов (чаще технологические b2b) для завоевания доверия клиентов необходимость обеспечения высокого uptime возникает с первым публичным релизом. Под катом я предлагаю посмотреть, из чего складывается время простоя, и как эффективнее всего работать над его уменьшением.

Показатели

Следовательно, если мы начали уменьшать downtime, его в первую очередь и нужно начать измерять. Очевидно, что прежде чем что-то улучшать, нужно понять текущее состояние.

Мы не будем здесь подробно говорить о том, как конкретно это делать, плюсы и минусы разных подходов, но тезисно процесс выглядит как-то так:

  • опираемся на около-бизнесовые метрики (ошибки в работе сервиса, время отклика сервиса, $/second, signups/second итп)
  • определяем, что такое хорошо, а что такое плохо
  • переход хорошо->плохо является началом инцидента
  • переход плохо->хорошо — конец инцидента
  • время от начало до конца — длительность инцидента (кэп с нами)
  • сумма длительностей инцидентов за период (месяц/квартал/год) — время простоя (downtime)
  • <время простоя>/<длительность периода> * 100 = процент доступности за период

Когда говорят об uptime/downtime, часто упоминают еще один показатель:

Учитывая, что все инциденты разные, усреднение длительности ни о чем в системном плане нам сказать не может. MTTR (mean time to repair) — среднее время от начала инцидента до его окончания.
Проблемы с ним начинаются прямо с первого слова в аббревиатуре.

В этот раз мы не будем ничего усреднять, а просто посмотрим, что происходит в ходе инцидента.

Анатомия инцидента

Давайте посмотрим, какие значимые этапы можно выделить в ходе инцидента:

  • detection — интервал между первой ошибкой, которую мы отдали пользователю, до того, как дежурному пришло SMS
  • reaction — от получения уведомления о проблеме до момента, когда человек приступил к решению данной проблемы (обычно в этот момент событие в мониторинге переводится в состояние Acknowledged)
  • investigation — от начала работы над проблемой до момента, когда понятна причина инцидента и мы знаем, что нужно сделать, чтобы восстановить работу.
  • elimination — время восстановления, например, откатываем релиз, промоутим новый master primary сервер БД

А пока рассмотрим подробнее каждую стадию. Возможно наша модель неполная и есть какие-то еще стадии, но предлагаю их вводить только после осознания, как это поможет нам на практике.

Detection

Почему не отправлять уведомление при первой же ошибке, которую получил пользователь? Почему вообще мы тратим время на обнаружение внештатной ситуации? Я думаю, что не существует ни одного более-менее крупного сервиса, у которого бы не было постоянного "фонового" потока ошибок. На самом деле я знаю многие компании, которые пытались так делать, но от этой идеи отказывались буквально через несколько часов, за которые получили несколько десятков SMS. Не все из них признак того, что что-то сломалось, бывают еще и баги в софте, невалидные данные полученные из формы и недостаточная валидация, итд.

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

Как мы можем сократить время обнаружения? Но вернемся к нашей изначальной задаче — снижению длительности инцидентов. Придумывать супер-логику обнаружения аномалий? Быстрее уведомлять?

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

Reaction

Мы предполагаем, что мониторинг справился с обнаружением проблемы и мы успешно разбудили дежурного инженера (вся эскалация тоже отработала на предыдущем этапе). Здесь у нас чисто человеческий фактор.

Его действия: Рассмотрим "худший" случай, выделенной дежурной службы у нас нет, и алерт настиг мирно спящего админа.

  • среагировать на SMS: тут очень помогает жена с чутким слухом, различные приложения для телефона, усиливающие эффект от получения SMS (1-5 минут)
  • принять решение о том, что из кровати он все-таки будет вылезать: если алерты настроены неправильно, человек может 2 минуты ждать "а вдруг придет resolve?" и уснуть (1-15 минут)
  • добраться до ноута, открыть глаза, проснуться, добраться до мониторинга, нажать Ack: (1-15 минут)

По моим наблюдениям такое время реакции похоже на правду. В итоге в худшем случае получаем 35 минут реакции.

Ни в коем случае не нужно писать регламент, согласно которому только что проснувшийся человек должен пошевеливаться! Так как в на этом этапе мы имеем дело с людьми, нужно действовать крайне осторожно и продумано. Попробуем просто создать условия.

Это делается очень просто: сделать критерий алерта нечувствительным к мелким проблемам и уведомлять, если инцидент длится какое-то значимое время. Давайте для начала уберем сомнения инженера в том, что проблема закончится сама. Да, мы только что увеличили длительность стадии "detection", но давайте рассмотрим на примере:

  • увеличиваем время обнаружения на 5 минут
  • количество инцидентов снижается: все короткие всплески ошибок как правило укладываются в 1 минуту. Эти короткие инциденты нужно обязательно фиксировать, но без уведомления людей. Часто суммарно они дают очень большое время простоя, но разбираться с ними можно в рабочее время. Для этой задачи вам потребуется высокая детализация в мониторинге, так как проблема уже закончилась, а диагностические тулзы в большинстве своем не хранят истории.
  • если человек вынужден реагировать на алерты раз в месяц или реже, а не через день, он будет реагировать на это более адекватно и не относиться к этому как к рутине
  • отложенная нотификация позволяет человеку не думать: если SMS пришло, значит всё серьезно и само не исправится

Если вас и такое время реакции не устраивает, стоит подумать о дежурной службе. Потенциально такой подход позволит сократить суммарное время реакции, на 15+ минут.

Investigation

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

  • смотрим в мониторинг, логи (если мониторинга недостаточно), запускаем еще какие-то диагностические тулзы
  • выдвигаем гипотезы
  • проверяем гипотезы, либо по метрикам, либо выполняя какие-то действия (рестартим все подряд:)
  • оцениваем результаты изменений
  • коммуницируем с коллегами, если ваших знаний о конкретной подсистеме недостаточно
    и так до просветления или окончания инцидента.

Как же ее уменьшать?
Здесь все не очень однозначно, есть несколько векторов: Эта стадия обычно самая значимая в суммарной длительности инцидента.

  • упрощать инфраструктуру: представьте, как быстро траблшутят люди, у которых одна база данных и один сервис
  • распространение знаний в команде: идеально, если коммуникация людей будет идти не в процессе инцидента, а во время ежедневной работы (коммуникация людей вообще очень долгий процесс)
  • мониторинг: многие думают, что мониторинг работает только на стадии "detection", но на самом деле он может выступать оптимизацией процесса проверки гипотез ("штатно ли работает БД?", "не уперся ли мой сервис в ресурсы?") и еще как транспорт распространения знаний в команде. "Серега, проверь, есть ли в логе X ошибки про дедлоки?" можно превратить в триггер, в описание которого будет ссылка на wiki с инструкцией.

Elimination

Но бывает так, что сразу понятна причина, но восстановление будет очень долгим. Как я говорил выше, эта стадия часто сливается с предыдущей. Например, у вас умер сервер с master primary (еще долго не смогу к этому привыкнуть:) базой данных, а реплику вы ни разу не промоутили, то есть вы будете читать документацию, раскатывать новый конфиг приложений итд.

Но давайте посмотрим, какие направления нам можно попробовать проработать проактивно: Естественно после каждого значимого инцидента нужно разбираться, как не допустить такое снова или сильно ускорить восстановление.

  • инструментарий управления инфраструктурой: если для того, чтобы все починить вам нужно раскатить новый конфиг, но это делается минимум за 20 минут — это ваше ограничение. Попробуйте придумать сценарии, что может произойти и способ экстренного ускорения каких-то процессов. Например, в ansible у вас настроен serial (параллельность выполнения задач) = 3, но если все равно лежим, можно катиться с serial=30, нужно всех научить это переопределять (аналогично про rolling update strategy в kubernetes).
  • учения: если вы знаете вероятные сценарии отказа и восстановление у вас не автоматизировано, у вас должны быть инструкция, которая обязательно должна быть протестирована. Запланируйте downtime (если нужно), проведите учения. Часто на этом этапе такие кейсы автоматизируются, так как в процессе учений выясняется большинство подводных камней даже самых сложных на первый взгляд процедур.
  • взаимодействие с подрядчиками: вы должны заранее знать, что будете делать, если вашему хостеру станет плохо. Часто осознание вероятности проблемы и затрат на закрытие рисков приводит к выводу — "просто будем ждать восстановления". Но с другой стороны к такому сценарию будут готовы и инженеры и бизнес. Например, можно проработать вопрос с переключением вашего трафика на заранее заготовленную заглушку, уведомить пользователей заранее заготовленным письмом итд. Или наоборот, вы делаете инструкцию, по которой мы даем хостеру 30 минут на восстановление, а дальше начинаем переезд в другой ДЦ, где уже есть реплика БД, но нужно развернуть все остальное. И здесь опять же учения, засекаем время на переезд итд.

MTBF (Mean Time Between Failures)

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

Здесь на первый план выходит вопрос, насколько вы позаботились об отказоустойчивости вашего сервиса:

  • есть ли единые точки отказа (SPOF) в инфраструктуре, какова вероятность отказа?
  • насколько вы уверены, что нет SPOF, о которых вы не знаете? (это ровно та проблема, которую решают с помощью chaos monkey)
  • хорошо ли балансировщики нагрузки отрабатывают отказы? (мой доклад про балансировку)
  • насколько отказоустойчива сеть?
  • насколько надежен датацентр?

Потом по такой карте планомерно работают, закрывая в первую очередь высоковероятные и серьезные по воздействию сценарии. Иногда, чтобы все это просчитать/спрогнозировать делают "карту рисков", где у каждого сценария (который смогли предположить, естественно всегда остаются те, которых мы пока не знаем) есть вероятность + эффект воздействия (даунтайм короткий/длинный, потеря данных, репутационные потери, итп).

Сейчас много говорят о том, что очень полезно писать "разборы" (post mortem) инцидентов, где анализируются причины проблемы, действия людей, прорабатываются возможные будущие действия. Другой прием, который можно использовать — классификация прошедших инцидентов. Но чтобы быстро взглянуть на причины всех аварий за прошлый период удобно просуммировать их длительность с группировкой по "классам проблем" и там где больше всего downtime принимать меры:

  • человеческие ошибки: снижать количество ручных действия в production, разные защиты от ошибки операторов
  • неудачные релизы: стоит улучшать тестирование (в том числе нагрузочное)
  • ошибки в приложениях: чинить утечки, крэши и другие "зависания"
  • сеть: купить оборудование, настроить, нанять сетевиков, сменить подрядчика
  • базы данных: нанять DBA, позаботиться про отказоустойчивость, купить железо получше
  • ДЦ: думать про резервный или переезд
  • внешние воздействия (ddos, блокировки, отзывы сертификатов, домены): купить antiddos, запастись проксями, замониторить срок действия доменов/сертификатов, иметь несколько сертификатов от разных CA.

То есть, если даже не пытаться предугадать возможные сценарии проблем, то работать с уже случившимися инцидентами определенно стоит.

Итого

Все инциденты разные:

Алгоритм работы над увеличением uptime очень похож на любую другую оптимизацию:

измеряй -> анализируй -> пробуй улучшить -> оценивай результат

Обычно бывает, что самые простые изменения приносят самый значимый эффект. По своему опыту могу сказать, что для существенного улучшения аптайма достаточно просто начать за ним следить и анализировать причины инцидентов.

Наш сервис мониторинга помогает не только со стадией "detection", но и сильно сокращает " investigation" (клиенты подтвердят)

Теги
Показать больше

Похожие статьи

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *

Кнопка «Наверх»
Закрыть