Execute cargas de trabalho de pilha completa em grande escala no GKE

Este tutorial mostra como executar uma aplicação Web suportada por uma base de dados relacional de alta disponibilidade em grande escala no Google Kubernetes Engine (GKE).

A aplicação de exemplo usada neste tutorial é o Bank of Anthos, uma aplicação Web baseada em HTTP que simula a rede de processamento de pagamentos de um banco. O Bank of Anthos usa vários serviços para funcionar. Este tutorial centra-se no frontend do Website e nas bases de dados relacionais PostgreSQL que suportam os serviços do Bank of Anthos. Para saber mais sobre o Bank of Anthos, incluindo a respetiva arquitetura e os serviços que implementa, consulte o Bank of Anthos no GitHub.

Prepare o ambiente

  1. Clone o repositório de exemplo usado neste tutorial:

    git clone https://github.com/GoogleCloudPlatform/bank-of-anthos.git
    cd bank-of-anthos/
    
  2. Defina variáveis de ambiente:

    PROJECT_ID=PROJECT_ID
    GSA_NAME=bank-of-anthos
    GSA_EMAIL=bank-of-anthos@${PROJECT_ID}.iam.gserviceaccount.com
    KSA_NAME=default
    

    Substitua PROJECT_ID pelo ID do seu Google Cloud projeto.

Configure o cluster e as contas de serviço

  1. Crie um cluster:

    gcloud container clusters create-auto bank-of-anthos --location=us-central1
    

    O cluster pode demorar até cinco minutos a ser iniciado.

  2. Crie uma conta de serviço do IAM:

    gcloud iam service-accounts create bank-of-anthos
    
  3. Conceda acesso à conta de serviço do IAM:

    gcloud projects add-iam-policy-binding PROJECT_ID \
      --role roles/cloudtrace.agent \
      --member "serviceAccount:bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com"
    gcloud projects add-iam-policy-binding PROJECT_ID \
      --role roles/monitoring.metricWriter \
      --member "serviceAccount:bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com"
    gcloud iam service-accounts add-iam-policy-binding "bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com" \
      --role roles/iam.workloadIdentityUser \
      --member "serviceAccount:PROJECT_ID.svc.id.goog[default/default]"
    

    Este passo concede o seguinte acesso:

    • roles/cloudtrace.agent: escreva dados de rastreio, como informações de latência, no rastreio.
    • roles/monitoring.metricWriter: escrever métricas no Cloud Monitoring.
    • roles/iam.workloadIdentityUser: Permitir que uma conta de serviço do Kubernetes use a federação de identidades da carga de trabalho para o GKE para atuar como a conta de serviço do IAM.
  4. Configure a conta de serviço do Kubernetes no espaço de nomes default para atuar como a conta de serviço da IAM que criou:default

    kubectl annotate serviceaccount default \
        iam.gke.io/gcp-service-account=bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com
    

    Isto permite que os pods que usam a conta de serviço do Kubernetes no espaço de nomes defaultdefault acedam aos mesmos recursos que a conta de serviço da IAM. Google Cloud

Implemente o Bank of Anthos e o PostgreSQL

Nesta secção, instala o Bank of Anthos e uma base de dados PostgreSQL no modo de alta disponibilidade (HA), que lhe permite dimensionar automaticamente as réplicas do servidor da base de dados. Se quiser ver os scripts, o gráfico Helm e os manifestos do Kubernetes usados nesta secção, consulte o repositório do Bank of Anthos no GitHub.

  1. Implemente o esquema da base de dados e um script de linguagem de definição de dados (LDD):

    kubectl create configmap initdb \
        --from-file=src/accounts/accounts-db/initdb/0-accounts-schema.sql \
        --from-file=src/accounts/accounts-db/initdb/1-load-testdata.sql \
        --from-file=src/ledger/ledger-db/initdb/0_init_tables.sql \
        --from-file=src/ledger/ledger-db/initdb/1_create_transactions.sh
    
  2. Instale o PostgreSQL através do gráfico Helm de exemplo:

    helm repo add bitnami https://charts.bitnami.com/bitnami
    helm install accounts-db bitnami/postgresql-ha \
        --version 10.0.1 \
        --values extras/postgres-hpa/helm-postgres-ha/values.yaml \
        --set="postgresql.initdbScriptsCM=initdb" \
        --set="postgresql.replicaCount=1" \
        --wait
    

    Este comando cria um cluster do PostgreSQL com uma contagem de réplicas inicial de 1. Mais adiante neste tutorial, vai dimensionar o cluster com base nas ligações recebidas. Esta operação pode demorar dez minutos ou mais a ser concluída.

  3. Implemente o Bank of Anthos:

    kubectl apply -f extras/jwt/jwt-secret.yaml
    kubectl apply -f extras/postgres-hpa/kubernetes-manifests
    

    Esta operação pode demorar alguns minutos a ser concluída.

Ponto de verificação: valide a configuração

  1. Verifique se todos os pods do Bank of Anthos estão em execução:

    kubectl get pods
    

    O resultado é semelhante ao seguinte:

    NAME                                  READY   STATUS
    accounts-db-pgpool-57ffc9d685-c7xs8   3/3     Running
    accounts-db-postgresql-0              1/1     Running
    balancereader-57b59769f8-xvp5k        1/1     Running
    contacts-54f59bb669-mgsqc             1/1     Running
    frontend-6f7fdc5b65-h48rs             1/1     Running
    ledgerwriter-cd74db4cd-jdqql          1/1     Running
    pgpool-operator-5f678457cd-cwbhs      1/1     Running
    transactionhistory-5b9b56b5c6-sz9qz   1/1     Running
    userservice-f45b46b49-fj7vm           1/1     Running
    
  2. Verifique se consegue aceder ao frontend do Website:

    1. Obtenha o endereço IP externo do serviço frontend:

      kubectl get ingress frontend
      

      O resultado é semelhante ao seguinte:

      NAME       CLASS    HOSTS   ADDRESS         PORTS   AGE
      frontend   <none>   *       203.0.113.9     80      12m
      
    2. Num navegador, aceda ao endereço IP externo. É apresentada a página de início de sessão do Bank of Anthos. Se tiver curiosidade, explore a aplicação.

      Se receber um erro 404, aguarde alguns minutos para que os microsserviços sejam aprovisionados e tente novamente.

Aumente/diminua automaticamente a escala da app Web e da base de dados PostgreSQL

O GKE Autopilot cria uma escala automática dos recursos de computação do cluster com base no número de cargas de trabalho no cluster. Para dimensionar automaticamente o número de pods no cluster com base nas métricas de recursos, tem de implementar a escala automática horizontal de pods do Kubernetes. Pode usar as métricas de CPU e memória do Kubernetes incorporadas ou usar métricas personalizadas, como pedidos HTTP por segundo ou a quantidade de declarações SELECT, retiradas do Cloud Monitoring.

Nesta secção, faz o seguinte:

  1. Configure a escala automática horizontal de pods para os microsserviços do Bank of Anthos usando métricas incorporadas e métricas personalizadas.
  2. Simule o carregamento na aplicação Bank of Anthos para acionar eventos de escalabilidade automática.
  3. Observe como o número de pods e os nós no seu cluster são automaticamente dimensionados para cima e para baixo em resposta à sua carga.

Configure a recolha de métricas personalizadas

Para ler métricas personalizadas da monitorização, tem de implementar o adaptador Custom Metrics - Stackdriver Adapter no seu cluster.

  1. Implemente o adaptador:

    kubectl apply -f https://raw.githubusercontent.com/GoogleCloudPlatform/k8s-stackdriver/master/custom-metrics-stackdriver-adapter/deploy/production/adapter.yaml
    
  2. Configure o adaptador para usar a Workload Identity Federation para o GKE para obter métricas:

    1. Configure a conta de serviço IAM:

      gcloud projects add-iam-policy-binding PROJECT_ID \
          --member "serviceAccount:bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com" \
          --role roles/monitoring.viewer
      gcloud iam service-accounts add-iam-policy-binding bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com \
          --role roles/iam.workloadIdentityUser \
          --member "serviceAccount:PROJECT_ID.svc.id.goog[custom-metrics/custom-metrics-stackdriver-adapter]"
      
    2. Anotar a conta de serviço do Kubernetes que o adaptador usa:

      kubectl annotate serviceaccount custom-metrics-stackdriver-adapter \
          --namespace=custom-metrics \
        iam.gke.io/gcp-service-account=bank-of-anthos@PROJECT_ID.iam.gserviceaccount.com
      
    3. Reinicie a implementação do adaptador para propagar as alterações:

      kubectl rollout restart deployment custom-metrics-stackdriver-adapter \
          --namespace=custom-metrics
      

Configure o dimensionamento automático para a base de dados

Quando implementou o Bank of Anthos e o PostgreSQL anteriormente neste tutorial, implementou a base de dados como um StatefulSet com uma réplica de leitura/gravação principal para processar todas as declarações SQL recebidas. Nesta secção, vai configurar o escalamento automático de pods horizontal para adicionar novas réplicas de leitura em espera para processar as declarações SELECT recebidas. Uma boa forma de reduzir a carga em cada réplica é distribuir declarações SELECT, que são operações de leitura. A implementação do PostgreSQL inclui uma ferramenta denominada Pgpool-II que alcança este equilíbrio de carga e melhora o débito do sistema.

O PostgreSQL exporta a métrica da declaração SELECT como uma métrica do Prometheus. Vai usar um exportador de métricas simples denominado prometheus-to-sd para enviar estas métricas para o Cloud Monitoring num formato suportado.

  1. Reveja o objeto HorizontalPodAutoscaler:

    # Copyright 2022 Google LLC
    #
    # Licensed under the Apache License, Version 2.0 (the "License");
    # you may not use this file except in compliance with the License.
    # You may obtain a copy of the License at
    #
    #      http://www.apache.org/licenses/LICENSE-2.0
    #
    # Unless required by applicable law or agreed to in writing, software
    # distributed under the License is distributed on an "AS IS" BASIS,
    # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    # See the License for the specific language governing permissions and
    # limitations under the License.
    
    ---
    apiVersion: autoscaling/v2
    kind: HorizontalPodAutoscaler
    metadata:
      name: accounts-db-postgresql
    spec:
      behavior:
        scaleUp:
          stabilizationWindowSeconds: 0
          policies:
          - type: Percent
            value: 100
            periodSeconds: 5
          selectPolicy: Max
      scaleTargetRef:
        apiVersion: apps/v1
        kind: StatefulSet
        name: accounts-db-postgresql
      minReplicas: 1
      maxReplicas: 5
      metrics:
      - type: External
        external:
          metric:
            name: custom.googleapis.com|mypgpool|pgpool2_pool_backend_stats_select_cnt
          target:
              type: AverageValue
              averageValue: "15"
    

    Este manifesto faz o seguinte:

    • Define o número máximo de réplicas durante um aumento para 5.
    • Define o número mínimo de durante uma redução para 1.
    • Usa uma métrica externa para tomar decisões de escalabilidade. Neste exemplo, a métrica é o número de declarações SELECT. Ocorre um evento de expansão se o número de declarações SELECT recebidas exceder 15.
  2. Aplique o manifesto ao cluster:

    kubectl apply -f extras/postgres-hpa/hpa/postgresql-hpa.yaml
    

Configure o ajuste de escala automático para a interface Web

Em Implemente o Bank of Anthos e o PostgreSQL, implementou a interface Web do Bank of Anthos. Quando o número de utilizadores aumenta, o userservice serviço consome mais recursos da CPU. Nesta secção, vai configurar o escalamento automático horizontal de pods para a implementação userservice quando os pods existentes usarem mais de 60% da respetiva CPU pedida e para a implementação frontend quando o número de pedidos HTTP recebidos para o equilibrador de carga for superior a 5 por segundo.

Configure o dimensionamento automático para a implementação do userservice

  1. Reveja o manifesto HorizontalPodAutoscaler para a userservice Implementação:

    # Copyright 2022 Google LLC
    #
    # Licensed under the Apache License, Version 2.0 (the "License");
    # you may not use this file except in compliance with the License.
    # You may obtain a copy of the License at
    #
    #      http://www.apache.org/licenses/LICENSE-2.0
    #
    # Unless required by applicable law or agreed to in writing, software
    # distributed under the License is distributed on an "AS IS" BASIS,
    # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    # See the License for the specific language governing permissions and
    # limitations under the License.
    
    ---
    apiVersion: autoscaling/v2
    kind: HorizontalPodAutoscaler
    metadata:
      name: userservice
    spec:
      behavior:
        scaleUp:
          stabilizationWindowSeconds: 0
          policies:
            - type: Percent
              value: 100
              periodSeconds: 5
          selectPolicy: Max
      scaleTargetRef:
        apiVersion: apps/v1
        kind: Deployment
        name: userservice
      minReplicas: 5
      maxReplicas: 50
      metrics:
        - type: Resource
          resource:
            name: cpu
            target:
              type: Utilization
              averageUtilization: 60
    

    Este manifesto faz o seguinte:

    • Define o número máximo de réplicas durante um aumento para 50.
    • Define o número mínimo de durante uma redução para 5.
    • Usa uma métrica do Kubernetes integrada para tomar decisões de escalabilidade. Neste exemplo, a métrica é a utilização da CPU e a utilização alvo é de 60%, o que evita a utilização excessiva e insuficiente.
  2. Aplique o manifesto ao cluster:

    kubectl apply -f extras/postgres-hpa/hpa/userservice.yaml
    

Configure o dimensionamento automático para a implementação de front-end

  1. Reveja o manifesto HorizontalPodAutoscaler para a userservice Implementação:

    # Copyright 2022 Google LLC
    #
    # Licensed under the Apache License, Version 2.0 (the "License");
    # you may not use this file except in compliance with the License.
    # You may obtain a copy of the License at
    #
    #      http://www.apache.org/licenses/LICENSE-2.0
    #
    # Unless required by applicable law or agreed to in writing, software
    # distributed under the License is distributed on an "AS IS" BASIS,
    # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    # See the License for the specific language governing permissions and
    # limitations under the License.
    
    ---
    apiVersion: autoscaling/v2
    kind: HorizontalPodAutoscaler
    metadata:
      name: frontend
    spec:
      behavior:
        scaleUp:
          stabilizationWindowSeconds: 0
          policies:
            - type: Percent
              value: 100
              periodSeconds: 5
          selectPolicy: Max
      scaleTargetRef:
        apiVersion: apps/v1
        kind: Deployment
        name: frontend
      minReplicas: 5
      maxReplicas: 25
      metrics:
        - type: External
          external:
            metric:
              name: loadbalancing.googleapis.com|https|request_count
              selector:
                matchLabels:
                  resource.labels.forwarding_rule_name: FORWARDING_RULE_NAME
            target:
              type: AverageValue
              averageValue: "5"
    

    Este manifesto usa os seguintes campos:

    • spec.scaleTargetRef: o recurso do Kubernetes a dimensionar.
    • spec.minReplicas: o número mínimo de réplicas, que é 5 neste exemplo.
    • spec.maxReplicas: o número máximo de réplicas, que é 25 neste exemplo.
    • spec.metrics.*: a métrica a usar. Neste exemplo, este é o número de pedidos HTTP por segundo, que é uma métrica personalizada do Cloud Monitoring fornecida pelo adaptador que implementou.
    • spec.metrics.external.metric.selector.matchLabels: A etiqueta de recurso específica a filtrar quando a escala automática.
  2. Encontre o nome da regra de encaminhamento do equilibrador de carga para a frontend implementação:

    export FW_RULE=$(kubectl get ingress frontend -o=jsonpath='{.metadata.annotations.ingress\.kubernetes\.io/forwarding-rule}')
    echo $FW_RULE
    

    O resultado é semelhante ao seguinte:

    k8s2-fr-j76hrtv4-default-frontend-wvvf7381
    
  3. Adicione a regra de encaminhamento ao manifesto:

    sed -i "s/FORWARDING_RULE_NAME/$FW_RULE/g" "extras/postgres-hpa/hpa/frontend.yaml"
    

    Este comando substitui FORWARDING_RULE_NAME pela regra de encaminhamento guardada.

  4. Aplique o manifesto ao cluster:

    kubectl apply -f extras/postgres-hpa/hpa/frontend.yaml
    

Ponto de verificação: valide a configuração do dimensionamento automático

Obtenha o estado dos seus recursos HorizontalPodAutoscaler:

kubectl get hpa

O resultado é semelhante ao seguinte:

NAME                     REFERENCE                            TARGETS             MINPODS   MAXPODS   REPLICAS   AGE
accounts-db-postgresql   StatefulSet/accounts-db-postgresql   10905m/15 (avg)     1         5         2          5m2s
contacts                 Deployment/contacts                  1%/70%              1         5         1          11m
frontend                 Deployment/frontend                  <unknown>/5 (avg)   5         25        1          34s
userservice              Deployment/userservice               0%/60%              5         50        5          4m56s

Neste momento, configurou a sua aplicação e o dimensionamento automático. Agora, o front-end e a base de dados podem ser dimensionados com base nas métricas que forneceu.

Simule a carga e observe o dimensionamento do GKE

O Bank of Anthos inclui um loadgenerator serviço que lhe permite simular tráfego para testar o escalamento da sua aplicação sob carga. Nesta secção, vai implementar o serviço loadgenerator, gerar uma carga e observar o escalamento resultante.

Implemente o gerador de testes de carga

  1. Crie uma variável de ambiente com o endereço IP do balanceador de carga do Bank of Anthos:

    export LB_IP=$(kubectl get ingress frontend -o=jsonpath='{.status.loadBalancer.ingress[0].ip}')
    echo $LB_IP
    

    O resultado é semelhante ao seguinte:

    203.0.113.9
    
  2. Adicione o endereço IP do balanceador de carga ao manifesto:

    sed -i "s/FRONTEND_IP_ADDRESS/$LB_IP/g" "extras/postgres-hpa/loadgenerator.yaml"
    
  3. Aplique o manifesto ao cluster:

    kubectl apply -f  extras/postgres-hpa/loadgenerator.yaml
    

O gerador de carga começa a adicionar um utilizador por segundo, até um máximo de 250 utilizadores.

Simule o carregamento

Nesta secção, usa um gerador de carga para simular picos no tráfego e observar o aumento do número de réplicas e do número de nós para acomodar o aumento da carga ao longo do tempo. Em seguida, termina o teste e observa a redução da escala da réplica e da contagem de nós em resposta.

  1. Exponha a interface Web do gerador de carga localmente:

    kubectl port-forward svc/loadgenerator 8080
    

    Se vir uma mensagem de erro, tente novamente quando o Pod estiver em funcionamento.

  2. Num navegador, abra a interface Web do gerador de carga.

    • Se estiver a usar uma shell local, abra um navegador e aceda a http://127.0.0.1:8080.
    • Se estiver a usar o Cloud Shell, clique em Pré-visualização Web e, de seguida, clique em Pré-visualizar na porta 8080.
  3. Clique no separador Gráficos para observar o desempenho ao longo do tempo.

  4. Abra uma nova janela de terminal e monitorize a contagem de réplicas dos escaladores automáticos de pods horizontais:

    kubectl get hpa -w
    

    O número de réplicas aumenta à medida que a carga aumenta. O aumento da escala pode demorar cerca de dez minutos.

    NAME                     REFERENCE                            TARGETS          MINPODS   MAXPODS   REPLICAS
    accounts-db-postgresql   StatefulSet/accounts-db-postgresql   8326m/15 (avg)   1         5         5
    contacts                 Deployment/contacts                  51%/70%          1         5         2
    frontend                 Deployment/frontend                  5200m/5 (avg)    5         25        13
    userservice              Deployment/userservice               71%/60%          5         50        17
    
  5. Abra outra janela de terminal e verifique o número de nós no cluster:

    gcloud container clusters list \
        --filter='name=bank-of-anthos' \
        --format='table(name, currentMasterVersion, currentNodeVersion, currentNodeCount)' \
        --location="us-central1"
    
  6. O número de nós aumentou da quantidade inicial de três nós para acomodar as novas réplicas.

  7. Abra a interface do gerador de carga e clique em Parar para terminar o teste.

  8. Verifique novamente a quantidade de réplicas e a quantidade de nós e observe à medida que os números diminuem com a carga reduzida. A redução pode demorar algum tempo, uma vez que o período de estabilização predefinido para réplicas no recurso HorizontalPodAutoscaler do Kubernetes é de cinco minutos. Para mais informações, consulte o artigo Intervalo de estabilização.