Поделиться через


Развертывание высокодоступной базы данных PostgreSQL в Службе Azure Kubernetes (AKS)

В этой статье описано, как развернуть высокодоступную базу данных PostgreSQL в AKS.

Это важно

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

Например, репозиторий Ray GitHub описывает несколько платформ, которые зависят от времени отклика, назначения и уровня поддержки.

Корпорация Майкрософт несет ответственность за создание пакетов с открытым кодом, которые мы развертываем в AKS. Эта ответственность включает полное управление процессами сборки, сканирования, подписывания, проверки и исправления ошибок, а также контроль над двоичными файлами в образах контейнеров. Для получения дополнительной информации см. Управление уязвимостями в AKS и Покрытие поддержки AKS.

Создание пароля для пользователя Bootstrap приложения

  1. Создайте секрет для проверки развертывания PostgreSQL с помощью интерактивного входа для пользователя начального приложения, используя команду kubectl create secret.

    PG_DATABASE_APPUSER_SECRET=$(echo -n | openssl rand -base64 16)
    
    kubectl create secret generic db-user-pass \
        --from-literal=username=app \
        --from-literal=password="${PG_DATABASE_APPUSER_SECRET}" \
        --namespace $PG_NAMESPACE \
        --context $AKS_PRIMARY_CLUSTER_NAME
    
  2. Убедитесь, что секрет был успешно создан с помощью kubectl get команды.

    kubectl get secret db-user-pass --namespace $PG_NAMESPACE --context $AKS_PRIMARY_CLUSTER_NAME
    

Установите переменные среды для кластера PostgreSQL

  • Разверните ConfigMap, чтобы задать переменные среды для кластера PostgreSQL с помощью следующей kubectl apply команды:

    cat <<EOF | kubectl apply --context $AKS_PRIMARY_CLUSTER_NAME -n $PG_NAMESPACE -f -
    apiVersion: v1
    kind: ConfigMap
    metadata:
        name: cnpg-controller-manager-config
    data:
        ENABLE_AZURE_PVC_UPDATES: 'true'
    EOF
    

Установка PodMonitors Prometheus

Prometheus создает PodMonitors для экземпляров CNPG с помощью набора правил записи по умолчанию, хранящихся в репозитории примеров GitHub CNPG. В рабочей среде эти правила будут изменены по мере необходимости.

  1. Добавьте репозиторий Prometheus Community Helm с помощью helm repo add команды.

    helm repo add prometheus-community \
        https://prometheus-community.github.io/helm-charts
    
  2. Обновите репозиторий Prometheus Community Helm и установите его в основном кластере с помощью команды helm upgrade с флагом --install.

    helm upgrade --install \
        --namespace $PG_NAMESPACE \
        -f https://raw.githubusercontent.com/cloudnative-pg/cloudnative-pg/main/docs/src/samples/monitoring/kube-stack-config.yaml \
        prometheus-community \
        prometheus-community/kube-prometheus-stack \
        --kube-context=$AKS_PRIMARY_CLUSTER_NAME
    

Создать федеративную учетную запись

В этом разделе вы создаете федеративные учетные данные удостоверения для резервного копирования PostgreSQL, чтобы предоставить CNPG возможность использовать удостоверение рабочей нагрузки AKS для аутентификации в целевой учетной записи хранения для резервных копий. Оператор CNPG создает учетную запись службы Kubernetes с тем же именем, что и кластер, который называется в манифесте развертывания кластера CNPG.

  1. Получите URL-адрес издателя OIDC кластера с помощью az aks show команды.

    export AKS_PRIMARY_CLUSTER_OIDC_ISSUER="$(az aks show \
        --name $AKS_PRIMARY_CLUSTER_NAME \
        --resource-group $RESOURCE_GROUP_NAME \
        --query "oidcIssuerProfile.issuerUrl" \
        --output tsv)"
    
  2. Создайте федеративные учетные данные удостоверения с помощью команды az identity federated-credential create.

    az identity federated-credential create \
        --name $AKS_PRIMARY_CLUSTER_FED_CREDENTIAL_NAME \
        --identity-name $AKS_UAMI_CLUSTER_IDENTITY_NAME \
        --resource-group $RESOURCE_GROUP_NAME \
        --issuer "${AKS_PRIMARY_CLUSTER_OIDC_ISSUER}" \
        --subject system:serviceaccount:"${PG_NAMESPACE}":"${PG_PRIMARY_CLUSTER_NAME}" \
        --audience api://AzureADTokenExchange
    

Развертывание кластера PostgreSQL с высоким уровнем доступности

В этом разделе описано, как развернуть высокодоступный кластер PostgreSQL с помощью настраиваемого определения ресурсов кластера CNPG (CRD).

Параметры CRD кластера

В следующей таблице описаны ключевые свойства, заданные в манифесте развертывания YAML для кластера CRD:

Недвижимость Определение
inheritedMetadata Зависит от оператора CNPG. Метаданные наследуются всеми объектами, связанными с кластером.
annotations: service.beta.kubernetes.io/azure-dns-label-name Метка DNS для использования при предоставлении конечных точек кластера Postgres для чтения и записи, а также только для чтения.
labels: azure.workload.identity/use: "true" Указывает, что AKS должен внедрять зависимости удостоверений рабочей нагрузки в модули pod, в которые размещаются экземпляры кластера PostgreSQL.
topologySpreadConstraints Требуются разные зоны и узлы с меткой "workload=postgres".
resources Настраивает класс Quality of Service (QoS) гарантированный. В рабочей среде эти значения являются ключевыми для максимизации использования базовой виртуальной машины узла и зависят от используемого SKU виртуальной машины Azure.
bootstrap Зависит от оператора CNPG. Инициализируется с пустой базой данных приложения.
storage / walStorage Зависит от оператора CNPG. Определяет шаблоны хранилища для службы PersistentVolumeClaims (PVCs) для хранения данных и журналов. Кроме того, можно указать хранилище для табличных пространств, чтобы разбить их на сегменты для увеличения операций ввода-вывода в секунду (IOPS).
replicationSlots Зависит от оператора CNPG. Включает слоты репликации для обеспечения высокой доступности.
postgresql Зависит от оператора CNPG. Сопоставляет параметры для postgresql.conf, pg_hba.confи pg_ident.conf config.
serviceAccountTemplate Содержит шаблон, необходимый для создания учетных записей службы и сопоставляет учетные данные федеративного удостоверения AKS с UAMI, чтобы включить проверку подлинности удостоверения рабочей нагрузки AKS из модулей pod, на которых размещены экземпляры PostgreSQL, с внешними ресурсами Azure.
barmanObjectStore Зависит от оператора CNPG. Настраивает набор инструментов barman-cloud с помощью идентификации рабочей нагрузки AKS для аутентификации в хранилище объектов Azure Blob.

Параметры производительности PostgreSQL

Производительность PostgreSQL значительно зависит от базовых ресурсов кластера. В следующей таблице приведены некоторые рекомендации по вычислению ключевых параметров для высокой производительности:

Недвижимость Рекомендуемое значение Определение
wal_compression lz4 Сжимает полностраничные записи в WAL-файле с указанным методом.
max_wal_size 6 ГБ Задает размер WAL, который активирует контрольную точку
checkpoint_timeout 15 мин Задает максимальное время между автоматическими контрольными точками WAL
checkpoint_flush_after 2 МБ Количество страниц, после которых ранее выполненные операции записи сбрасываются на диск
wal_writer_flush_after 2 МБ Объем данных, записанных WAL-писателем, который запускает очистку.
min_wal_size 4 ГБ Задает минимальный размер для сжатия WAL до
shared_buffers 25% памяти узла Задает количество буферов общей памяти, используемых сервером
effective_cache_size 75% памяти узла Задает предположение планировщика об общем размере кэшей данных
work_mem 1/256-й объем памяти узла Задает максимальный объем памяти, используемый для рабочих областей запросов
maintenance_work_mem 6.25% памяти узла Задает максимальный объем памяти, используемый для операций обслуживания
autovacuum_vacuum_cost_limit 2400 Объем затрат вакуума, доступный перед перерывом, для автовакуума
random_page_cost 1.1 Задает оценку планировщика стоимости не последовательно извлекаемой страницы диска.
effective_io_concurrency 64 Количество одновременных запросов, которые можно эффективно обрабатывать подсистемой диска
maintenance_io_concurrency 64 Вариант "effective_io_concurrency", используемый для обслуживания

Развертывание PostgreSQL

  1. Разверните кластер PostgreSQL с помощью Cluster CRD, используя команду kubectl apply.

    cat <<EOF | kubectl apply --context $AKS_PRIMARY_CLUSTER_NAME -n $PG_NAMESPACE -v 9 -f -
    apiVersion: postgresql.cnpg.io/v1
    kind: Cluster
    metadata:
      name: $PG_PRIMARY_CLUSTER_NAME
    spec:
      inheritedMetadata:
        annotations:
          service.beta.kubernetes.io/azure-dns-label-name: $AKS_PRIMARY_CLUSTER_PG_DNSPREFIX
        labels:
          azure.workload.identity/use: "true"
    
      instances: 3
      startDelay: 30
      stopDelay: 30
      minSyncReplicas: 1
      maxSyncReplicas: 1
      replicationSlots:
        highAvailability:
          enabled: true
        updateInterval: 30
    
      topologySpreadConstraints:
      - maxSkew: 1
        topologyKey: topology.kubernetes.io/zone
        whenUnsatisfiable: DoNotSchedule
        labelSelector:
          matchLabels:
            cnpg.io/cluster: $PG_PRIMARY_CLUSTER_NAME
    
      affinity:
        nodeSelector:
          workload: postgres
    
      resources:
        requests:
          memory: '8Gi'
          cpu: 2
        limits:
          memory: '8Gi'
          cpu: 2
    
      bootstrap:
        initdb:
          database: appdb
          owner: app
          secret:
            name: db-user-pass
          dataChecksums: true
    
      storage:
        size: 32Gi
        pvcTemplate:
          accessModes:
            - ReadWriteOnce
          resources:
            requests:
              storage: 32Gi
          storageClassName: $POSTGRES_STORAGE_CLASS
    
      walStorage:
        size: 32Gi
        pvcTemplate:
          accessModes:
            - ReadWriteOnce
          resources:
            requests:
              storage: 32Gi
          storageClassName: $POSTGRES_STORAGE_CLASS
    
      monitoring:
        enablePodMonitor: true
    
      postgresql:
        parameters:
          wal_compression: lz4
          max_wal_size: 6GB
          checkpoint_timeout: 15min
          checkpoint_flush_after: 2MB
          wal_writer_flush_after: 2MB
          min_wal_size: 4GB
          shared_buffers: 4GB
          effective_cache_size: 12GB
          work_mem: 62MB
          maintenance_work_mem: 1GB
          autovacuum_vacuum_cost_limit: "2400"
          random_page_cost: "1.1"
          effective_io_concurrency: "64"
          maintenance_io_concurrency: "64"
        pg_hba:
          - host all all all scram-sha-256
    
      serviceAccountTemplate:
        metadata:
          annotations:
            azure.workload.identity/client-id: "$AKS_UAMI_WORKLOAD_CLIENTID"
          labels:
            azure.workload.identity/use: "true"
    
      backup:
        barmanObjectStore:
          destinationPath: "https://${PG_PRIMARY_STORAGE_ACCOUNT_NAME}.blob.core.windows.net/backups"
          azureCredentials:
            inheritFromAzureAD: true
        retentionPolicy: '7d'
    EOF
    
  1. Убедитесь, что основной кластер PostgreSQL успешно создан с помощью kubectl get команды. CrD кластера CNPG указал три экземпляра, которые можно проверить, просматривая модули pod после создания и объединения каждого экземпляра для репликации. Будьте терпеливы, так как может занять некоторое время, чтобы все три экземпляра стали доступными и присоединились к кластеру.

    kubectl get pods --context $AKS_PRIMARY_CLUSTER_NAME --namespace $PG_NAMESPACE -l cnpg.io/cluster=$PG_PRIMARY_CLUSTER_NAME
    

    Пример результата

    NAME                         READY   STATUS    RESTARTS   AGE
    pg-primary-cnpg-r8c7unrw-1   1/1     Running   0          4m25s
    pg-primary-cnpg-r8c7unrw-2   1/1     Running   0          3m33s
    pg-primary-cnpg-r8c7unrw-3   1/1     Running   0          2m49s
    

Это важно

Если вы используете локальную NVMe с хранилищем контейнеров Azure, и модуль pod зависает в состоянии инициализации с ошибкой с несколькими подключениями, скорее всего, он все еще ищет том на потерянном узле. Как только pod начинает работать, он переходит в CrashLoopBackOff состояние, так как новая реплика была создана на новом узле без данных, и CNPG не может найти каталог pgdata. Чтобы устранить эту проблему, необходимо уничтожить затронутый экземпляр и создать новый экземпляр. Выполните следующую команду:

kubectl cnpg destroy [cnpg-cluster-name] [instance-number]  

Убедитесь, что PodMonitor Prometheus работает

Оператор CNPG автоматически создает PodMonitor для основного экземпляра с помощью правил записи, созданных во время установки Сообщества Prometheus.

  1. Убедитесь, что podMonitor выполняется с помощью kubectl get команды.

    kubectl --namespace $PG_NAMESPACE \
        --context $AKS_PRIMARY_CLUSTER_NAME \
        get podmonitors.monitoring.coreos.com \
        $PG_PRIMARY_CLUSTER_NAME \
        --output yaml
    

    Пример результата

     kind: PodMonitor
     metadata:
      annotations:
        cnpg.io/operatorVersion: 1.23.1
    ...
    

Если вы используете Azure Monitor для Managed Prometheus, необходимо добавить еще один монитор Pod с помощью пользовательского имени группы. Управляемый Prometheus не интегрирует пользовательские определения ресурсов (CRD) из сообщества Prometheus. За исключением названия группы, CRD совпадают. Это позволяет мониторам pod для управляемой системы Prometheus существовать наряду с мониторами pod сообщества. Если вы не используете Управляемый Prometheus, можно пропустить это. Создайте новый монитор pod:

cat <<EOF | kubectl apply --context $AKS_PRIMARY_CLUSTER_NAME --namespace $PG_NAMESPACE -f -
apiVersion: azmonitoring.coreos.com/v1
kind: PodMonitor
metadata:
  name: cnpg-cluster-metrics-managed-prometheus
  namespace: ${PG_NAMESPACE}
  labels:
    azure.workload.identity/use: "true"
    cnpg.io/cluster: ${PG_PRIMARY_CLUSTER_NAME}
spec:
  selector:
    matchLabels:
      azure.workload.identity/use: "true"
      cnpg.io/cluster: ${PG_PRIMARY_CLUSTER_NAME}
  podMetricsEndpoints:
    - port: metrics
EOF

Убедитесь, что монитор pod создан (обратите внимание на разницу в имени группы).

kubectl --namespace $PG_NAMESPACE \
    --context $AKS_PRIMARY_CLUSTER_NAME \
    get podmonitors.azmonitoring.coreos.com \
    -l cnpg.io/cluster=$PG_PRIMARY_CLUSTER_NAME \
    -o yaml

Вариант A - Рабочая область Azure Monitor

После развертывания кластера Postgres и монитора pod можно просмотреть метрики с помощью портала Azure в рабочей области Azure Monitor.

Снимок экрана: метрики кластера Postgres в рабочей области Azure Monitor на портале Azure.

Вариант B — управляемый сервис Grafana

Кроме того, после развертывания кластера Postgres и мониторов pod можно создать панель мониторинга метрик на экземпляре Управляемой Grafana, созданном скриптом развертывания, чтобы визуализировать метрики, экспортированные в рабочую область Azure Monitor. Вы можете получить доступ к Managed Grafana через портал Azure. Перейдите к управляемому экземпляру Grafana, созданному скриптом развертывания, и выберите ссылку "Конечная точка", как показано ниже:

Снимок экрана: метрики кластера Postgres в экземпляре Управляемой Grafana Azure на портале Azure.

При выборе ссылки "Конечная точка" откроется новое окно браузера, в котором можно создать панели мониторинга в Managed Grafana. Следуя инструкциям по настройке источника данных Azure Monitor, вы можете добавить визуализации для создания панели мониторинга метрик из кластера Postgres. После настройки подключения к источнику данных в главном меню выберите параметр "Источники данных". Вы увидите набор параметров источника данных для подключения к источнику данных, как показано ниже.

Снимок экрана: параметры источника данных Azure Monitor на портале Azure.

В параметре Managed Prometheus выберите параметр для создания панели мониторинга, чтобы открыть редактор панели мониторинга. После открытия окна редактора выберите параметр "Добавить визуализацию", а затем выберите параметр Managed Prometheus, чтобы просмотреть метрики из кластера Postgres. После выбора метрики, которую вы хотите визуализировать, нажмите кнопку "Выполнить запросы", чтобы получить данные для визуализации, как показано ниже:

Снимок экрана: панель мониторинга Managed Prometheus с метриками кластера Postgres.

Щелкните значок "Сохранить", чтобы добавить панель на панель мониторинга. Вы можете добавить другие панели, нажав кнопку "Добавить" в редакторе панели мониторинга и повторив этот процесс, чтобы визуализировать другие метрики. При добавлении визуализаций метрик, вы должны получить что-то, что выглядит так:

Снимок экрана: сохраненная панель мониторинга Managed Prometheus на портале Azure.

Щелкните значок "Сохранить", чтобы сохранить панель мониторинга.


Дальнейшие шаги

Соавторы

Корпорация Майкрософт поддерживает эту статью. Первоначальная версия была написана следующими участниками:

  • Кен Килти | Ведущий TPM
  • Рассел де Пина | Главный технический менеджер программ
  • Адриан Джоан | Старший инженер клиента
  • Дженни Хейс | Старший разработчик содержимого
  • Кэрол Смит | Старший разработчик содержимого
  • Эрин Шаффер | Разработчик содержимого 2
  • Адам Шариф | Инженер клиента 2