Azure Metadata Service: Scheduled Events para VMs do Linux

Aplica-se a: ✔️ VMs do Windows Conjuntos ✔️ de dimensionamento ✔️ flexíveis Conjuntos de dimensionamento uniformes

O Scheduled Events é um Azure Metadata Service que dá tempo à aplicação para se preparar para a manutenção da máquina virtual (VM). Fornece informações sobre os próximos eventos de manutenção (por exemplo, reiniciar) para que a aplicação possa preparar-se e limitar a interrupção. Está disponível para todos os tipos de Máquinas Virtuais do Azure, incluindo PaaS e IaaS no Windows e no Linux.

Para obter informações sobre Os Eventos Agendados no Linux, veja Scheduled Events for Linux VMs (Eventos Agendados para VMs do Linux).

Nota

Os Eventos Agendados estão geralmente disponíveis em todas as Regiões do Azure. Veja Disponibilidade de Versões e Regiões para obter as informações de versão mais recentes.

Porquê utilizar Eventos Agendados?

Muitas aplicações podem beneficiar do tempo de preparação para a manutenção das VMs. O tempo pode ser utilizado para executar tarefas específicas da aplicação que melhorem a disponibilidade, a fiabilidade e a capacidade de serviço, incluindo:

  • Ponto de verificação e restauro.
  • Esvaziamento de ligações.
  • Ativação pós-falha da réplica primária.
  • Remoção de um conjunto de balanceadores de carga.
  • Registo de eventos.
  • Encerramento correto.

Com o Scheduled Events, a sua aplicação pode saber quando ocorrerá a manutenção e acionar tarefas para limitar o respetivo impacto.

O Scheduled Events fornece eventos nos seguintes casos de utilização:

Noções Básicas

O Serviço de Metadados expõe informações sobre a execução de VMs através de um ponto final REST acessível a partir da VM. As informações estão disponíveis através de um IP não encaminhável para que não estejam expostas fora da VM.

Âmbito

Os eventos agendados são entregues e podem ser reconhecidos por:

  • Máquinas Virtuais autónomo.
  • Todas as VMs num serviço cloud do Azure (clássico).
  • Todas as VMs num conjunto de disponibilidade.
  • Todas as VMs num grupo de colocação de conjuntos de dimensionamento.

Nota

Os Eventos Agendados para todas as máquinas virtuais (VMs) num inquilino do Controlador de Recursos de Infraestrutura (FC) são entregues a todas as VMs num inquilino do FC. O inquilino do FC equivale a uma VM autónoma, a um Serviço Cloud completo, a um Conjunto de Disponibilidade completo e a um Grupo de Colocação para um Conjunto de Dimensionamento de VMs (VMSS), independentemente da utilização da Zona de Disponibilidade.

Como resultado, verifique o Resources campo no evento para identificar que VMs são afetadas.

Deteção de pontos finais

Para VMs ativadas para VNET, o Serviço de Metadados está disponível a partir de um IP não encaminhável estático, 169.254.169.254. O ponto final completo para a versão mais recente dos Eventos Agendados é:

http://169.254.169.254/metadata/scheduledevents?api-version=2020-07-01

Se a VM não for criada num Rede Virtual, os casos predefinidos para serviços cloud e VMs clássicas, é necessária lógica adicional para detetar o endereço IP a utilizar. Para saber como detetar o ponto final do anfitrião, veja este exemplo.

Disponibilidade da versão e da região

O serviço Eventos Agendados tem o controlo de versões. As versões são obrigatórias; a versão atual é 2020-07-01.

Versão Tipo de Versão Regiões Notas de Versão
2020-07-01 Disponibilidade Geral Todos
  • Foi adicionado suporte para a Duração do Evento
  • 2019-08-01 Disponibilidade Geral Todos
  • Foi adicionado suporte para o EventSource
  • 2019-04-01 Disponibilidade Geral Todos
  • Foi adicionado suporte para a Descrição do Evento
  • 2019-01-01 Disponibilidade Geral Todos
  • Foi adicionado suporte para conjuntos de dimensionamento de máquinas virtuais EventType "Terminate"
  • 2017-11-01 Disponibilidade Geral Todos
  • Foi adicionado suporte para expulsão de VM Spot EventType "Preempt"
  • 2017-08-01 Disponibilidade Geral Todos
  • Foi removido o caráter de sublinhado pré-end dos nomes de recursos das VMs IaaS
  • Requisito de cabeçalho de metadados imposto para todos os pedidos
  • 2017-03-01 Pré-visualizar Todos
  • Versão inicial
  • Nota

    Versões de pré-visualização anteriores de Eventos Agendados suportadas {latest} como a versão da API. Este formato já não é suportado e será preterido no futuro.

    Ativar e desativar Eventos Agendados

    Os Eventos Agendados estão ativados para o seu serviço quando fizer um pedido de eventos pela primeira vez. Deverá esperar uma resposta atrasada na sua primeira chamada de até dois minutos.

    Os Eventos Agendados serão desativados para o seu serviço se não fizer um pedido durante 24 horas.

    Manutenção iniciada pelo utilizador

    A manutenção da VM iniciada pelo utilizador através do portal do Azure, da API, da CLI ou do PowerShell resulta num evento agendado. Em seguida, pode testar a lógica de preparação da manutenção na sua aplicação e a sua aplicação pode preparar-se para a manutenção iniciada pelo utilizador.

    Se reiniciar uma VM, é agendado um evento com o tipo Reboot . Se reimplementar uma VM, é agendado um evento com o tipo Redeploy . Normalmente, os eventos com uma origem de eventos de utilizador podem ser imediatamente aprovados para evitar um atraso nas ações iniciadas pelo utilizador. Recomendamos que tenha uma VM primária e secundária a comunicar e aprovar eventos agendados gerados pelo utilizador caso a VM primária não responda. Isto evitará atrasos na recuperação da aplicação para um bom estado.

    Utilizar a API

    Cabeçalhos

    Quando consulta o Serviço de Metadados, tem de fornecer o cabeçalho Metadata:true para garantir que o pedido não foi redirecionado involuntariamente. O Metadata:true cabeçalho é necessário para todos os pedidos de eventos agendados. A não inclusão do cabeçalho no pedido resulta numa resposta "Pedido Incorreto" do Serviço de Metadados.

    Consultar eventos

    Pode consultar eventos agendados ao efetuar a seguinte chamada:

    Exemplo de Bash

    curl -H Metadata:true http://169.254.169.254/metadata/scheduledevents?api-version=2020-07-01
    

    Exemplo do PowerShell

    Invoke-RestMethod -Headers @{"Metadata"="true"} -Method GET -Uri "http://169.254.169.254/metadata/scheduledevents?api-version=2020-07-01" | ConvertTo-Json -Depth 64
    

    Exemplo de Python

    import json
    import requests
    
    metadata_url ="http://169.254.169.254/metadata/scheduledevents"
    header = {'Metadata' : 'true'}
    query_params = {'api-version':'2020-07-01'}
    
    def get_scheduled_events():           
        resp = requests.get(metadata_url, headers = header, params = query_params)
        data = resp.json()
        return data
    
    

    Uma resposta contém uma matriz de eventos agendados. Uma matriz vazia significa que atualmente não estão agendados eventos. No caso de existirem eventos agendados, a resposta contém uma matriz de eventos.

    {
        "DocumentIncarnation": {IncarnationID},
        "Events": [
            {
                "EventId": {eventID},
                "EventType": "Reboot" | "Redeploy" | "Freeze" | "Preempt" | "Terminate",
                "ResourceType": "VirtualMachine",
                "Resources": [{resourceName}],
                "EventStatus": "Scheduled" | "Started",
                "NotBefore": {timeInUTC},       
                "Description": {eventDescription},
                "EventSource" : "Platform" | "User",
                "DurationInSeconds" : {timeInSeconds},
            }
        ]
    }
    

    Propriedades do evento

    Propriedade Descrição
    Encarnação do Documento Número inteiro que aumenta quando a matriz de eventos é alterada. Os documentos com a mesma encarnação contêm as mesmas informações do evento e a encarnação será incrementada quando um evento mudar.
    EventId Identificador exclusivo global para este evento.

    Exemplo:
    • 602d9444-d2cd-49c7-8624-8643e7171297
    EventType Impacto que este evento causa.

    Valores:
    • Freeze: A Máquina Virtual está agendada para ser interrompida durante alguns segundos. A conectividade da CPU e da rede pode ser suspensa, mas não há qualquer impacto na memória ou nos ficheiros abertos.
    • Reboot: a Máquina Virtual está agendada para reinício (a memória não persistente é perdida).
    • Redeploy: A Máquina Virtual está agendada para ser movida para outro nó (os discos efémeros são perdidos).
    • Preempt: a Máquina Virtual Spot está a ser eliminada (os discos efémeros são perdidos). Este evento é disponibilizado com base no melhor esforço
    • Terminate: a máquina virtual está agendada para ser eliminada.
    ResourceType Tipo de recurso que este evento afeta.

    Valores:
    • VirtualMachine
    Recursos Lista de recursos que este evento afeta.

    Exemplo:
    • ["FrontEnd_IN_0", "BackEnd_IN_0"]
    EventStatus Estado deste evento.

    Valores:
    • Scheduled: este evento está agendado para ser iniciado após a hora especificada na NotBefore propriedade .
    • Started: este evento foi iniciado.
    Nunca Completed é fornecido nenhum estado ou um estado semelhante. O evento já não é devolvido quando o evento está concluído.
    NotBefore Hora após a qual este evento pode ser iniciado. É garantido que o evento não é iniciado antes desta hora. Ficará em branco se o evento já tiver sido iniciado

    Exemplo:
    • Seg, 19 Set 2016 18:29:47 GMT
    Description Descrição deste evento.

    Exemplo:
    • O servidor anfitrião está a ser submetido a manutenção.
    EventSource Iniciador do evento.

    Exemplo:
    • Platform: este evento é iniciado pela plataforma.
    • User: este evento é iniciado pelo utilizador.
    DurationInSeconds A duração esperada da interrupção causada pelo evento.

    Exemplo:
    • 9: a interrupção causada pelo evento irá durar 9 segundos.
    • 0: o evento não interromperá a VM nem afetará a sua disponibilidade (por exemplo, atualização para a rede)
    • -1: o valor predefinido utilizado se a duração do impacto for desconhecida ou não aplicável.

    Agendamento de eventos

    Cada evento é agendado para um período mínimo de tempo no futuro com base no tipo de evento. Desta vez, reflete-se na propriedade de NotBefore um evento.

    EventType Aviso mínimo
    Fixar 15 minutos
    Reiniciar 15 minutos
    Voltar a implementar 10 minutos
    Preempt 30 segundos
    Terminate Configurável pelo Utilizador: 5 a 15 minutos

    Nota

    Em alguns casos, o Azure consegue prever a falha do anfitrião devido a hardware degradado e tentará mitigar a interrupção do serviço ao agendar uma migração. As máquinas virtuais afetadas receberão um evento agendado com um NotBefore que é normalmente de alguns dias no futuro. O tempo real varia consoante a avaliação do risco de falha prevista. Quando possível, o Azure tenta dar um aviso prévio de 7 dias, mas o tempo real varia e pode ser menor se a predição for que existe uma alta probabilidade de o hardware falhar iminentemente. Para minimizar o risco para o seu serviço caso o hardware falhe antes da migração iniciada pelo sistema, recomendamos que reimplemente a máquina virtual o mais rapidamente possível.

    Nota

    No caso de o nó de anfitrião sofrer uma falha de hardware, o Azure ignorará o período de aviso mínimo e iniciará imediatamente o processo de recuperação das máquinas virtuais afetadas. Isto reduz o tempo de recuperação no caso de as VMs afetadas não conseguirem responder. Durante o processo de recuperação, será criado um evento para todas as VMs afetadas com EventType = Reboot e EventStatus = Started.

    Frequência de consulta

    Pode consultar o ponto final para obter atualizações com a frequência ou pouca frequência que quiser. No entanto, quanto mais tempo demorar entre os pedidos, mais tempo perderá potencialmente para reagir a um evento futuro. A maioria dos eventos tem um aviso prévio de 5 a 15 minutos, embora, em alguns casos, o aviso prévio possa ser de apenas 30 segundos. Para garantir que tem o máximo de tempo possível para realizar ações de mitigação, recomendamos que consulte o serviço uma vez por segundo.

    Iniciar um evento

    Depois de conhecer um evento futuro e concluir a lógica para um encerramento correto, pode aprovar o evento pendente ao fazer uma POST chamada para o Serviço de Metadados com EventId. Esta chamada indica ao Azure que pode encurtar o tempo mínimo de notificação (sempre que possível). O evento pode não ser iniciado imediatamente após a aprovação. Em alguns casos, o Azure exigirá a aprovação de todas as VMs alojadas no nó antes de prosseguir com o evento.

    O exemplo JSON seguinte é esperado no corpo do POST pedido. O pedido deve conter uma lista de StartRequests. Cada StartRequest um contém EventId para o evento que pretende agilizar:

    {
    	"StartRequests" : [
    		{
    			"EventId": {EventId}
    		}
    	]
    }
    

    O serviço devolverá sempre um código de êxito 200 no caso de um ID de evento válido, mesmo que já tenha sido aprovado por uma VM diferente. Um código de erro 400 indica que o cabeçalho ou payload do pedido foi mal formado.

    Nota

    Os eventos não continuarão a menos que sejam aprovados através de uma mensagem POST ou o tempo Não Antes decorrido. Isto inclui eventos acionados pelo utilizador, como reinícios da VM a partir do portal do Azure.

    Exemplo de Bash

    curl -H Metadata:true -X POST -d '{"StartRequests": [{"EventId": "f020ba2e-3bc0-4c40-a10b-86575a9eabd5"}]}' http://169.254.169.254/metadata/scheduledevents?api-version=2020-07-01
    

    Exemplo do PowerShell

    Invoke-RestMethod -Headers @{"Metadata" = "true"} -Method POST -body '{"StartRequests": [{"EventId": "5DD55B64-45AD-49D3-BBC9-F57D4EA97BD7"}]}' -Uri http://169.254.169.254/metadata/scheduledevents?api-version=2020-07-01 | ConvertTo-Json -Depth 64
    

    Exemplo de Python

    import json
    import requests
    
    def confirm_scheduled_event(event_id):  
       # This payload confirms a single event with id event_id
       payload = json.dumps({"StartRequests": [{"EventId": event_id }]})
       response = requests.post("http://169.254.169.254/metadata/scheduledevents", 
                                headers =  {'Metadata' : 'true'}, 
                                params = {'api-version':'2020-07-01'}, 
                                data = payload)    
       return response.status_code
    

    Nota

    Reconhecer um evento permite que o evento prossiga para todos Resources no evento e não apenas para a VM que reconhece o evento. Por conseguinte, pode optar por eleger um líder para coordenar a confirmação, o que pode ser tão simples como a primeira máquina no Resources campo.

    Respostas de exemplo

    Segue-se um exemplo de uma série de eventos que foram vistos por duas VMs que foram migradas em direto para outro nó.

    O DocumentIncarnation está a mudar sempre que existem novas informações no Events. Uma aprovação do evento permitiria que o congelamento continuasse tanto para WestNO_0 como para WestNO_1. O DurationInSeconds de -1 indica que a plataforma não sabe quanto tempo demorará a operação.

    {
        "DocumentIncarnation":  1,
        "Events":  [
                   ]
    }
    
    {
        "DocumentIncarnation":  2,
        "Events":  [
                       {
                           "EventId":  "C7061BAC-AFDC-4513-B24B-AA5F13A16123",
                           "EventStatus":  "Scheduled",
                           "EventType":  "Freeze",
                           "ResourceType":  "VirtualMachine",
                           "Resources":  [
                                             "WestNO_0",
                                             "WestNO_1"
                                         ],
                           "NotBefore":  "Mon, 11 Apr 2022 22:26:58 GMT",
                           "Description":  "Virtual machine is being paused because of a memory-preserving Live Migration operation.",
                           "EventSource":  "Platform",
                           "DurationInSeconds":  5
                       }
                   ]
    }
    
    {
        "DocumentIncarnation":  3,
        "Events":  [
                       {
                           "EventId":  "C7061BAC-AFDC-4513-B24B-AA5F13A16123",
                           "EventStatus":  "Started",
                           "EventType":  "Freeze",
                           "ResourceType":  "VirtualMachine",
                           "Resources":  [
                                             "WestNO_0",
                                             "WestNO_1"
                                         ],
                           "NotBefore":  "",
                           "Description":  "Virtual machine is being paused because of a memory-preserving Live Migration operation.",
                           "EventSource":  "Platform",
                           "DurationInSeconds":  5
                       }
                   ]
    }
    
    {
        "DocumentIncarnation":  4,
        "Events":  [
                   ]
    }
    
    

    Exemplo de Python

    O exemplo seguinte consulta o Serviço de Metadados para eventos agendados e aprova cada evento pendente:

    #!/usr/bin/python
    import json
    import requests
    from time import sleep
    
    # The URL to access the metadata service
    metadata_url ="http://169.254.169.254/metadata/scheduledevents"
    # This must be sent otherwise the request will be ignored
    header = {'Metadata' : 'true'}
    # Current version of the API
    query_params = {'api-version':'2020-07-01'}
    
    def get_scheduled_events():           
        resp = requests.get(metadata_url, headers = header, params = query_params)
        data = resp.json()
        return data
    
    def confirm_scheduled_event(event_id):  
        # This payload confirms a single event with id event_id
        # You can confirm multiple events in a single request if needed      
        payload = json.dumps({"StartRequests": [{"EventId": event_id }]})
        response = requests.post(metadata_url, 
                                headers= header,
                                params = query_params, 
                                data = payload)    
        return response.status_code
    
    def log(event): 
        # This is an optional placeholder for logging events to your system 
        print(event["Description"])
        return
    
    def advanced_sample(last_document_incarnation): 
        # Poll every second to see if there are new scheduled events to process
        # Since some events may have necessarily short warning periods, it is 
        # recommended to poll frequently
        found_document_incarnation = last_document_incarnation
        while (last_document_incarnation == found_document_incarnation):
            sleep(1)
            payload = get_scheduled_events()    
            found_document_incarnation = payload["DocumentIncarnation"]        
            
        # We recommend processing all events in a document together, 
        # even if you won't be actioning on them right away
        for event in payload["Events"]:
    
            # Events that have already started, logged for tracking
            if (event["EventStatus"] == "Started"):
                log(event)
                
            # Approve all user initiated events. These are typically created by an 
            # administrator and approving them immediately can help to avoid delays 
            # in admin actions
            elif (event["EventSource"] == "User"):
                confirm_scheduled_event(event["EventId"])            
                
            # For this application, freeze events less that 9 seconds are considered
            # no impact. This will immediately approve them
            elif (event["EventType"] == "Freeze" and 
                int(event["DurationInSeconds"]) >= 0  and 
                int(event["DurationInSeconds"]) < 9):
                confirm_scheduled_event(event["EventId"])
                
            # Events that may be impactful (eg. Reboot or redeploy) may need custom 
            # handling for your application
            else: 
                #TODO Custom handling for impactful events
                log(event)
        print("Processed events from document: " + str(found_document_incarnation))
        return found_document_incarnation
    
    def main():
        # This will track the last set of events seen 
        last_document_incarnation = "-1"
    
        input_text = "\
            Press 1 to poll for new events \n\
            Press 2 to exit \n "
        program_exit = False 
    
        while program_exit == False:
            user_input = input(input_text)    
            if (user_input == "1"):                        
                last_document_incarnation = advanced_sample(last_document_incarnation)
            elif (user_input == "2"):
                program_exit = True       
    
    if __name__ == '__main__':
        main()
    

    Passos seguintes