SRE. Рецепты выживания в продакшене для инженера по надежности

Mustand
Loe katkendit
Märgi loetuks
Autor kirjutab parasjagu seda raamatut
  • Maht: 50 lk.
  • Viimase uuenduse kuupäev: 23 juuni 2024
  • Uute peatükkide avaldamise sagedus: umbes üks kord 4 nädala jooksul
  • Kirjutamise alguskuupäev: 07 jaanuar 2024
  • Lisateave LitResi kohta: mustandid
Kuidas lugeda raamatut pärast ostmist
  • Lugemine ainult LitRes “Loe!”
Šrift:Väiksem АаSuurem Aa

13. Расселяйте критичные сервисы и непредсказуемые сервисы

Представьте себе ситуацию, что у вас есть один бекенд. Например, он отвечает за оформление заказа на сайте, что является критической функциональностью вашего бизнеса. Нет заказов = нет денег. В какой-то момент времени вы приходите к отличной идее, что хочется получать немного больше информации о том, что делает клиент на сайте. Вы добавляете отправку событий со стороны клиента в свой бекенд. Это ведь такое красивое решение: запрос с клиента проходит через бекенд, обогащается там дополнительной информацией и записывается в специальную базу данных для сбора исторических данных. У вас уже есть опыт и вы учли предыдущий совет про раздельные базы данных.

Данные приходят, вы сделали на этих данных очень красивые дашборды о поведении пользователя… Но в один день что-то идёт не так и весь бекенд ломается от нагрузки, с которой вы ничего не можете сделать. Оказалось, что в последнем утреннем релизе фронтенда закралась очень маленькая ошибочка, в результате которой все загружаемые пользователями страницы начали отправлять десятикратное количество своих событий. И самое печальное, что они продолжают это делать, даже если пользователь не производит никаких действий. В прямом смысле вы сами себе сделали Ddos-атаку.

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

Отсюда следует правило: не смешивайте сервисы.

Дополнительные преимущества такого подхода:

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

Для раздельных сервисов проще обеспечивать масштабирование.

Разделение сервисов повышает безопасность, ограничивая поверхность атаки и снижая риск для критически важных частей.

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

Выделенные сервисы облегчают мониторинг и выявление проблем.

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

14. Exponential backoff

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

Если у вас есть какой-то сервис, в который вы постоянно ходите с ретраями, пытаясь получить ответ – не надо его добивать, когда он уже сломался. Сломанный сервис вполне ясно говорит, что он не может обработать ваш запрос, и возвращает какую-то ошибку. Например, 500 или 503, или что-то еще начинающееся с цифры 5.

Это может быть в нескольких случаях:

– отвалился конкретно этот запрос по "какой-то причине"

– отвалился конкретно этот хост

– отвалился сервис целиком

– и еще масса других вариантов

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

С особенным вниманием этот совет стоит изучить разработчикам клиентских приложений… Что может быть лучше, чем ситуация, когда бекенд прилёг, а все клиенты начинают без перерыва пытаться всунуть ему всё новые и новые запросы? Самая интрига в том, что вы ничего не можете с ними сделать в моменте.

15. Учитесь деградировать заранее

Теперь немного про деградацию. Представьте себе, что ваши коллеги-маркетологи запустили рекламную акцию! С кем не бывает… Реклама, дающая новые заказы, это просто чудесно. Коллеги – классные ребята и всегда согласовывают с вами акции, к которым вы заранее готовитесь. Но что-то пошло не так и акция запустилась на сутки раньше, чем вы планировали добавить ресурсов в свою систему. Бекенд быстро сломался, в том числе из-за пользователей, беспрерывно нажимающих “обновить” в браузере. Деньги потрачены зря, вечеринку по поводу успешных продаж придётся отменить.

Совсем не сесть в калошу помогут средства деградации, которые надо сделать заранее. Если заранее не сделали, то сделайте после первого такого инцидента, когда вы задумались, что было бы неплохо иметь запасной парашют.

В случае прихода внезапного трафика у вас не будет никаких вариантов кроме: масштабировать и деградировать. Третий вариант – смириться и переждать – не рассматриваем.

Масштабировать сервис бывает довольно сложно. Сколько нужно будет времени, чтобы развернуть ещё ресурсов – кажется, это порядок минут в лучшем случае (и то, если вы заранее всё предусмотрели). Также важно оценить ваши возможности по оплате этих дополнительных ресурсов.

Деградацию предусмотреть достаточно легко. Это может быть автоматика или ручное управление. Автоматика работает быстро, но в ней могут быть ошибки случайного включения. Ручное управление – медленнее, но с вашим интеллектом и системой принятия решений.

Итак, к вам нагрянули пользователи. Причина вам неизвестна. Сколько это будет длиться – неизвестно. Нужно делать сразу всё: деградировать и масштабировать одновременно!

Деградация – это не "отвечаю через раз", это "отвечаю всегда, но не полной функциональность".

Желательно иметь несколько уровней деградации:

– всё плоховатенько – будем отключать эти малозаметные блоки, типа “сопутствующие товары” и “такие же как вы покупают”

– всё становится хуже – будем отключать функциональность по нарастающей важности, например “дата доставки” или “превью при наведении”

– все совсем плохо – отдаём статику типа “вот наши лучшие товары, на сайте технические работы”

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

Деньги: заранее оцените ваши возможности по быстрому масштабированию сервиса в случае необходимости. Любое железо стоит деньги. Согласуйте это количество денег с тем, кто отвечает за финансы. А-то может легко получиться так, что вы очень элегантно обработаете рекламную акцию, получите заказы, но все заработанные деньги уйдут на оплату облачных квот.

16. Кэши и заглушки

Это продолжение темы про деградацию. Если у вас есть всякие реал-тайм данные, которые вы готовите на каждый запрос пользователя, имейте в виду: тот сервис, откуда вы их реал-тайм берете, обязательно перестанет работать. Если хотите жить красиво – имейте какой-то универсальный дефолтный вариант ответа. Если вы для каждого пользователя показываете "Такие же как вы покупали вот это", то в случае поломки начните показывать "Топ-5 покупок в нашем магазине". Это точно лучше, чем не показывать ничего.

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

Состав этих кешей и заглушек необходимо согласовать с продакт-оунером.

17. Fallback или "последний шанс"

Теперь представим себе ситуацию, что вы уже отмасштабировали всё, что могли, выключили всю функциональность, которую в принципе можно было выключить, и это всё равно не помогает. Здесь появляется Тыква!

Тыква – это народное название для страницы последней надежды (fallback). В беспощадной борьбе с "502: Bad Gateway" (или другими ошибками про невозможность обработать запрос) выигрывает тот, кто сдаётся последним.

Подготовьте какую-то статическую страницу или набор страниц на тот случай, если всё пойдёт совсем плохо, и отправляйте туда пользователей, запросы которых не удалось обслужить. Состав страницы согласуйте с продакт-оунером.

Из чего можно сделать тыкву:

– если это сайт новостей, то периодически генерируйте статическую страницу с "Топ лучших новостей планеты всей"

– если это интернет-магазин, пусть там будет одна страница с вашим лучшим товаром и что-то полезное на javascript

– сделайте на странице "тетрис", в конце концов – это будет хотя бы забавно

– укажите на странице самые полезные данные для посетителя, которые помогут ему решить свою задачу, например: адрес шоурума, номер телефона для записи к специалисту, кнопка для связи через мессенджер…

Важно! В реальности всегда существуют запросы, которые не удалось обслужить ни одним способом. Об этом важно знать, поэтому на количество показов тыквы нужно сделать мониторинг. Когда вы начнете видеть данные о показах тыквы, вы можете с удивлением обнаружить, что в систему приходят запросы, в принципе неспособные корректно работать, например, из-за багов в системе. Удачной охоты!

18. Прогнозируйте нагрузку на смежников

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

Архитектура вашего проекта может быть какой угодно совершенной, но сценарий работы вашей фичи может вполне затрагивать и других.

Например, вы реализовали рассылку уведомлений на мобильный телефон, в тексте которого есть картинка, загружающаяся из хранилища. Конкретно ваша часть работает отлично и даже текст без опечаток. Вы попробовали на паре сотен получателей – всё понравилось, начинаем рассылать на всех, кто есть в нашей базе. Чем быстрее, тем лучше! Это очень круто – отправить миллион уведомлений за несколько минут, а потом рассказывать об этом на конференциях, не правда ли?

 

Тут нужно учитывать, что при получении уведомления это устройство пойдет за картинкой – это может быть сюрпризом для хранилища этих картинок (предупредите их). Но уведомление не бывает просто с картинкой, оно обычно откручивает статистику показов (предупредите их тоже). Дальше завертелся ураган событий: пользователь увидел уведомление и нажал, чтобы пойти в приложение. Приложение пошло в бэкенд за новыми данными, бэкенд пошёл куда-то ещё, чтобы персонализировать выдачу (пока остановимся на этом), приложение пошло куда-то ещё, чтобы получить настройки пользователя. Скорость вашей рассылки сыграет здесь злую шутку – чем быстрее ваш очень производительный сервис всё отправит, тем больше одновременной нагрузки создадут мобильные клиенты на всю вашу систему.

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

19. Прогнозируйте неответы реалтаймовых источников

Итак, мы подготовились к нашей рассылке, помогли подготовиться коллегам, чьи сервисы будем использовать в процессе обработки запросов. Выпускаем кракена!

Вы завариваете себе ромашковый чай и начинаете удовлетворённо наблюдать за скоростью рассылки, за графиком растущего на ваш сервис трафика, несущего вам богатство… всё отлично!

Система-то сложная – бэкенд ходит реалтайм в другие бэкенды (назовём их источники). В этот момент становится очень важно уметь различать ситуацию разового неответа источника на запрос от ситуации его полной поломки.

В случае разового неответа повтор запроса (перезапрос) в источник даст нужный результат.

А в случае полной поломки перезапрос может сделать ещё хуже. Например, если у него есть очередь, в которую ваш перезапрос будет заботливо сложен в ожидании обработки. Источник лежит – очередь растёт…

Истинные джентльмены собирают статистику неответов и на основании неё считают вероятность успеха запроса: насколько хорошо отвечает источник в принципе за последний интервал времени. Назовём это "вероятность ответа". На основе этих данных вы можете предположить вероятность его ответа на текущий запрос. Если она мала, то, возможно, не стоит и пытаться.

В этом смысле можно варьировать схемы, но суть не меняется – копите и анализируйте данные.

20. Правильно экспериментируйте с сетью

Современные приложения используют такую базовую сущность, как сеть передачи данных. Если вы, конечно, не делаете какое-то особое приложение, у которого требуется обеспечить сетевую изоляцию – в этом случае вам понадобятся другие советы.

Каналы передачи данных имеют сразу несколько свойств, влияющих на работу вашей системы. Например, скорость передачи данных. В конце концов, она может работать, а может не работать. Частота отказов является таким же свойством вашей сетевой инфраструктуры.

Если вы уже начали проводить испытания стабильности вашей системы, то скорее всего у вас уже есть нагрузочное тестирование, тестирование отключения каких-то компонентов. Следующий важный шаг – это изучение влияние работоспособности сети на работу вашей системы.

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

Чтобы правильно оценить влияние неполадок в сетевой инфраструктуре на вашу систему, нужно проводить испытания разными способами: отключение части сети, замедление скорости передачи данных, “моргание” сети…

Если вы думаете, что облачная инфраструктура полностью ограждает вас от этих проблем, вы ошибаетесь. Она тоже ломается. Проведите испытания своей системы в локальной среде, на работу которой вы можете повлиять. С какой-то вероятностью вам удастся найти места для улучшения, которые уберегут вашу систему от поломки в реальных условиях.

21. Никому не верьте

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

Если вы несёте ответственность за работу действительно важной системы, возьмите себе за правило проверять всю новую информацию, которая к вам поступает, и которая может оказать влияние на надёжность вашей системы. В вопросах надёжности нет места таким явлением, как “мне кажется”, “мне так сказали”, “ну скорее всего это так”… Важны только факты.

И даже то, что я тут пишу, тоже проверяйте.

22. Стандартизируйте процессы

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

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

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

23. Инструкции для «Людочки»

Инструкция для аварийных ситуаций и регламентных работ должна быть такая, чтобы не задействовать мозг человека вообще. Как говорил когда-то один из моих боссов: "Я позвоню нашей Люде и она по твоей инструкции должна суметь это сделать". Люда работала у нас на ресепшене. (Сложно сказать, откуда у неё возьмется доступ в продакшен, но идея отражена верно).

Со временем “я позвоню Люде” заменилось на “представь, что ты на шашлыках в лесу”.

Плохими я называю инструкции, которые:

– допускают неоднозначность трактовок

– содержат слова "если"

– содержат в принципе много слов

– изобилуют терминами

– содержат намёки, типа, это и так очевидно

– … ещё много прочих пунктов

Идеальная инструкция – это набор команд, которые надо скопировать и куда-то вставить, и ссылок, по которым нужно перейти, чтобы открылась конкретная страница.

Кстати, если ваша инструкция достигла этой стадии, пора задуматься о механизации.

24. Не пытайтесь самостоятельно защититься от DDoS и готовьтесь к нему заранее

DDoS рано или поздно приходит ко всему, что заслуживает внимания. Лучше думать про него несколько заранее. Если вы планируете защищаться от DDoS с помощью файлика заблокированных ip – вы не планируете от него защищаться. Если у вас какой-то рейтлимитер, который по User-Agent будет блокировать запросы – вы тоже не планируете защищаться. Это будет работать только в случаях школьных экспериментов, хотя тоже может пригодиться.

Признайте себе, что у вас нет экспертизы, чтобы делать это хорошо, иначе этот вид атак себя давно бы уже исчерпал. DDoS лучше научиться переживать, запасая себе способы деградации, кэши, статику – что угодно, чтобы не позориться перед пользователями в час Х, а также изучить возможности провайдера или облака, аутсорс-решения, которые "по кнопке" начнут фильтровать ваш входящий трафик. Но этот вопрос нужно изучить заранее, чтобы не бегать потом перед Новым Годом в жару продаж, когда ваш чОрный конкурент решил потратить сотню баксов и вывести ваш интернет-магазинчик из строя на пару часов. Так или иначе, если потеря денег в случае отказа превышает затраты на подготовку и применение, то этим стоит заняться. Слово "заранее" было использовано здесь четыре раза.

25. Все обновления базы пробуйте на тестовом стенде

Это кошмар DBA – "Я запустил построение индекса и всё умерло". К чему я веду: если что-то нужно поковырять в базе, то стоит хотя бы восстановить у себя её копию и сделать это сначала на копии. А если копия будет ещё и под синтетической нагрузкой, то ситуация будет более близка к реальности. Возможно, вас ждут сюрпризы, о которых вы пожалели бы в продакшене.

26. Катите фичу отключенной

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

Например, вы выкатили фичу, а она работает не так, как надо. Что делать? Откатить релиз, конечно же. Внезапное исчезновение возможности откатиться, собрать релиз, утерять доступ – может случиться что угодно, приводящее к невозможному исправлению ситуации.

Поэтому: катить выключенной. Включать через какие-то рубильники/конфиги, при включении фичи логировать, что она включилась (иначе вы рискуете не узнать, если вдруг включение не сработало). А для отключения логирования сделать ещё один выключатель. Слишком сложно? Если вы хотите уверенности в своих действиях, придётся это сделать.

27. Исследуйте post-mortem’ы

Если у вас в продакшене произошла какая-то таинственная история, которая "не воспроизводится", приложите достаточно усилий, чтобы разобраться в случившемся. Если вы не понимаете, что именно случилось и не можете этого повторить – это самое худшее развитие событий! Вы не контролируете происходящее и не можете знать, где и когда оно взорвёт ваш продакшен.

Запланируйте потратить на это исследование какое-то разумное количество времени. Нет нужды копаться до истины любой ценой – ситуация может никогда не повториться. Хотя бы убедитесь, что вы приложили достаточно усилий для выявления причины.

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

Потратьте время на предотвращение катастрофы, если она уже начала стучаться в вашу дверь.