BT

Disseminando conhecimento e inovação em desenvolvimento de software corporativo.

Contribuir

Tópicos

Escolha a região

Início Notícias Simplificando a criação de Stateful Serverless Workflows com Azure Orchestrators

Simplificando a criação de Stateful Serverless Workflows com Azure Orchestrators

O Azure Durable Functions estende o paradigma da computação sem servidor, introduzindo o conceito de orquestração de funções, permitindo a definição de fluxos de trabalho mais complexos. Se já imaginou usá-los, a Microsoft publicou um guia para ajudar os desenvolvedores a iniciar sua jornada nesta nova funcionalidade.

O Azure Functions é um serviço fornecido pela Microsoft que inicia basicamente a partir de um disparo; ele recebe uma entrada, executa um processamento e produz uma saída como resultado. O Durable Functions amplia este conceito, pois de certa maneira, acrescenta o estado a algo que é no fundo, sem estado. O Durable Functions é um conjunto de funções chamadas de uma função orquestradora que executa as demais funções em uma única transação, permitindo assim a escrita de código de fluxos de trabalho complexos pelos desenvolvedores.

Os dois conceitos fundamentais por de traz da Azure Function são as funções e gatilhos. Uma função é um único método em uma classe estática. Um gatilho é um evento que aciona o código. Uma função é um único método em uma classe estática. Um gatilho é um evento que aciona o código. Gatilhos comuns são Http, executados a partir de uma requisição HTTP por um usuário, e o Timer, que é o agendamento da execução de um código. Além disto, o Durable Functions utiliza dois novos conceitos:

[FunctionName("GetAllRepositoriesForOrganization")]
public static async Task<List> GetAllRepositoriesForOrganization([ActivityTrigger] DurableActivityContext context)
{
// retrieves the organization name from the Orchestrator function
var organizationName = context.GetInput();
// invoke the API to retrieve the list of repositories of a specific organization
var repositories = (await github.Repository.GetAllForOrg(organizationName)).Select(x => (x.Id, x.Name)).ToList();
return repositories;
}
  • Orchestrator functions, que podem ser vistas como uma co-rotina baseada na nuvem. Em outras palavras, uma função orquestradora é capaz de definir o ponto em execução na função, acionar outras funções e esperar até que as execuções sejam completas e então voltar ao ponto em que havia parado.
  • Activity functions, são funções que podem ser executadas dentro de um orquestrador. Respondem somente a um orquestrador que as chama. Os resultados de uma activity function são armazenados em um cache e são executados apenas uma vez por instância de orquestrador. Este é um exemplo de uma activity function que recupera uma lista de repositórios do GitHub:

Observe o uso do atributo ActivityTrigger para o parâmetro DurableActivityContext: isso é o que qualifica uma função como Activity Function.

Com isso em mente, podemos definir uma função que orquestra a recuperação de todos os repositórios de uma organização e, em seguida, somar o total de pendências em aberto para cada repositório e armazenar o resultado em algum lugar:

[FunctionName("Orchestrator")]
public static async Task RunOrchestrator(
    [OrchestrationTrigger] DurableOrchestrationContext context)
{
    // retrieves the organization name from the Orchestrator_HttpStart function
    var organizationName = context.GetInput();
    // retrieves the list of repositories for an organization by invoking a separate Activity Function.
    var repositories = await context.CallActivityAsync<List>("GetAllRepositoriesForOrganization", organizationName);

    // Creates an array of task to store the result of each functions
    var tasks = new Task[repositories.Count];
    for (int i = 0; i < repositories.Count; i++)
    {
        // Starting a `GetOpenedIssues` activity WITHOUT `async`
        // This will starts Activity Functions in parallel instead of sequentially.
        tasks[i] = context.CallActivityAsync("GetOpenedIssues", (repositories[i]));
    }

    // Wait for all Activity Functions to complete execution
    await Task.WhenAll(tasks);

    // Retrieve the result of each Activity Function and return them in a list
    var openedIssues = tasks.Select(x => x.Result).ToList();

    // Send the list to an Activity Function to save them to Blob Storage.
    await context.CallActivityAsync("SaveRepositories", openedIssues);

    return context.InstanceId;
}

No exemplo acima, observe o uso do atributo OrchestrationTrigger com um parâmetro DurableOrchestrationContext que qualifica o RunOrchestrator como uma função do orquestrador.

O que é interessante no código acima é que cada chamada do context, por si só, é uma Azure Function. Isso significa que a execução do fluxo se beneficia da escalabilidade e da confiabilidade das Azure Functions.

Você pode encontrar o código acima no GitHub e, claro, não deixe de conferir o tutorial da Microsoft para obter todos os detalhes.

Avalie esse artigo

Relevância
Estilo/Redação

Conteúdo educacional

BT