Релиз nxs-anomaly: отечественная альтернатива Grafana OnCall для управления дежурствами, маршрутизации оповещений и эскалации инцидентов. Доступен на GitHub
Все статьи

Интеграция защищённого контура в Yandex Cloud

Разбираем кейс построения закрытого контура разработки в Yandex Cloud

Время чтения
9 минут
Раздел
Статьи
Интеграция защищённого контура в Yandex Cloud

О заказчике

Всем привет! НИКСИС на связи.

В этой статье разберём кейс построения закрытого контура разработки в Yandex Cloud.

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

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

Поэтому было принято решение создать production-контур в отечественном облаке.

Что требовалось

Одновременно необходимо было сохранить изоляцию инфраструктуры и предоставить разработчикам возможность создавать и запускать сервисы в Yandex Cloud.

При полностью закрытом контуре возникают несколько проблем:

  • По окончании настройки весь доступ к внешнему миру (и интернету, конечно) будет отключён, что усложняет администрирование: обновления будут проходить через согласование с ИБ.
  • Закрытые контуры требуют больших инвестиций в разработку и дальнейшую поддержку, так как все компоненты должны быть реализованы внутри компании.
  • Могут возникнуть проблемы при интеграции новых технологий или продуктов от других поставщиков. В дальнейшем это может осложнить масштабирование и расширение бизнеса.

Исходные требования были следующими:

  • настроить соединение между облаком и сетью Заказчика;
  • завязать всю авторизацию на LDAP.

После нескольких брейнштормов и рабочих созвонов пришли к следующему решению:

  • Создать IPsec-туннель между Yandex Cloud и UserGate по протоколу IKEv2.
  • Использовать LDAP и Keycloak для авторизации, где это возможно.
  • С помощью Terraform-модулей из репозитория nxs-marketplace-terraform автоматизировать развёртывание инфраструктуры.

Сама инфраструктура должна была состоять из:

  • StrongSwan;
  • Kubernetes;
  • GitLab;
  • Vault by HashiCorp;
  • Keycloak;
  • и ряда других компонентов.

Настраиваем StrongSwan site-to-site IKEv2 IPsec tunnel

Для начала разберёмся, что такое IPsec-туннель.

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

Если сравнивать, например, с OpenVPN, который работает на уровне пользователя, то IPsec, работающий на уровне ядра системы, позволяет повысить скорость и производительность.

Для туннеля был выбран протокол IKEv2. IKEv1, созданный ещё в 1990-х годах, на сегодняшний день считается устаревшим вариантом протокола.

В качестве метода шифрования выбрали PSK (Pre-Shared Key).

Перед проектной командой стоял выбор между PSK и сертификатами. В итоге остановились на PSK по нескольким причинам.

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

Во-вторых, контур закрытый, и информация о нём доступна только определённому кругу сотрудников.

Сначала необходимо было построить туннель между Yandex Cloud и закрытым контуром Заказчика.

Всё выглядело достаточно просто. Но, как это обычно бывает с инфраструктурными проектами, возникла проблема.

В последней на тот момент версии прошивки UserGate был обнаружен баг.

При создании IPsec-туннеля UserGate создавал множественные соединения, которые разрывались по тайм-ауту. Проблема была подтверждена разработчиком, а версия ПО отправлена на доработку.

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

В итоге была реализована связка:

StrongSwan (виртуальная машина в Yandex Cloud) → StrongSwan (виртуальная машина за UserGate в инфраструктуре Заказчика).

Основные этапы настройки:

  1. 1. Устанавливаем StrongSwan.

  2. 2. Конфигурим /etc/ipsec.conf:

config setup
        charondebug="all" 
        uniqueids=yes
        strictcrlpolicy=no

conn connection
        authby=secret
        left=10.12.0.21
        leftid=84.0.0.1
        leftsubnet=10.12.0.0/24,10.13.0.0/24
        right=202.0.0.3
        rightid=%any
        rightsubnet=10.1.1.0/24,10.1.4.0/24
        ike=aes256-sha256-modp2048,aes256-sha256-modp1024,aes256-sha1-modp2048,aes256-sha1-modp1024!
        esp=aes256-sha256,aes256-sha1!
        keyingtries=3
        ikelifetime=1h
        lifetime=8h
        dpdaction=hold
        auto=start
        type=tunnel
        keyexchange=ikev2

Если коротко, то left — это локальный (local) сервер, а right — удалённый (remote).

Всё, что связано с шифрованием (ike, esp) на обоих хостах должно быть одинаково. Подробности можно найти в официальной документации.


3. Настраиваем /etc/ipsec.secrets:

#source destination 84.0.0.1 202.0.0.3 : PSK "тут какой-то ключ в base64"

Тут важна только строчка с адресами и ключом, source/destination указаны для того, чтобы не запутаться.

4. Настраиваем сеть как описано в этой статье.


  1. 5. Добавляем правила в /etc/ufw/before.rules:

# разрешаем ssh
-A ufw-before-input -p tcp -m tcp --dport 22 -j ACCEPT
-A ufw-before-output -p tcp -m tcp --sport 22 -j ACCEPT

Включаем перенаправление трафика ESP:

-A ufw-before-forward --match policy --pol ipsec --dir in --proto esp -s 10.12.0.0/24 -j ACCEPT
-A ufw-before-forward --match policy --pol ipsec --dir out --proto esp -d 10.12.0.0/24 -j ACCEPT

# разрешаем forwarding 
-A ufw-before-forward -s 10.1.1.0/24 -d 10.12.0.0/24 -i eth0 -m policy --dir in --pol ipsec --reqid 1 --proto esp -j ACCEPT
-A ufw-before-forward -s 10.12.0.0/24 -d 10.1.1.0/24 -o eth0 -m policy --dir out --pol ipsec --reqid 1 --proto esp -j ACCEPT

-A ufw-before-forward -s 10.1.4.0/24 -d 10.12.0.0/24 -i eth0 -m policy --dir in --pol ipsec --reqid 1 --proto esp -j ACCEPT
-A ufw-before-forward -s 10.12.0.0/24 -d 10.1.4.0/24 -o eth0 -m policy --dir out --pol ipsec --reqid 1 --proto esp -j ACCEPT


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

Дополнительная информация с примерами есть на официальном сайте.


  1. 6. Создаём статические маршруты до сетей назначения.

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




Настраиваем инфраструктуру

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

Порядок настройки не является обязательным. Однако выбранная последовательность позволяет сократить время реализации проекта.

Большинство решений принималось с учётом дальнейшей эксплуатации: инфраструктура должна была быть понятной и удобной для администраторов, которым предстояло её поддерживать.

1. VPN

«Зачем? Ведь уже есть IPsec-туннель», — может возникнуть вопрос.

VPN необходим для удобного доступа сотрудников и внешних подрядчиков к инфраструктуре.

Для этой задачи был выбран Pritunl VPN.

Преимущества:

  • простота первичной настройки;
  • начало работы сразу после установки;
  • простое добавление сущностей;
  • удобное создание новых пользователей.

2. GitLab

GitLab был развёрнут в Docker Compose.

Основная причина — удобство сопровождения:

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

После развёртывания и настройки GitLab каждый следующий шаг описывается с помощью IaC.

CI/CD настраивается для всего, что возможно автоматизировать, чтобы клиент мог создавать инфраструктуру и сервисы с минимальным количеством ручных действий.

При этом каждый проект должен содержать README с подробным описанием сервиса.

3. Кластер Kubernetes

Следующий компонент — Kubernetes.

Решение — Managed Kubernetes от Yandex Cloud.

Во-первых, бюджеты проекта позволяли использовать managed-решение.

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

В-третьих, у команды Nixys есть Terraform-модуль, с помощью которого кластер можно быстро развернуть.

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

Terraform-модуль доступен в репозитории nxs-marketplace-terraform.

4. Кластер Vault

Бэкендом будет выступать Consul.

Почему именно Vault? Всем сервисам необходимы сертификаты.

Поэтому следующим шагом становится деплой и настройка cert-manager в связке с Vault.

5. Cert-manager

Сert-manager запускается в кластере Kubernetes.

Для быстрого получения сертификатов из Vault настраивается ClusterIssuer.

Для наших целей манифест выглядит следующим образом:

apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
 name: vault-issuer
spec:
 vault:
   auth:
     kubernetes:
       mountPath: /v1/auth/kubernetes
       role: clusterissuer
       secretRef:
         key: token
         name: issuer-token-lmzpj
   path: pki/sign/example
   server: http://vault.example.com


Это немного отличается от примера из инструкции, поэтому требуются небольшие корректировки:

  • имя роли указывается в соответствии с используемой конфигурацией. В данном случае —clusterissuer;
  • path — pki/sign/example, расположение сертификатов в Vault.

Чтобы Ingress стали защищёнными, в их манифесты добавляется аннотация с именем ClusterIssuer:

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
 name: example-name
 namespace: example
 labels:
   app: example
 annotations:
   cert-manager.io/cluster-issuer: vault-issuer
   meta.helm.sh/release-name: example-name
   meta.helm.sh/release-namespace: example
spec:
 ingressClassName: nginx
 rules:
   - host: example.example.com
     http:
       paths:
         - path: /
           pathType: ImplementationSpecific
           backend:
             service:
               name: example
               port:
                 number: 8080

После настройки сертификатов во все Ingress добавляется соответствующая аннотация:

annotations:
  cert-manager.io/cluster-issuer: vault-issuer

6. Keycloak

Изначально планировалось построить авторизацию на базе связки Keycloak + LDAP, но в процессе выяснилось, что вместо LDAP уже настроен ADFS.

Поэтому было принято решение использовать существующую инфраструктуру.

Требовалась единая точка авторизации в AD через связку Keycloak ↔ ADFS.

В итоге SSO было настроено на базе SAML 2.0.

SSO

Single Sign-On упрощает работу пользователей: после одной авторизации они получают доступ к сервисам, подключённым к Keycloak, пока действует пользовательская сессия.

Пользователи создаются в Active Directory, после чего для авторизации в системе используются корпоративные учётные данные.

SAML

Если говорить упрощённо, SAML — стандарт обмена информацией о безопасности между различными системами.

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

После настройки Keycloak авторизация настраивается для сервисов, которые были развёрнуты ранее:

  • GitLab;
  • Vault;
  • Grafana;
  • Kibana.

Подробно останавливаться на настройке Keycloak не будем, иначе статья превратится в галерею скриншотов.

Со стороны Keycloak настраивается Identity Provider согласно официальной инструкции.

После этого настраиваются Clients для каждого сервиса, кроме Kibana.

Для Kibana используется oauth2-proxy. Информация по его настройке и конфигурации приведена в этой статье.

Остальные сервисы настраиваются через SAML согласно официальной документации.

Результат

В результате заказчик получил полностью закрытый контур для разработки в Yandex Cloud с защищённым соединением с корпоративной инфраструктурой.

В инфраструктуре используются StrongSwan, Kubernetes, GitLab, Vault, Consul, cert-manager, Keycloak, ADFS и другие компоненты.

При этом значительная часть инфраструктуры описана через IaC, а сервисы подключены к CI/CD. Для пользователей реализована единая точка авторизации через Keycloak и ADFS, а управление сертификатами автоматизировано с помощью Vault и cert-manager.

Отдельно стоит отметить проблему с UserGate: из-за бага в используемой версии прошивки первоначальную схему подключения пришлось изменить и добавить StrongSwan с обеих сторон.

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

Спасибо за внимание!

Оставьте заявку, чтобы обсудить проект

Ваши контакты
О вашем проекте

Нажав на кнопку, соглашаюсь на обработку персональных данных, Ознакомлен со всеми документами, размещенными на сайте

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