Установка и настройка для Яндекс.Облака#

В этом разделе описана установка и настройка ANIC в качестве Ingress для Яндекс.Облака.

Настройка локальной рабочей среды для работы с Kubernetes и Яндекс.Облаком#

Необходимые инструменты:

  • Helm для управления пакетами Kubernetes;

  • kubectl для управления кластерами Kubernetes;

  • Docker для работы с контейнерами.

Пример для Ubuntu 24/04.

  1. Скачайте и установите CLI (YC) для управления ресурсами в Яндекс.Облаке:

    $ curl -sSL https://storage.yandexcloud.net/yandexcloud-yc/install.sh | bash
    $ yc init
    

    Запустится процесс настройки CLI, где потребуется ввести токен для доступа в Яндекс.Облако. Токен можно получить по ссылке https://oauth.yandex.ru/verification_code.

  2. Добавьте параметры подключения к Kubernetes-кластеру (например, otus) в файл ~/.kube/config и подключитесь к кластеру:

    $ yc managed-kubernetes cluster get-credentials otus --external
    
  3. Проверьте конфигурацию кластера, ноды и доступные сервисы:

    $ kubectl config view
    $ kubectl get nodes
    $ kubectl get svc
    

Получение доступа к образу ANIC#

  1. Создайте Docker-секрет.

    Выполните авторизацию в Docker Registry, чтобы получить доступ к образу:

    $ docker login -u=<login> -p=<password> anic.docker.angie.software
    

    После успешной авторизации информация о доступе будет сохранена в файле ~/.docker/config.json.

  2. Создайте секрет для Kubernetes, используя файл Docker-конфигурации:

    $ kubectl create secret generic regcred \
          --from-file=.dockerconfigjson=$HOME/.docker/config.json \
          --type=kubernetes.io/dockerconfigjson
    

    Секрет regcred будет использоваться для доступа к приватным образам в Kubernetes.

Получение и настройка Helm-чартов#

  1. Склонируйте Helm-чарты из репозитория:

    $ git clone https://git.angie.software/web-server/anic-helm-charts.git
    $ cd anic-helm-charts/anic/
    
  2. Отредактируйте values.yaml. Укажите имя созданного секрета для доступа к образам и включите поддержку менеджера сертификатов:

    ...
    imagePullSecretName: "regcred"
    ...
    enableCertManager: true
    ...
    
  3. Соберите и установите чарт:

    $ helm install anic .
    
  4. Обновите чарт:

    $ helm upgrade anic .
    

Запуск менеджера сертификатов#

  1. Установите cert-manager для управления сертификатами. Работа тестировалась на примере версии 1.12.1:

    $ kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.12.1/cert-manager.yaml
    
  2. Убедитесь, что три пода cert-manager находятся в состоянии running с готовностью 1/1:

    $ kubectl get pods -n cert-manager --watch
    
  3. Создайте объект ClusterIssuer для выпуска сертификатов:

    http01-clusterissuer.yaml
    apiVersion: cert-manager.io/v1
    kind: ClusterIssuer
    metadata:
      name: http01-clusterissuer
    spec:
      acme:
        server: https://acme-v02.api.letsencrypt.org/directory
        email: test@test.ru
        privateKeySecretRef:
          name: http01-clusterissuer-secret
        solvers:
        - http01:
            ingress:
              class: angie
    

    В этом примере cert-manager настроен для автоматической выдачи сертификатов от Let’s Encrypt с помощью HTTP-01 проверки.

  4. Примените манифест для объекта ClusterIssuer:

    $ kubectl apply -f http01-clusterissuer.yaml
    

После выполнения всех шагов, у вас будет настроен доступ к образу ANIC, чарт развернут в Kubernetes, а cert-manager будет управлять сертификатами.

Развертывание ANIC и тестового приложения в Kubernetes#

  1. Настройте домен и поиск внешнего IP-адреса. Создайте Ingress-ресурс, сервис и деплоймент для тестового приложения.

    Замените доменное имя otus-kube.mtdlb.ru на ваш действующий домен. Внешний IP-адрес кластера можно найти в Яндекс.Облаке в разделе Managed Service for KubernetesКластерыotusСеть. Этот IP-адрес будет использоваться для привязки домена.

    app-angie.yaml
    apiVersion: networking.k8s.io/v1
    kind: Ingress
    metadata:
      name: minimal-ingress
      annotations:
        cert-manager.io/cluster-issuer: "http01-clusterissuer"
        acme.cert-manager.io/http01-edit-in-place: "true"
    spec:
      ingressClassName: angie
      tls:
        - hosts:
          - otus-kube.mtdlb.ru
          secretName: domain-name-secret
      rules:
        - host: otus-kube.mtdlb.ru
          http:
            paths:
            - path: /
              pathType: Prefix
              backend:
                service:
                  name: app
                  port:
                    number: 80
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: app
    spec:
      selector:
        app: app
      ports:
        - protocol: TCP
          port: 80
          targetPort: 80
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: app-deployment
      labels:
        app: app
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: app
      template:
        metadata:
          labels:
            app: app
        spec:
          containers:
          - name: app
            image: angie:latest
            ports:
            - containerPort: 80
    
  2. Запустите приложение:

    $ kubectl apply -f app-angie.yaml
    
  3. Проверьте статус SSL-сертификата и его секрет в Kubernetes:

    $ kubectl describe certificate domain-name-secret
    $ kubectl describe secret domain-name-secret
    

Проверка работы#

Откройте в браузере домен, который вы указали в конфигурации (например, https://otus-kube.mtdlb.ru).

Если возникают проблемы, можно проверить логи подов:

$ kubectl logs -l app=app

Также можно посмотреть конфигурацию ANIC (подставьте в anic-64ff957589-jlg7s имя пода с ANIC в вашем кластере):

$ kubectl exec anic-64ff957589-jlg7s -- angie -T

Удаление развернутого приложения#

Если нужно удалить все созданные ресурсы, выполните:

$ kubectl delete -f app-angie.yaml

Проксирование TCP-трафика через ANIC в Kubernetes#

Ниже приведен пример настройки проксирования TCP-трафика для доступа к MySQL.

Предварительно необходимо включить globalConfiguration в values.yaml чарта, за счет него можно определить listener.

  1. Установите чарт с выключенным параметром globalConfiguration:

    globalConfiguration:
      ## Creates the GlobalConfiguration custom resource. Requires controller.enableCustomResources.
      create: false
    
  2. Выполните команду:

    $ helm upgrade anic .
    
  3. Теперь установите чарт с включенным параметром globalConfiguration и добавьте TCP-прослушиватель:

    globalConfiguration:
      ## Creates the GlobalConfiguration custom resource. Requires controller.enableCustomResources.
      create: true
    
      ## The spec of the GlobalConfiguration for defining the global configuration parameters of the Ingress Controller.
      spec:
        listeners:
        # - name: dns-udp
        #   port: 5353
        #   protocol: UDP
        - name: mysql-tcp
          port: 13306
          protocol: TCP
    
  4. Обновите чарт:

    $ helm upgrade anic .
    

    Теперь ANIC будет слушать TCP-порт 13306 для подключения к MySQL.

  5. Создайте секрет с паролем root:

    mysql-seceret.yaml
    apiVersion: v1
     kind: Secret
     metadata:
       name: mysql-secret
     type: kubernetes.io/basic-auth
     stringData:
       password: kljJ218q23cujvdshi
    
  6. Создайте постоянное хранилище (volume) для MySQL:

    mysql-storage.yaml
    apiVersion: v1
    kind: PersistentVolume
    metadata:
      name: mysql-pv-volume
      labels:
        type: local
    spec:
      storageClassName: manual
      capacity:
        storage: 10Gi
      accessModes:
        - ReadWriteOnce
      hostPath:
        path: "/mnt/data"
    ---
    apiVersion: v1
    kind: PersistentVolumeClaim
    metadata:
      name: mysql-pv-claim
    spec:
      storageClassName: manual
      accessModes:
        - ReadWriteOnce
      resources:
        requests:
          storage: 10Gi
    
  7. Разверните сам MySQL:

    mysql-deployment.yaml
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: mysql
    spec:
      selector:
        matchLabels:
          app: mysql
      strategy:
        type: Recreate
      template:
        metadata:
          labels:
            app: mysql
        spec:
          containers:
          - image: mysql:8.0
            name: mysql
            env:
            - name: MYSQL_ROOT_PASSWORD
              valueFrom:
                secretKeyRef:
                  name: mysql-secret
                  key: password
            ports:
            - containerPort: 3306
              name: mysql
            volumeMounts:
            - name: mysql-persistent-storage
              mountPath: /var/lib/mysql
          volumes:
          - name: mysql-persistent-storage
            persistentVolumeClaim:
              claimName: mysql-pv-claim
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: mysql
    spec:
      ports:
      - port: 3306
      selector:
        app: mysql
    
  8. Создайте сервис для MySQL:

    mysql-service.yaml
    apiVersion: v1
    kind: Service
    metadata:
      name: mysql-ext
    spec:
      type: LoadBalancer
      ports:
      - port: 13306
        name: mysql
        targetPort: 13306
      # Kubernetes-метки селектора, использованные в шаблоне подов при создании объекта Deployment.
      selector:
        app: mysql-tcp
    
  9. Настройте ANIC для MySQL:

    anic-mysql.yaml
    apiVersion: k8s.angie.software/v1alpha1
    kind: TransportServer
    metadata:
      name: mysql-tcp
    spec:
      listener:
        name: mysql-tcp
        protocol: TCP
      upstreams:
      - name: mysql
        service: mysql
        port: 3306
      action:
        pass: mysql
    
  10. Примените настройки, чтобы развернуть сервис:

    $ kubectl apply -f mysql-secret.yaml
    $ kubectl apply -f mysql-storage.yaml
    $ kubectl apply -f mysql-deployment.yaml
    $ kubectl apply -f mysql-service.yaml
    $ kubectl apply -f anic-mysql.yaml
    

    Теперь трафик на порт 13306 будет перенаправляться в MySQL.

  11. Проверьте статус:

    $ kubectl get svc           # Список сервисов
    $ kubectl describe gc       # Описание GlobalConfiguration
    $ kubectl describe ts mysql-tcp   # Описание TCP-listener
    $ kubectl describe service anic  # Информация об ANIC