Compartilhar via


Implementação de failover do lado do cliente na Grade de Eventos do Azure

A recuperação de desastre geralmente envolve a criação de um recurso de backup para evitar interrupções quando uma região se torna não íntegra. Durante esse processo, uma região primária e secundária de recursos da Grade de Eventos do Azure será necessária na carga de trabalho.

Há diferentes maneiras de se recuperar de uma perda grave de funcionalidade do aplicativo. Neste artigo, descreveremos a lista de verificação que você precisará seguir para preparar seu cliente para se recuperar de uma falha devido a uma região ou um recurso não íntegro.

A Grade de Eventos dá suporte à GeoDR (recuperação de desastre geográfico) manual e automática no lado do servidor. Você ainda poderá implementar a lógica de recuperação de desastre do lado do cliente se quiser um controle maior sobre o processo de failover. Para obter detalhes sobre GeoDR automático, veja Recuperação de desastre geográfico do lado do servidor na Grade de Eventos do Azure.

A tabela a seguir ilustra o failover do lado do cliente e o suporte à recuperação de desastre geográfico na Grade de Eventos.

Recurso da Grade de Eventos Suporte a failover do lado do cliente Suporte à GeoDR (recuperação de desastre geográfico)
Tópicos personalizados Com suporte Entre áreas geográficas/regional
Tópicos do sistema Sem suporte Habilitado automaticamente
Domínios Com suporte Entre áreas geográficas/regional
Namespaces de parceiro Com suporte Sem suporte
Namespaces Com suporte Sem suporte

Considerações sobre o failover do lado do cliente

  1. Crie e configure seu recurso primário da Grade de Eventos.
  2. Crie e configure seu recurso secundário da Grade de Eventos.
  3. Tenha em mente que ambos os recursos devem ter a mesma configuração, sub-recursos e funcionalidades habilitados.
  4. Os recursos da Grade de Eventos precisam ser hospedados em regiões diferentes.
  5. Se o recurso da Grade de Eventos tiver recursos dependentes, como um recurso de armazenamento para mensagens mortas, você deverá usar a mesma região usada no recurso secundário da Grade de Eventos.
  6. Verifique se os pontos de extremidade são testados regularmente para fornecer a garantia de que os recursos do plano de recuperação estão em vigor e funcionando corretamente.

Exemplo de implementação básica de failover do lado do cliente para tópicos personalizados

O código do exemplo a seguir é um editor .NET simples que tenta publicar primeiro em seu tópico principal. Se não for bem-sucedido, ele falhará no tópico secundário. Em ambos os casos, ele também verifica a api de integridade do outro tópico fazendo um GET no https://<topic-name>.<topic-region>.eventgrid.azure.net/api/health. Um tópico íntegro deve sempre responder com 200 OK quando um GET é feito no ponto de extremidade /api/health.

Observação

O código de exemplo a seguir destina-se apenas a fins de demonstração e não ao uso em produção.

using System;
using System.Net.Http;
using System.Collections.Generic;
using System.Threading.Tasks;
using Azure;
using Azure.Messaging.EventGrid;

namespace EventGridFailoverPublisher
{
    // This captures the "Data" portion of an EventGridEvent on a custom topic
    class FailoverEventData
    {
        public string TestStatus { get; set; }
    }

    class Program
    {
        static async Task Main(string[] args)
        {
            // TODO: Enter the endpoint each topic. You can find this topic endpoint value
            // in the "Overview" section in the "Event Grid topics" page in Azure Portal..
            string primaryTopic = "https://<primary-topic-name>.<primary-topic-region>.eventgrid.azure.net/api/events";
            string secondaryTopic = "https://<secondary-topic-name>.<secondary-topic-region>.eventgrid.azure.net/api/events";

            // TODO: Enter topic key for each topic. You can find this in the "Access Keys" section in the
            // "Event Grid topics" page in Azure Portal.
            string primaryTopicKey = "<your-primary-topic-key>";
            string secondaryTopicKey = "<your-secondary-topic-key>";

            Uri primaryTopicUri = new Uri(primaryTopic);
            Uri secondaryTopicUri = new Uri(secondaryTopic);

            Uri primaryTopicHealthProbe = new Uri($"https://{primaryTopicUri.Host}/api/health");
            Uri secondaryTopicHealthProbe = new Uri($"https://{secondaryTopicUri.Host}/api/health");

            var httpClient = new HttpClient();

            try
            {
                var client = new EventGridPublisherClient(primaryTopicUri, new AzureKeyCredential(primaryTopicKey));

                await client.SendEventsAsync(GetEventsList());
                Console.Write("Published events to primary Event Grid topic.");

                HttpResponseMessage health = httpClient.GetAsync(secondaryTopicHealthProbe).Result;
                Console.Write("\n\nSecondary Topic health " + health);
            }
            catch (RequestFailedException ex)
            {
                var client = new EventGridPublisherClient(secondaryTopicUri, new AzureKeyCredential(secondaryTopicKey));

                await client.SendEventsAsync(GetEventsList());
                Console.Write("Published events to secondary Event Grid topic. Reason for primary topic failure:\n\n" + ex);

                HttpResponseMessage health = await httpClient.GetAsync(primaryTopicHealthProbe);
                Console.WriteLine($"Primary Topic health {health}");
            }

            Console.ReadLine();
        }

        static IList<EventGridEvent> GetEventsList()
        {
            List<EventGridEvent> eventsList = new List<EventGridEvent>();

            for (int i = 0; i < 5; i++)
            {
                eventsList.Add(new EventGridEvent(
                    subject: "test" + i,
                    eventType: "Contoso.Failover.Test",
                    dataVersion: "2.0",
                    data: new FailoverEventData
                    {
                        TestStatus = "success"
                    }));
            }

            return eventsList;
        }
    }
}

Experimentar

Agora que você tem todos os componentes em vigor, é possível testar sua implementação de failover.

Para garantir que o failover esteja funcionando, altere alguns caracteres na chave de tópico primária para invalidá-la. Experimente executar o publicador novamente. Com o exemplo a seguir, os eventos continuarão fluindo pela Grade de Eventos, mas quando você examinar o cliente, verá que eles estão sendo publicados por meio do tópico secundário.

Extensões possíveis

Há muitas maneiras de estender este exemplo com base em suas necessidades. Para cenários de alto volume, talvez convenha verificar regularmente a api de integridade do tópico de maneira independente. Dessa forma, se um tópico ficasse inativo, não seria necessário verificá-lo em cada publicação. Após saber que um tópico não é íntegro, será possível definir a publicação do tópico secundário como padrão.

Da mesma forma, talvez convenha implementar a lógica de failback com base em suas necessidades específicas. Se a publicação no data center mais próximo for essencial para você reduzir a latência, será possível investigar periodicamente a api de integridade de um tópico que realizou o failover. Uma vez que esteja íntegro novamente, é seguro fazer o failback para o data center mais próximo.

Próximas etapas