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
V3 programozási modell
V4 programozási modell
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.
V3 programozási modell
function.json
Ha Visual Studio Code-ban vagy az Azure portálon fejleszt, itt van a vezénylő function.json fájl.
{
"bindings": [
{
"name": "context",
"type": "orchestrationTrigger",
"direction": "in"
}
],
"disabled": false
}
A kulcsbeállítás a orchestrationTrigger kötés típusa. Minden orchestrátor funkcióknak ezt a trigger típust kell használnia.
Figyelmeztetés
A vezénylő függvények "nincs I/O" szabályának követéséhez ne használjon bemeneti vagy kimeneti kötéseket az orchestrationTrigger eseményindító-kötéssel. Ha más bemeneti vagy kimeneti kötésekre van szüksége, használja őket a vezénylő által meghívott függvényekben activityTrigger . További információkért tekintse meg a vezénylő függvény kódjának korlátozásait.
index.js
Az orchestrator funkció a következő:
const df = require("durable-functions");
module.exports = df.orchestrator(function* (context) {
context.log("Starting chain sample");
const output = [];
output.push(yield context.df.callActivity("E1_SayHello", "Tokyo"));
output.push(yield context.df.callActivity("E1_SayHello", "Seattle"));
output.push(yield context.df.callActivity("E1_SayHello", "London"));
return output;
});
Minden JavaScript vezénylési függvénynek tartalmaznia kell a modultdurable-functions. Ez egy könyvtár, amellyel Durable Functions-t írhat JavaScriptben. Három fő különbség a vezénylő függvény és az egyéb JavaScript-függvények között:
- A vezénylő függvény egy generátorfüggvény.
- A függvény a modul
durable-functions metódusának orchestrator hívásába van csomagolva (ittdf).
- A függvény szinkronos. Mivel a
orchestrator metódus hív context.done, a függvény visszatér.
Az context objektum egy df tartós vezénylési környezeti objektumot tartalmaz, amely lehetővé teszi más tevékenységfüggvények meghívását és bemeneti paraméterek átadását annak metódusával callActivity . A kód egymás után háromszor hívja meg a E1_SayHello-t különböző paraméterértékekkel, és a yield segítségével jelzi, hogy a végrehajtásnak várnia kell az aszinkron tevékenységfüggvény-hívások visszatérése előtt. A rendszer hozzáadja az egyes hívások visszatérési értékét a outputs tömbhöz, amelyet a függvény végén ad vissza.
V4 programozási modell
const df = require("durable-functions");
const helloActivityName = "sayHello";
df.app.orchestration("helloSequence", function* (context) {
context.log("Starting chain sample");
const output = [];
output.push(yield context.df.callActivity(helloActivityName, "Tokyo"));
output.push(yield context.df.callActivity(helloActivityName, "Seattle"));
output.push(yield context.df.callActivity(helloActivityName, "Cairo"));
return output;
});
Minden JavaScript vezénylési függvénynek tartalmaznia kell a modultdurable-functions. Ez a modul lehetővé teszi Durable Functions JavaScriptben való írását. A V4-csomópont programozási modelljének használatához telepítenie kell a v3.x verziót durable-functions.
Két fő különbség a vezénylő függvény és az egyéb JavaScript-függvények között:
- A vezénylő függvény egy generátorfüggvény.
- A függvény szinkronos. A függvény visszatér.
Az context objektum egy df tartós vezénylési környezeti objektumot tartalmaz, amely lehetővé teszi más tevékenységfüggvények meghívását és bemeneti paraméterek átadását annak metódusával callActivity . A kód egymás után háromszor hívja meg a sayHello-t különböző paraméterértékekkel, és a yield segítségével jelzi, hogy a végrehajtásnak várnia kell az aszinkron tevékenységfüggvény-hívások visszatérése előtt. A rendszer hozzáadja az egyes hívások visszatérési értékét a outputs tömbhöz, amelyet a függvény végén ad vissza.
Megjegyzés:
Python Durable Functions csak a Functions 3.0 futtatókörnyezetben érhetők el.
function.json
Ha Visual Studio Code-ot vagy az Azure portált használja fejlesztésre, íme a vezénylő függvény function.json fájljának tartalma. A legtöbb vezénylő function.json fájl szinte pontosan így néz ki.
{
"scriptFile": "__init__.py",
"bindings": [
{
"name": "context",
"type": "orchestrationTrigger",
"direction": "in"
}
]
}
A fontos a orchestrationTrigger kötés típusa. Minden orchestrátor funkcióknak ezt a trigger típust kell használnia.
Figyelmeztetés
A vezénylőfüggvények "nincs I/O" szabályának betartásához ne használjon bemeneti vagy kimeneti kötéseket az orchestrationTrigger eseményindító kötés használatakor. Ha más bemeneti vagy kimeneti kötésekre van szükség, azokat a activityTrigger függvények kontextusában kell használni, amelyeket a vezénylő hív meg. További információkért tekintse meg a vezénylő függvénykód korlátozásait ismertető cikket.
__init__.py
Az orchestrator funkció a következő:
import azure.functions as func
import azure.durable_functions as df
def orchestrator_function(context: df.DurableOrchestrationContext):
result1 = yield context.call_activity('E1_SayHello', "Tokyo")
result2 = yield context.call_activity('E1_SayHello', "Seattle")
result3 = yield context.call_activity('E1_SayHello', "London")
return [result1, result2, result3]
main = df.Orchestrator.create(orchestrator_function)
Minden Python vezénylési függvénynek tartalmaznia kell a durable-functions csomagot. Ez egy könyvtár, amely lehetővé teszi, hogy Pythonban írjon Durable Functions-t. Két fő különbség a vezénylő függvény és az egyéb Python függvények között:
- A vezénylő függvény egy generátorfüggvény.
- A fájl a fájl végén található megjelöléssel
main = df.Orchestrator.create(<orchestrator function name>) regisztrálja a vezénylő függvényt. Ez segít megkülönböztetni a fájlban deklarált többi segédfüggvénytől.
Az context objektum lehetővé teszi más tevékenységfüggvények meghívását és bemeneti paraméterek átadását annak metódusával call_activity . A kód egymás után háromszor hívja meg a E1_SayHello-t különböző paraméterértékekkel, és a yield segítségével jelzi, hogy a végrehajtásnak várnia kell az aszinkron tevékenységfüggvény-hívások visszatérése előtt. Az egyes hívások visszatérési értéke a függvény végén lesz visszaadva.
A PowerShell-minta még nem érhető el.
Java minta még nem érhető el.
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.
Az alábbi kód egy vezénylőt mutat be, amely egymás után három tevékenységet hív meg:
import {
OrchestrationContext,
TOrchestrator,
} from "@microsoft/durabletask-js";
const greetingOrchestrator: TOrchestrator = async function* (
ctx: OrchestrationContext,
name: string
): any {
// Step 1: Say hello to the person
const greeting: string = yield ctx.callActivity(sayHello, name);
// Step 2: Process the greeting
const processedGreeting: string = yield ctx.callActivity(processGreeting, greeting);
// Step 3: Finalize the response
const finalResponse: string = yield ctx.callActivity(finalizeResponse, processedGreeting);
return finalResponse;
};
Minden JavaScript-orchestrátor olyan generátorfüggvény (async function*), amely a yield használatával hív meg tevékenységeket. A vezénylési környezet metódusa callActivity a tevékenységek végrehajtását ütemezi. A kód három tevékenységet hív meg egymás után, és átadja az egyes tevékenységek kimenetét a következőnek.
Az alábbi kód egy vezénylőt mutat be, amely egymás után három tevékenységet hív meg:
from durabletask import task
# Orchestrator function
def function_chaining_orchestrator(ctx: task.OrchestrationContext, name: str) -> str:
"""Orchestrator that demonstrates function chaining pattern."""
# Call first activity
greeting = yield ctx.call_activity(say_hello, input=name)
# Call second activity with the result from first activity
processed_greeting = yield ctx.call_activity(process_greeting, input=greeting)
# Call third activity with the result from second activity
final_response = yield ctx.call_activity(finalize_response, input=processed_greeting)
return final_response
Minden Python vezénylő olyan generátorfunkció, amely yield használatával hívja meg a tevékenységeket. A vezénylési környezet metódusa call_activity a tevékenységek végrehajtását ütemezi. A kód három tevékenységet hív meg egymás után, és átadja az egyes tevékenységek kimenetét a következőnek.
Ez a minta .NET, JavaScript, Java és Python esetében jelenik meg.
Az alábbi kód egy vezénylőt mutat be, amely egymás után három tevékenységet hív meg:
import com.microsoft.durabletask.DurableTaskGrpcWorker;
import com.microsoft.durabletask.DurableTaskSchedulerWorkerExtensions;
import com.microsoft.durabletask.TaskOrchestration;
import com.microsoft.durabletask.TaskOrchestrationFactory;
DurableTaskGrpcWorker worker = DurableTaskSchedulerWorkerExtensions.createWorkerBuilder(connectionString)
.addOrchestration(new TaskOrchestrationFactory() {
@Override
public String getName() { return "ActivityChaining"; }
@Override
public TaskOrchestration create() {
return ctx -> {
String input = ctx.getInput(String.class);
// Call activities in sequence, passing output from one to the next
String x = ctx.callActivity("Reverse", input, String.class).await();
String y = ctx.callActivity("Capitalize", x, String.class).await();
String z = ctx.callActivity("ReplaceWhitespace", y, String.class).await();
ctx.complete(z);
};
}
})
.build();
Java-ban az orkesztrátorokat a TaskOrchestrationFactory használatával definiálják. A környezet metódusa callActivity ütemezi a tevékenységek végrehajtását, és await() megvárja az eredményt. A kód három tevékenységet hív meg egymás után, és átadja az egyes tevékenységek kimenetét a következőnek.
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}!";
}
V3 programozási modell
E1_SayHello/function.json
A function.json fájl az E1_SayHello esetén hasonló az E1_HelloSequence fájlhoz, azzal a különbséggel, hogy activityTrigger kötéstípust használ orchestrationTrigger helyett.
{
"bindings": [
{
"name": "name",
"type": "activityTrigger",
"direction": "in"
}
],
"disabled": false
}
Megjegyzés:
Használja a activityTrigger kötést az összes olyan tevékenységfüggvényhez, amelyet egy vezénylési függvény hív meg.
A E1_SayHello megvalósítása egy viszonylag triviális karakterlánc formázási művelet.
E1_SayHello/index.js
module.exports = function (context) {
context.done(null, `Hello ${context.bindings.name}!`);
};
A vezénylési függvénnyel ellentétben a tevékenységfüggvénynek nincs szüksége speciális beállításra. A vezénylő a kötés neve alatt adja át a context.bindings bemenetet az activityTrigger objektumon – ebben az esetben context.bindings.name. Állítsa be a kötés nevét az exportált függvény paramétereként, hogy közvetlenül hozzáférjen hozzá, ahogy azt a példa mutatja.
V4 programozási modell
sayHello formázza az üdvözlő karakterláncot.
const df = require("durable-functions");
const helloActivityName = "sayHello";
df.app.activity(helloActivityName, {
handler: function (input) {
return `Hello ${input}`;
},
});
A vezénylési függvénnyel ellentétben a tevékenységfüggvénynek nincs szüksége speciális beállításra. A vezénylő a függvény első argumentumaként adja át a bemenetet. A második argumentum a meghívási környezet, amelyet ez a példa nem használ.
E1_SayHello/function.json
A function.json fájl az E1_SayHello esetén hasonló az E1_HelloSequence fájlhoz, azzal a különbséggel, hogy activityTrigger kötéstípust használ orchestrationTrigger helyett.
{
"scriptFile": "__init__.py",
"bindings": [
{
"name": "name",
"type": "activityTrigger",
"direction": "in"
}
]
}
Megjegyzés:
Az orchestrációs függvény által hívott összes tevékenységfüggvénynek a(z) activityTrigger bindingot kell használniuk.
A E1_SayHello megvalósítása egy viszonylag triviális karakterlánc formázási művelet.
E1_SayHello/__init__.py
def main(name: str) -> str:
return f"Hello {name}!"
A vezénylő függvénnyel ellentétben az aktivitásfüggvényhez nincs szükség speciális beállításra. A vezénylő függvény által neki átadott bemenet közvetlenül elérhető a függvény paramétereként.
Hamarosan megjelenik a PowerShell-minta.
Hamarosan jön a Java példa.
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.
A Durable Task SDK tevékenységei egyszerű függvények:
import { ActivityContext } from "@microsoft/durabletask-js";
const sayHello = async (_ctx: ActivityContext, name: string): Promise<string> => {
return `Hello ${name}!`;
};
const processGreeting = async (_ctx: ActivityContext, greeting: string): Promise<string> => {
return `${greeting} How are you today?`;
};
const finalizeResponse = async (_ctx: ActivityContext, response: string): Promise<string> => {
return `${response} I hope you're doing well!`;
};
A vezénylőkkel ellentétben a tevékenységek I/O-műveleteket hajthatnak végre, például HTTP-hívásokat, adatbázis-lekérdezéseket és fájlhozzáférést. A bemenet közvetlenül paraméterként lesz átadva.
A Durable Task SDK tevékenységei egyszerű függvények:
from durabletask import task
def say_hello(ctx: task.ActivityContext, name: str) -> str:
"""First activity that greets the user."""
return f"Hello {name}!"
def process_greeting(ctx: task.ActivityContext, greeting: str) -> str:
"""Second activity that processes the greeting."""
return f"{greeting} How are you today?"
def finalize_response(ctx: task.ActivityContext, response: str) -> str:
"""Third activity that finalizes the response."""
return f"{response} I hope you're doing well!"
A vezénylőkkel ellentétben a tevékenységek I/O-műveleteket hajthatnak végre, például HTTP-hívásokat, adatbázis-lekérdezéseket és fájlhozzáférést. A bemenet közvetlenül paraméterként lesz átadva.
Ez a minta .NET, JavaScript, Java és Python esetében jelenik meg.
A Java tevékenységei a TaskActivityFactory használatával vannak definiálva:
import com.microsoft.durabletask.TaskActivity;
import com.microsoft.durabletask.TaskActivityFactory;
.addActivity(new TaskActivityFactory() {
@Override
public String getName() { return "Reverse"; }
@Override
public TaskActivity create() {
return ctx -> {
String input = ctx.getInput(String.class);
StringBuilder builder = new StringBuilder(input);
builder.reverse();
return builder.toString();
};
}
})
.addActivity(new TaskActivityFactory() {
@Override
public String getName() { return "Capitalize"; }
@Override
public TaskActivity create() {
return ctx -> ctx.getInput(String.class).toUpperCase();
}
})
.addActivity(new TaskActivityFactory() {
@Override
public String getName() { return "ReplaceWhitespace"; }
@Override
public TaskActivity create() {
return ctx -> {
String input = ctx.getInput(String.class);
return input.trim().replaceAll("\\s", "-");
};
}
})
Minden tevékenységet regisztráljon a dolgozó építővel a addActivity használatával. A tevékenységek I/O-műveleteket hajthatnak végre, és eredményeket adhatnak vissza a vezénylőnek.
Ü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.
V3 programozási modell
HttpStart/function.json
{
"bindings": [
{
"authLevel": "anonymous",
"name": "req",
"type": "httpTrigger",
"direction": "in",
"route": "orchestrators/{functionName}",
"methods": ["post"]
},
{
"name": "$return",
"type": "http",
"direction": "out"
},
{
"name": "starter",
"type": "orchestrationClient",
"direction": "in"
}
],
"disabled": false
}
A vezénylőkkel való interakcióhoz adjon hozzá egy bemeneti kötést durableClient .
HttpStart/index.js
const df = require("durable-functions");
module.exports = async function (context, req) {
const client = df.getClient(context);
const instanceId = await client.startNew(req.params.functionName, undefined, req.body);
context.log(`Started orchestration with ID = '${instanceId}'.`);
return client.createCheckStatusResponse(context.bindingData.req, instanceId);
};
A df.getClient objektum lekéréséhez használja a DurableOrchestrationClient-t. 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.
V4 programozási modell
const df = require("durable-functions");
const { app } = require("@azure/functions");
app.http("httpStart", {
route: "orchestrators/{orchestratorName}",
extraInputs: [df.input.durableClient()],
handler: async (request, context) => {
const client = df.getClient(context);
const body = await request.json();
const instanceId = await client.startNew(request.params.orchestratorName, { input: body });
context.log(`Started orchestration with ID = '${instanceId}'.`);
return client.createCheckStatusResponse(request, instanceId);
},
});
Az orchestrátorok kezeléséhez és interakcióba lépéséhez adjon hozzá egy durableClient bemeneti kötést. A függvény regisztrálásakor adja meg a extraInputs kötést az argumentumban. Kérje le a durableClient bemenetet a hívással df.input.durableClient().
A df.getClient objektum lekéréséhez használja a DurableClient-t. 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.
HttpStart/function.json
{
"scriptFile": "__init__.py",
"bindings": [
{
"authLevel": "anonymous",
"name": "req",
"type": "httpTrigger",
"direction": "in",
"route": "orchestrators/{functionName}",
"methods": [
"post",
"get"
]
},
{
"name": "$return",
"type": "http",
"direction": "out"
},
{
"name": "starter",
"type": "durableClient",
"direction": "in"
}
]
}
A vezénylőkkel való interakcióhoz a függvénynek tartalmaznia kell egy bemeneti kötést durableClient .
HttpStart/__init__.py
import logging
import azure.functions as func
import azure.durable_functions as df
async def main(req: func.HttpRequest, starter: str) -> func.HttpResponse:
client = df.DurableOrchestrationClient(starter)
instance_id = await client.start_new(req.route_params["functionName"], None, None)
logging.info(f"Started orchestration with ID = '{instance_id}'.")
return client.create_check_status_response(req, instance_id)
A DurableOrchestrationClient konstruktor használatával hozzon létre egy Durable Functions-ügyfelet. 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.
Hamarosan megjelenik a PowerShell-minta.
Hamarosan jön a Java példa.
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ó.
import {
DurableTaskAzureManagedClientBuilder,
} from "@microsoft/durabletask-js-azuremanaged";
const connectionString =
process.env.DURABLE_TASK_SCHEDULER_CONNECTION_STRING ||
"Endpoint=http://localhost:8080;Authentication=None;TaskHub=default";
const client = new DurableTaskAzureManagedClientBuilder()
.connectionString(connectionString)
.build();
// Schedule a new orchestration instance
const instanceId = await client.scheduleNewOrchestration(greetingOrchestrator, "World");
console.log(`Started orchestration with ID: ${instanceId}`);
// Wait for the orchestration to complete
const state = await client.waitForOrchestrationCompletion(instanceId, true, 30);
console.log(`Orchestration completed with result: ${state?.serializedOutput}`);
Hozza létre a DurableTaskAzureManagedClientBuilder a Durable Task Scheduler kapcsolati karakterlánc használatával. Az scheduleNewOrchestration vezénylés indítására, és waitForOrchestrationCompletion a befejezésre való várakozásra használható.
from durabletask.azuremanaged.client import DurableTaskSchedulerClient
# Create the client
client = DurableTaskSchedulerClient(
host_address=endpoint,
secure_channel=endpoint != "http://localhost:8080",
taskhub=taskhub_name,
token_credential=credential
)
# Schedule a new orchestration instance
instance_id = client.schedule_new_orchestration(
function_chaining_orchestrator,
input="World"
)
print(f"Started orchestration with ID: {instance_id}")
# Wait for the orchestration to complete
result = client.wait_for_orchestration_completion(instance_id, timeout=60)
if result and result.runtime_status == "COMPLETED":
print(f"Orchestration completed with result: {result.serialized_output}")
A DurableTaskSchedulerClient tartós feladatütemezőhöz csatlakozik. Az schedule_new_orchestration vezénylés indítására, és wait_for_orchestration_completion a befejezésre való várakozásra használható.
Ez a minta .NET, JavaScript, Java és Python esetében jelenik meg.
import java.time.Duration;
import com.microsoft.durabletask.DurableTaskClient;
import com.microsoft.durabletask.NewOrchestrationInstanceOptions;
import com.microsoft.durabletask.OrchestrationMetadata;
import com.microsoft.durabletask.azuremanaged.DurableTaskSchedulerClientExtensions;
// Create the client
DurableTaskClient client = DurableTaskSchedulerClientExtensions
.createClientBuilder(connectionString)
.build();
// Schedule a new orchestration instance
String instanceId = client.scheduleNewOrchestrationInstance(
"ActivityChaining",
new NewOrchestrationInstanceOptions().setInput("Hello, world!"));
System.out.println("Started orchestration with ID: " + instanceId);
// Wait for the orchestration to complete
OrchestrationMetadata result = client.waitForInstanceCompletion(
instanceId,
Duration.ofSeconds(30),
true);
System.out.println("Orchestration completed with result: " + result.readOutputAs(String.class));
Hozza létre a DurableTaskClient egy kapcsolati karakterlánc használatával. Az scheduleNewOrchestrationInstance vezénylés indítására, és waitForInstanceCompletion 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:
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
Indítsa el a feldolgozót a vezénylő és a tevékenységek regisztrálásához.
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.