Függvényláncolási minta

A függvényláncolás egy olyan minta, amelyben függvénysorozatot futtat sorrendben. Gyakori, hogy az egyik függvény kimenetét a következő bemenetnek adja át. Ez a cikk a Durable Functions rövid útmutató (C#, JavaScript) végrehajtásakor létrehozott láncolássorozatot ismerteti. TypeScript, Python, PowerShell vagy Java). További információ a Durable Functions áttekintésében.

Előfeltételek

A függvényláncolás egy olyan minta, amely sorrendben futtatja a tevékenységek sorozatát. Gyakori, hogy egy tevékenység kimenetét a következő bemenetnek adja át. Ez a cikk a Durable Task SDK-k .NET, JavaScript, Python és Java láncolását ismerteti.

Függvények a láncoló mintában

Ez a cikk az alábbi függvényeket ismerteti a mintaalkalmazásban:

  • E1_HelloSequence: Egy vezénylő függvény , amely egymás után többször hív E1_SayHello meg. Tárolja az egyes kimeneteket, és rögzíti az eredményeket.
  • E1_SayHello: Egy tevékenységfüggvény, amely hozzáadja a "Hello" szót egy sztring elejéhez.
  • HttpStart: HTTP által aktivált durable ügyfélfüggvény amely elindítja az orchestrator egy példányát.

Ez a cikk a mintaalkalmazás alábbi összetevőit ismerteti:

  • GreetingOrchestration, greetingOrchestrator, , function_chaining_orchestratorvagy ActivityChaining: Olyan vezénylő, amely több tevékenységet hív meg egymás után. Tárolja az egyes kimeneteket, és rögzíti az eredményeket.
  • Tevékenységfüggvények: A bemeneti és visszaadott eredményeket feldolgozó tevékenységek. Minden tevékenység egy egyszerű átalakítást hajt végre a bemeneten.
  • Kliens: Egy kliensalkalmazás, amely elindít egy orchestrátor példányt, és várja az eredményt.

Orchestrator függvény kódja

[FunctionName("E1_HelloSequence")]
public static async Task<List<string>> Run(
    [OrchestrationTrigger] IDurableOrchestrationContext context)
{
    var outputs = new List<string>();

    outputs.Add(await context.CallActivityAsync<string>("E1_SayHello", "Tokyo"));
    outputs.Add(await context.CallActivityAsync<string>("E1_SayHello", "Seattle"));
    outputs.Add(await context.CallActivityAsync<string>("E1_SayHello_DirectInput", "London"));

    // returns ["Hello Tokyo!", "Hello Seattle!", "Hello London!"]
    return outputs;
}

Minden C# vezénylési függvénynek DurableOrchestrationContext típusú paraméterrel kell rendelkeznie, amely a Microsoft.Azure.WebJobs.Extensions.DurableTask szerelvényben található. Ezzel a környezeti objektummal meghívhat más tevékenységfüggvényeket , és bemeneti paramétereket adhat át annak metódusával CallActivityAsync .

A kód egymás után háromszor hív E1_SayHello meg különböző paraméterértékeket. A rendszer hozzáadja az egyes hívások visszatérési értékét a outputs listához, amelyet a függvény végén ad vissza.

Ez a kód egy vezénylőt jelenít meg, amely egymás után három tevékenységet hív meg, és minden kimenetet átad a következő tevékenységnek:

using System.Threading.Tasks;
using Microsoft.DurableTask;

[DurableTask]
public class GreetingOrchestration : TaskOrchestrator<string, string>
{
    public override async Task<string> RunAsync(TaskOrchestrationContext context, string name)
    {
        // Step 1: Say hello to the person
        string greeting = await context.CallActivityAsync<string>(nameof(SayHelloActivity), name);

        // Step 2: Process the greeting
        string processedGreeting = await context.CallActivityAsync<string>(nameof(ProcessGreetingActivity), greeting);

        // Step 3: Finalize the response
        string finalResponse = await context.CallActivityAsync<string>(nameof(FinalizeResponseActivity), processedGreeting);

        return finalResponse;
    }
}

Minden .NET vezérlő örökli TaskOrchestrator<TInput, TOutput>. Ez a TaskOrchestrationContext lehetővé teszi a tevékenységek meghívását a CallActivityAsync segítségével. A kód három tevékenységet hív meg egymás után, ahol minden tevékenység megkapja az előző tevékenység kimenetét.

Tevékenységfüggvény kódja

[FunctionName("E1_SayHello")]
public static string SayHello([ActivityTrigger] IDurableActivityContext context)
{
    string name = context.GetInput<string>();
    return $"Hello {name}!";
}

A tevékenységek az attribútumot ActivityTrigger használják. Tevékenységműveletekhez használd a IDurableActivityContext-t, például a bemeneti adatok olvasásához GetInput<T>.

E1_SayHello formázza az üdvözlő karakterláncot.

Ahelyett, hogy IDurableActivityContext-hez kötne, kössön közvetlenül a tevékenységfüggvénybe átadott típushoz. Például:

[FunctionName("E1_SayHello_DirectInput")]
public static string SayHelloDirectInput([ActivityTrigger] string name)
{
    return $"Hello {name}!";
}

A Durable Task SDK-ben a tevékenységek a következőtől öröklődnek: TaskActivity<TInput, TOutput>

using System.Threading.Tasks;
using Microsoft.DurableTask;
using Microsoft.Extensions.Logging;

[DurableTask]
public class SayHelloActivity : TaskActivity<string, string>
{
    private readonly ILogger<SayHelloActivity> _logger;

    public SayHelloActivity(ILogger<SayHelloActivity> logger)
    {
        _logger = logger;
    }

    public override Task<string> RunAsync(TaskActivityContext context, string name)
    {
        _logger.LogInformation("Activity SayHello called with name: {Name}", name);
        return Task.FromResult($"Hello {name}!");
    }
}

[DurableTask]
public class ProcessGreetingActivity : TaskActivity<string, string>
{
    public override Task<string> RunAsync(TaskActivityContext context, string greeting)
    {
        return Task.FromResult($"{greeting} How are you today?");
    }
}

[DurableTask]
public class FinalizeResponseActivity : TaskActivity<string, string>
{
    public override Task<string> RunAsync(TaskActivityContext context, string response)
    {
        return Task.FromResult($"{response} I hope you're doing well!");
    }
}

Szolgáltatások, mint a ILogger, lekéréséhez használja a függőséginjektálást. Adja hozzá a [DurableTask] attribútumot a dolgozónál való tevékenység regisztrálásához.

Ügyfélkód az orkesztráció elindításához

Orkesztrátorfunkció-példány indítása egy kliensfunkcióból. A HttpStart HTTP-triggerelt függvény használatával indítsa el a E1_HelloSequence példányokat.

public static class HttpStart
{
    [FunctionName("HttpStart")]
    public static async Task<HttpResponseMessage> Run(
        [HttpTrigger(AuthorizationLevel.Function, methods: "post", Route = "orchestrators/{functionName}")] HttpRequestMessage req,
        [DurableClient] IDurableClient starter,
        string functionName,
        ILogger log)
    {
        // Function input comes from the request content.
        object eventData = await req.Content.ReadAsAsync<object>();
        string instanceId = await starter.StartNewAsync(functionName, eventData);

        log.LogInformation($"Started orchestration with ID = '{instanceId}'.");

        return starter.CreateCheckStatusResponse(req, instanceId);
    }
}

A vezénylőkkel való interakcióhoz adjon hozzá egy bemeneti kötést DurableClient . Használja a kliensprogramot egy orchestration elindításához, és adjon vissza egy HTTP-választ, amely tartalmazza az új orchestration állapotának ellenőrzésére szolgáló URL-eket.

Indítsa el az orkestrációt egy ügyfélalkalmazásból. Az ügyfél ütemezi az orchestration-t, és megvárja annak befejezését.

using System;
using Microsoft.DurableTask.Client;

// Create the client
var client = DurableTaskClientBuilder.UseDurableTaskScheduler(connectionString).Build();

// Schedule a new orchestration instance
string instanceId = await client.ScheduleNewOrchestrationInstanceAsync(
    nameof(GreetingOrchestration),
    input: "World");

Console.WriteLine($"Started orchestration with ID: {instanceId}");

// Wait for the orchestration to complete
OrchestrationMetadata result = await client.WaitForInstanceCompletionAsync(
    instanceId,
    getInputsAndOutputs: true);

Console.WriteLine($"Orchestration completed with result: {result.ReadOutputAs<string>()}");

Hozza létre a DurableTaskClient a Durable Task Scheduler kapcsolati karakterlánc használatával. Az ScheduleNewOrchestrationInstanceAsync vezénylés indítására, és WaitForInstanceCompletionAsync a befejezésre való várakozásra használható.

A függvényláncoló minta futtatása

A E1_HelloSequence vezénylés futtatásához küldje el ezt a HTTP POST-kérést a HttpStart függvénynek.

POST http://{host}/orchestrators/E1_HelloSequence

Megjegyzés:

Az előző HTTP-kódrészlet feltételezi, hogy a minta host.json fájlja eltávolítja az alapértelmezett api/ előtagot az összes HTTP-eseményindító függvény URL-címéről. Keresse meg ezt a konfigurációt a minta host.json fájljában.

Ha például egy myfunctionapp nevű függvényalkalmazásban futtatja a mintát, cserélje le {host}-t myfunctionapp.azurewebsites.net-re.

A kérelem HTTP 202-t ad vissza (a rövidség kedvéért levágva):

HTTP/1.1 202 Accepted
Content-Length: 719
Content-Type: application/json; charset=utf-8
Location: http://{host}/runtime/webhooks/durabletask/instances/96924899c16d43b08a536de376ac786b?taskHub=DurableFunctionsHub&connection=Storage&code={systemKey}

(...trimmed...)

A vezénylési üzenetsorok azonnal elindulnak. A Location fejlécben szereplő URL segítségével ellenőrizze a végrehajtás állapotát.

GET http://{host}/runtime/webhooks/durabletask/instances/96924899c16d43b08a536de376ac786b?taskHub=DurableFunctionsHub&connection=Storage&code={systemKey}

A válasz az orchestráció állapotát mutatja. Mivel gyorsan befejeződik, a példány gyakran befejezett állapotban van, és az alábbihoz hasonló választ ad vissza (a rövidség kedvéért levágva):

HTTP/1.1 200 OK
Content-Length: 179
Content-Type: application/json; charset=utf-8

{"runtimeStatus":"Completed","input":null,"output":["Hello Tokyo!","Hello Seattle!","Hello London!"],"createdTime":"2017-06-29T05:24:57Z","lastUpdatedTime":"2017-06-29T05:24:59Z"}

A példány runtimeStatusbefejeződött, és output tartalmazza a vezénylő függvény végrehajtásának JSON-szerializált eredményét.

Megjegyzés:

Hasonló kezdő logikát implementálhat más triggertípusokhoz, például queueTrigger, eventHubTriggervagy timerTrigger.

Tekintse át a függvény végrehajtási naplóit. A E1_HelloSequence függvény a vezénylés megbízhatóságában leírt visszajátszási viselkedés miatt többször is elindul és fejeződik be. De E1_SayHello csak háromszor hajtódik végre, mert a tevékenységfüggvény-végrehajtások nem kerülnek újra lejátszásra.

A minta futtatásához a következőkre van szükség:

  1. Indítsa el a Durable Task Scheduler emulátort (helyi fejlesztéshez):

    docker run -d -p 8080:8080 -p 8082:8082 --name dts-emulator mcr.microsoft.com/dts/dts-emulator:latest
    
  2. Indítsa el a feldolgozót a vezénylő és a tevékenységek regisztrálásához.

  3. Futtassa a klienst az orkesztráció ütemezéséhez, és várja meg az eredményt.

Az ügyfél kimenete a láncolt vezénylés eredményét jeleníti meg:

Started orchestration with ID: abc123
Orchestration completed with result: "Hello World! How are you today? I hope you're doing well!"

A munkavégző naplókban minden tevékenység egymás után fut, és a kimenetet a következő tevékenységnek továbbítja.

Következő lépések

Ez a minta egy egyszerű függvénylánc-összekapcsolást mutat be. Ezután implementálja a ventilátor-out/ventilátor-in mintát.

Ez a minta egy egyszerű függvénylánc-összekapcsolást mutat be. Ezután ismerkedjen meg a további mintákkal.

A Teljes JavaScript SDK-példákért tekintse meg a Durable Task JavaScript SDK-mintáit.