Todos os produtos
Search
Central de documentação

Alibaba Cloud Service Mesh:Ative roteamento com reconhecimento de zona

Última atualização: Jun 28, 2026

O tráfego entre zonas aumenta a latência e gera custos adicionais de transferência de dados. O roteamento com reconhecimento de zona mantém as requisições na mesma zona de disponibilidade sempre que há endpoints íntegros, o que reduz ambos os fatores. Quando os endpoints da mesma zona ficam indisponíveis, o tráfego passa automaticamente por failover para a zona mais próxima.

O Service Mesh (ASM) oferece suporte ao roteamento com reconhecimento de zona (também chamado de roteamento intra-zona) por meio do balanceamento de carga de localidade do Istio. Não é necessário alterar o código da aplicação. Este tópico demonstra como ativar o roteamento com reconhecimento de zona para um serviço de exemplo implantado em duas zonas. No exemplo a seguir, um gateway de entrada habilita o acesso a uma aplicação HTTPBin.

Como funciona

Quando um cliente inicia uma requisição para acessar um serviço, o sistema a roteia para o serviço no mesmo nó ou na mesma zona do cliente, com base nas informações de topologia da região e da zona onde o cliente reside. Cada endpoint herda a região, a zona e a subzona de seu nó. Ao ativar o balanceamento de carga de localidade por meio de uma DestinationRule, o proxy sidecar atribui níveis de prioridade aos endpoints:

Prioridade

Significado

0

Mesma zona do chamador (prioridade mais alta)

1

Zona diferente, mesma região

O tráfego é direcionado primeiro aos endpoints de prioridade 0. Se eles se tornarem não íntegros (detectados pela detecção de outliers), o proxy executa failover para o próximo nível de prioridade.

Pré-requisitos

Antes de começar, verifique se você tem:

Etapa 1: Implantar aplicações de exemplo

Este tutorial utiliza duas aplicações:

  • sleep -- um cliente baseado em curl, implantado em cn-hongkong-b

  • helloworld -- o serviço de destino, com v1 em cn-hongkong-b e v2 em cn-hongkong-c

Nota

Substitua cn-hongkong-b e cn-hongkong-c pelas zonas onde residem os nós do seu cluster.

Implantar o cliente sleep

  1. Crie o arquivo sleep.yaml:

    Visualize sleep.yaml

    # Copyright Istio Authors
    #
    #   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.
    
    ##################################################################################################
    # Sleep service
    ##################################################################################################
    apiVersion: v1
    kind: ServiceAccount
    metadata:
      name: sleep
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: sleep
      labels:
        app: sleep
        service: sleep
    spec:
      ports:
      - port: 80
        name: http
      selector:
        app: sleep
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: sleep
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: sleep
      template:
        metadata:
          labels:
            app: sleep
        spec:
          affinity:
            nodeAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
                nodeSelectorTerms:
                - matchExpressions:
                  - key: failure-domain.beta.kubernetes.io/zone
                    operator: In
                    values:
                      - 'cn-hongkong-b'
          terminationGracePeriodSeconds: 0
          serviceAccountName: sleep
          containers:
          - name: sleep
            image: curlimages/curl
            command: ["/bin/sleep", "3650d"]
            imagePullPolicy: IfNotPresent
            volumeMounts:
            - mountPath: /etc/sleep/tls
              name: secret-volume
          volumes:
          - name: secret-volume
            secret:
              secretName: sleep-secret
              optional: true
  2. Aplique o manifesto:

    kubectl apply -f sleep.yaml

Implantar o serviço helloworld

  1. Crie o arquivo helloworld.yaml:

    Visualize helloworld.yaml

    apiVersion: v1
    kind: Service
    metadata:
      name: helloworld
      labels:
        app: helloworld
        service: helloworld
    spec:
      ports:
      - port: 5000
        name: http
      selector:
        app: helloworld
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: helloworld-v1
      labels:
        app: helloworld
        version: v1
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: helloworld
          version: v1
      template:
        metadata:
          labels:
            app: helloworld
            version: v1
        spec:
          affinity:
            nodeAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
                nodeSelectorTerms:
                - matchExpressions:
                  - key: failure-domain.beta.kubernetes.io/zone
                    operator: In
                    values:
                      - 'cn-hongkong-b'
          containers:
          - name: helloworld
            image: docker.io/istio/examples-helloworld-v1
            resources:
              requests:
                cpu: "100m"
            imagePullPolicy: IfNotPresent
            ports:
            - containerPort: 5000
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: helloworld-v2
      labels:
        app: helloworld
        version: v2
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: helloworld
          version: v2
      template:
        metadata:
          labels:
            app: helloworld
            version: v2
        spec:
          affinity:
            nodeAffinity:
              requiredDuringSchedulingIgnoredDuringExecution:
                nodeSelectorTerms:
                - matchExpressions:
                  - key: failure-domain.beta.kubernetes.io/zone
                    operator: In
                    values:
                      - 'cn-hongkong-c'
          containers:
          - name: helloworld
            image: docker.io/istio/examples-helloworld-v2
            resources:
              requests:
                cpu: "100m"
            imagePullPolicy: IfNotPresent
            ports:
            - containerPort: 5000
  2. Aplique o manifesto:

    kubectl apply -f helloworld.yaml

Verificar o registro de endpoints

Consulte as informações de cluster do Envoy no pod sleep para confirmar se ambos os endpoints helloworld estão registrados com metadados de zona:

kubectl exec "$(kubectl get pod -l app=sleep -o jsonpath='{.items[0].metadata.name}')" \
  -c sleep -- curl -s localhost:15000/clusters | grep helloworld

Na saída, procure pelos campos zone e priority. Antes de ativar o roteamento com reconhecimento de zona, ambos os endpoints compartilham a mesma prioridade (priority::0):

outbound|5000||helloworld.default.svc.cluster.local::172.28.32.49:5000::zone::cn-hongkong-b
outbound|5000||helloworld.default.svc.cluster.local::172.28.32.49:5000::priority::0
...
outbound|5000||helloworld.default.svc.cluster.local::172.28.33.155:5000::zone::cn-hongkong-c
outbound|5000||helloworld.default.svc.cluster.local::172.28.33.155:5000::priority::0

Prioridades iguais indicam que o proxy distribui o tráfego entre ambos os endpoints sem preferência de zona.

Etapa 2: Ativar o roteamento com reconhecimento de zona com uma DestinationRule

Crie uma DestinationRule que ative o balanceamento de carga de localidade e configure a detecção de outliers para o serviço helloworld. A detecção de outliers é obrigatória para o failover; sem ela, o proxy não consegue detectar endpoints não íntegros nem redirecionar o tráfego para outra zona.

  1. Crie o arquivo helloworld-failover.yaml. Campos principais:

    Campo

    Finalidade

    localityLbSetting.enabled

    Ativa o roteamento com reconhecimento de zona

    outlierDetection

    Detecta endpoints não íntegros e aciona o failover para a próxima zona

    consecutive5xxErrors: 1

    Remove um endpoint após um único erro 5xx (agressivo, apenas para demonstração)

    baseEjectionTime: 1m

    Mantém os endpoints removidos fora de serviço por 1 minuto

    interval: 1s

    Verifica a integridade do endpoint a cada segundo

    maxRequestsPerConnection: 1

    Força uma nova conexão por requisição (apenas para demonstração)

    apiVersion: networking.istio.io/v1beta1
    kind: DestinationRule
    metadata:
      name: helloworld-failover
      namespace: default
    spec:
      host: helloworld.default.svc.cluster.local
      trafficPolicy:
        connectionPool:
          http:
            maxRequestsPerConnection: 1
        loadBalancer:
          localityLbSetting:
            enabled: true
          simple: ROUND_ROBIN
        outlierDetection:
          baseEjectionTime: 1m
          consecutive5xxErrors: 1
          interval: 1s
  2. Aplique a DestinationRule:

    kubectl apply -f helloworld-failover.yaml
  3. Verifique se as prioridades dos endpoints foram alteradas. O endpoint da mesma zona (cn-hongkong-b) agora tem priority::0, e o endpoint entre zonas (cn-hongkong-c) tem priority::1. Prioridades diferentes confirmam que o roteamento com reconhecimento de zona está ativo. O proxy envia todo o tráfego primeiro para o endpoint de prioridade 0 (mesma zona).

    kubectl exec "$(kubectl get pod -l app=sleep -o jsonpath='{.items[0].metadata.name}')" \
      -c sleep -- curl -s localhost:15000/clusters | grep helloworld
    outbound|5000||helloworld.default.svc.cluster.local::172.28.32.49:5000::zone::cn-hongkong-b
    outbound|5000||helloworld.default.svc.cluster.local::172.28.32.49:5000::priority::0
    ...
    outbound|5000||helloworld.default.svc.cluster.local::172.28.33.155:5000::zone::cn-hongkong-c
    outbound|5000||helloworld.default.svc.cluster.local::172.28.33.155:5000::priority::1

Etapa 3: Verificar o comportamento de roteamento

Com o roteamento com reconhecimento de zona ativado, todas as requisições do pod sleep (cn-hongkong-b) são roteadas para o helloworld-v1 na mesma zona. As etapas a seguir confirmam esse comportamento e testam o failover quando o endpoint da mesma zona fica indisponível.

Confirme o roteamento na mesma zona

Execute o comando a seguir várias vezes:

kubectl exec -c sleep \
  "$(kubectl get pod -l app=sleep -o jsonpath='{.items[0].metadata.name}')" \
  -- curl -sSL helloworld:5000/hello

Saída esperada:

Hello version: v1, instance: helloworld-v1-6f88967849-sq2h2

Todas as respostas vêm da v1 (o endpoint da mesma zona em cn-hongkong-b).

Testar o failover entre zonas

  1. Dimensione o helloworld-v1 para zero réplicas para simular uma interrupção em cn-hongkong-b:

    kubectl scale deploy helloworld-v1 --replicas=0
  2. Aguarde alguns segundos e envie requisições novamente. Saída esperada: O tráfego agora é roteado para a v2 em cn-hongkong-c, o que confirma que o failover entre zonas funciona quando os endpoints da mesma zona estão indisponíveis.

    kubectl exec -c sleep \
      "$(kubectl get pod -l app=sleep -o jsonpath='{.items[0].metadata.name}')" \
      -- curl -sSL helloworld:5000/hello
    Hello version: v2, instance: helloworld-v2-75db5f978d-s7v4k

Restaurar o endpoint da mesma zona

  1. Dimensione o helloworld-v1 de volta para uma réplica:

    kubectl scale deploy helloworld-v1 --replicas=1
  2. Aguarde alguns segundos e verifique se o tráfego retorna para a v1. Saída esperada: O tráfego volta a ser roteado para o endpoint da mesma zona após a recuperação.

    kubectl exec -c sleep \
      "$(kubectl get pod -l app=sleep -o jsonpath='{.items[0].metadata.name}')" \
      -- curl -sSL helloworld:5000/hello
    Hello version: v1, instance: helloworld-v1-6f88967849-sq2h2