Резервирование резервирования. Как я наш интернет труба шатал

Syn-Ack Хабр! Меня зовут Сергей Минаев, я руководитель направления администрирования веб-сервисов в компании «Спортмастер».

В преддверии наступающего Нового года хочется, чтобы было спокойно и тихо, можно было кушать оливье, спокойно отдыхать, а не вот это вот все: пожар, караул, SRE взбунтовались! Говорят, резервирование — ненастоящее!

da823ok0jr46s78eetzldrshsqa.jpeg

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

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

Какая у нас задача и какая проблематика


izkzslfznnihkgyyigvq9swuyf4.jpeg

Из всего списка рассмотренных нами проблем выбивается баг прошивки пограничных коммутаторов.

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

И если Split-Brain или локальные проблемы (например, залипание ARP) наши сетевые администраторы решают просто подняв бровь, то при недоступности всей площадки нужно думать как-то иначе.

Видел чудеса техники, но такого!


7k3racw9eopydk4tikbwyv0btyc.jpeg

С этапом постановки проблематики и цели мы закончили, теперь переходим ко второму этапу — осмотримся. ИТ-инфраструктура у нас построено достаточно канонична, с соблюдением бест-практисов и «здравого смысла»:

  • Две площадки или еще одна маленькая площадочка
  • Разные каналы от разных провайдеров
  • SDN
  • Дублирующее оборудование


Для доступа из интернета мы используем балансировщики. Это несколько парных кластеров серверов, которые располагаются на разных площадках, подключены в разные коммутаторы по LACP, внешняя сеть растянута между площадками, IP резервируются по VRRP (keepalived).
Вполне себе джентльменский набор техник, а не простое «авось». Но, возвращаясь к опыту: на Деда Мороза надейся, а сам не плошай.

А какие вообще варианты? Огласите весь список, пожалуйста


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

  • Несколько площадок с резервированием «уровня инфраструктуры»
  • Резервирование на уровне ПО


С первого взгляда, никакого rocket science нет: делаем несколько независимых точек присутствия, репликация данных, независимая обработка данных и глобальная блокировка.

auk9plpq2f8rocmcauce_gfnz1e.jpeg

Чтобы сделать несколько точек присутствия, для начала нужно как-то направить к ним трафик клиентов. Если делать «глобальный» балансировщик — он тоже может стать недоступным. Значит, нужно переходить немного вбок и на другой уровень.

Самое простое, что приходит в голову — эта балансировка на уровне DNS. Никаких особых настроек она не требует, добавляй только адреса и дополнительные DNS серверы на разных площадках.

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

Но, не все так просто, как кажется… — закон Мерфи.

Что мы делаем? Тестируем!


image-loader.svg

Мы собрали небольшой локальный тестовый стенд в корпоративной сети, этого вполне достаточно, технология-то нетребовательная. Стенд — два сервера с Nginx, да настройка двух IP-адресов на одно имя, TTL занижен. Все готово, приступаем.

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

curl -v 'https://dnsrr.test.local'
* Trying 5.6.7.300:443...
* connect to 5.6.7.300 port 443 failed: Время ожидания соединения истекло
* Trying 1.2.3.256:443...
* Connected to dnsrr.test.local (1.2.3.256) port 443 (#0)
* ALPN, offering h2
* ALPN, offering http/1.1
* CAfile: /etc/ssl/certs/ca-certificates.crt
* CApath: none

Ну, какое-то переключение есть. Вот только тайм-аут по умолчанию — 1 минута. Можно его, конечно, скрутить вниз, но ведь никто не будет менять параметры у себя. Но давайте ради эксперимента все же попробуем:

curl --connect-timeout 2 -vs 'https://dnsrr.test.local' -o /dev/null
* Trying 5.6.7.300:443...
* After 998ms connect time, move on!
* connect to 5.6.7.300 port 443 failed: Время ожидания соединения истекло
* Trying 1.2.3.256:443...
* Connected to dnsrr.test.local (1.2.3.256) port 443 (#0)
* ALPN, offering h2

Ну, в принципе, оно работает, пускай и в очень лабораторных условиях. А вот Postman отказался воспринимать DNS RR. Хорошо, попробуем подключиться «реальными приложениями» — Chrome, Firefox. Все становится несколько интереснее:

  • Если один из балансировщиков полностью недоступен, Chrome требуется около 15 секунд на переключение, Firefox — около 5
  • Если на одном из серверов не отвечает порт 80/443, оба браузера переключаются за 2–3 секунды


На мобильных устройствах Safari и Chrome (Android) могут «залипнуть» на достаточно продолжительно время, вплоть до 20–30 секунд. Клиенты в приложениях мы не тестировали, предполагаем, что нам придется дописывать логику для резолва всех IP из записей и обработку доступности-недоступности балансировщиков.

Сыровато, но хоть какой-то результат.

Вместо заключения


DNS Round Robin используется большинством интернет-гигантов, так что она, конечно же, имеет право на жизнь. Скорее всего, мы чего-то не учитываем.
Из плюсов технологии: можно делать две технически независимые точки для подключения, есть шанс, что падение одной точки не заденет другую.
Без минусов никуда: веса настроить нельзя, распределение клиентов как повезет
Опосля всех рассуждений и мысленных экспериментов, подкрепленных натурными проверками, мы остановились на следующем:

  1. Все новое — хорошо забытое старое, чем проще — тем лучше, минус на минус дает плюс. DNS-балансировке быть, хотя бы в продолжительном пилотном режиме.
  2. Чтобы не настроить подпорок и улучшить доступность, вторую точку входа (балансировщик) мы будем размещать в облаке
  3. На начальном этапе — пропускаем трафик на наши площадки, если они не отвечают — отдаем заглушку < — Мы где-то здесь
  4. Доработка наших систем для работы без доступности всех макро- и микросервисов. Например, можно показывать каталог товаров, но отключать корзину.
  5. Доработка наших систем для работы в распределенном режиме: синхронизации, блокировки и весь остальной набор головной боли. Это поможет нам балансировать трафик и направлять на «локальную» площадку относительно пользователя. В идеале — балансировка на удаленную, если локальная недоступна.

© Habrahabr.ru