SRE для legacy-систем: как работать с тем, что уже есть¶
Представьте, что вам поручили отреставрировать старинный особняк XIX века. У него осыпается фасад, перекошены оконные рамы, а проводка помнит ещё царскую Россию. Вы не можете просто снести его и построить на его месте стеклянный небоскрёб — это памятник, его нужно сохранить, и живут в нём люди прямо сейчас. Ваша задача — сделать его безопасным и пригодным для жизни, не ломая стен. Примерно так же выглядит работа с legacy-системой: вы не переписываете её с нуля — вы учитесь с ней жить и постепенно приводить в порядок.
Реальность: legacy есть у всех¶
Если вы работаете в IT больше пары недель, вы уже знаете: компании, где всё написано на современном стеке, микросервисы на Kubernetes, а код покрыт тестами — не существует. За любым блестящим фасадом скрывается гора легаси, которая держит на себе основной бизнес-процесс. И это нормально.
Самый опасный миф в SRE — «мы перепишем всё на микросервисах, и тогда займёмся надёжностью». Big-bang переписывание (когда вы год пишете новую систему, а потом одним релизом заменяете старую) почти всегда проваливается: требования меняются, бизнес не ждёт, команда выгорает. Google, Amazon и другие гиганты давно поняли: legacy не враг, а данность. К ней нужно применять SRE не когда-нибудь потом, а именно сейчас.
Важно
SRE — это не про стек технологий, а про подход. Процессы, SLO и автоматизация работают одинаково и на современном Go-сервисе, и на COBOL-программе 1985 года.
С чего начать: три простых шага¶
С legacy не нужно начинать с «давайте внедрим observability на уровне распределённых трейсов с OpenTelemetry». Это сломает и систему, и команду. Достаточно трёх вещей:
-
Observability. Добавьте хотя бы базовые метрики: сколько запросов приходит, сколько из них с ошибками, какое время ответа. Это не требует переписывания — часто можно поднять агент на уровне ОС или reverse-proxy. Логи уже есть — начните централизованно собирать их в одном месте. Подробнее про метрики, логи и трейсы — в главе «Телеметрия». Не делайте идеально, сделайте работающе.
-
SLO. Не нужно ставить 99,99%. Для legacy-системы даже SLO в 99% — это уже гигантский шаг вперёд. Зафиксируйте текущее состояние системы и договоритесь с бизнесом: «сейчас наш сервис доступен примерно 95% времени, давайте поставим цель 97% и будем к ней двигаться». Как формулировать SLO — в главе «SLO».
-
Error budget. Как только у вас появился SLO, автоматически появляется бюджет ошибок. Вы начнёте видеть, сколько «недоступности» система уже потребила за месяц. Это знание само по себе меняет решения: если бюджет почти исчерпан, можно осознанно остановить релизы. Как это работает — в главе «Error Budget».
Вытесняем, а не заменяем: паттерн «Strangler Fig»¶
В природе есть интересное растение — фикус-душитель. Он не убивает дерево-хозяин мгновенно. Он сначала оплетает его корнями, питается его соками, постепенно укореняется в земле, и только когда его собственная структура становится достаточно крепкой — дерево-хозяин отмирает.
В работе с legacy это называется Strangler Fig pattern. Вы не переписываете всю систему целиком. Вы берёте один маленький кусочек функциональности (скажем, «страницу входа пользователя») и реализуете его в новом сервисе. Старый код продолжает работать — вы просто перенаправляете часть трафика на новый сервис через маршрутизатор. Когда новая реализация доказала свою стабильность — вы перенаправляете на неё весь трафик, а старый кусок удаляете. И так — шаг за шагом, кусочек за кусочком.
Обёртка вместо переделки: антихрупкость вокруг legacy¶
Вы не можете (или не хотите) трогать код legacy-системы — у неё нет тестов, страшно чихнуть в его сторону. Но вы можете построить защитный слой вокруг неё, не залезая внутрь. Это называется reliability wrapper (обёртка надёжности) или «sidecar for legacy»:
- Таймауты. Legacy может зависать на минуту. Поставьте перед ней reverse-proxy (например, nginx или Envoy) с таймаутом в 5 секунд. Если система не ответила — пользователь хотя бы не будет ждать вечно.
- Retry (повторные попытки). Legacy иногда падает по случайным причинам. Пусть обёртка автоматически повторяет запрос — пользователь часто даже не заметит сбоя.
- Circuit breaker. Если legacy начала стабильно падать — обёртка перестаёт отправлять к ней запросы на несколько минут, давая ей остыть.
- Rate limiting. Legacy не умеет обрабатывать пиковые нагрузки? Обёртка ограничивает входящий поток, чтобы не положить систему.
Все эти техники реализуются на уровне инфраструктуры, без единого изменения в коде legacy. Подробно про каждый паттерн — в главе «Техники: timeout, retry, circuit breaker, load balancing».
Автоматизация операций: вы не исправите код, но исправите процесс¶
Legacy-системы часто живут за счёт героического ручного труда: «Вася в 3 часа ночи подключается по SSH и перезапускает сервис, когда падает очередь». Это классический toil (ручной труд).
Вы не можете сделать код стабильнее? Отлично. Автоматизируйте его обслуживание. Напишите скрипт, который сам перезапускает сервис при падении. Настройте автоочистку логов, чтобы диск не забивался. Поставьте systemd-юнит или supervisor, который мониторит процесс и перезапускает его при сбое. Сделайте playbook в Ansible для типовых операций. Это не требует доступа к исходному коду, но радикально снижает нагрузку на команду.
Антипаттерн: «legacy слишком хрупкий для SRE»¶
Самое опасное заблуждение звучит так: «Мы не можем добавить мониторинг и SLO к этой системе — она и так еле дышит, лишняя нагрузка её добьёт» или «SRE для нас — это роскошь, мы просто пытаемся не упасть».
На самом деле всё наоборот. Legacy — это система, которая нуждается в SRE больше всех. Если современный микросервис можно перезапустить и он не сломается, то устаревшая база данных восстанавливается сутки вручную. Если ошибка в новом API видна сразу, то ошибка в старом монолите может копиться месяцами, пока не обвалит всё.
Чем более хрупкая система, тем больше ей нужны: - Метрики, чтобы заметить умирание до катастрофы. - SLO, чтобы иметь объективный разговор с бизнесом: «нам нужно три месяца на стабилизацию, и вот вам цифры, почему». - Автоматизация, чтобы убрать человеческий фактор из рутинных операций.
Стратегия внедрения: с чего начать прямо завтра¶
-
Выберите один сервис. Самый проблемный или самый критичный для бизнеса. Не пытайтесь охватить всё сразу.
-
Добавьте один SLO. Даже «99% запросов должны завершаться успешно» — уже цель. Измеряйте её изо дня в день. Когда SLO нарушается — фиксируйте инциденты.
-
Автоматизируйте одну операцию. Посмотрите на список toil (мы говорили про него в главе «Toil: ручной труд»). Возьмите самую частую ручную операцию — и автоматизируйте её. Один скрипт, который экономит инженеру час в день, окупается за неделю.
Когда этот цикл сработал на одном сервисе — переносите опыт на следующий. Распространение SRE на legacy не должно быть революцией. Это эволюция: шаг за шагом, сервис за сервисом, метрика за метрикой.
Итог¶
Legacy не исчезнет никогда. Её нельзя игнорировать. Её нельзя «переписать за год» — бизнес этого не даст. Единственный работающий путь — принять её как есть и постепенно внедрять практики SRE: observability, SLO, error budget, автоматизацию и защитные обёртки.
SRE для legacy — это не про технологии. Это про дисциплину: перестать гадать, начать измерять, перестать делать руками, начать автоматизировать. Особняк XIX века можно сделать безопасным и удобным для жизни. Он не станет небоскрёбом из стекла и стали — но он и не должен.