Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
Ewige Orchestrierungen sind Orchestratorfunktionen, die unbegrenzt ausgeführt werden, indem sie ihren eigenen Verlauf mithilfe der continue-as-new API regelmäßig zurücksetzen. Sie sind nützlich für Aggregatoren, regelmäßige Hintergrundaufträge und jedes Durable Functions-Szenario, das eine endlose Schleife ohne unbegrenztes Verlaufswachstum erfordert.
Ohne continue-as-new würde ein Orchestrator, der sich in einer Endlosschleife befindet, mit jeder geplanten Aufgabe den Orchestrierungsverlauf ansammeln, was schließlich Leistungsprobleme und eine übermäßige Nutzung des Arbeitsspeichers verursachen würde. Das ewige Orchestrierungsmuster löst dies, indem die Geschichte bei jeder Iteration zurückgesetzt wird.
Hinweis
Ewige Orchestrierungscodebeispiele sind für C#, JavaScript, Python und Java verfügbar. PowerShell unterstützt continue-as-newnicht .
In diesem Artikel:
- Wie "Continue-as-new" funktioniert – Der Mechanismus zum Zurücksetzen
- Überlegungen – Ausnahmeverhalten, unvollständige Aufgaben und externe Ereignisse
- Beispiel für periodische Arbeit – Eine Bereinigungsroutine, die Timer-Überlappungen verhindert
- Beginnen Sie eine ewige Orchestrierung – Start- und Singletonmuster
- Verlassen von einer ewigen Orchestrierung - sanftes Stoppen und Beenden
Ewige Orchestrierungen sind Orchestrierungen , die unbegrenzt ausgeführt werden, indem sie ihren eigenen Verlauf mithilfe der continue-as-new API regelmäßig zurücksetzen. Sie sind nützlich für Aggregatoren, regelmäßige Hintergrundaufträge und jedes Szenario, das eine endlose Schleife ohne ungebundenes Verlaufswachstum erfordert.
Ohne continue-as-new würde eine Orchestrierung, die sich endlos wiederholt, mit jedem geplanten Vorgang Verlauf ansammeln, was schließlich Leistungsprobleme und übermäßige Speichernutzung verursacht. Das ewige Orchestrierungsmuster löst dies, indem die Geschichte bei jeder Iteration zurückgesetzt wird.
Von Bedeutung
Derzeit ist das PowerShell Durable Task SDK nicht verfügbar.
In diesem Artikel:
- Funktionsweise von "Continue-as-new" – der Rücksetzmechanismus
- Überlegungen – Ausnahmeverhalten, unvollständige Aufgaben und externe Ereignisse
- Beispiel für regelmäßige Arbeit – Eine Bereinigungsschleife, die Zeitgeberüberlappungen verhindert
- Beginnen Sie eine ewige Orchestrierung – Start- und Singletonmuster
- Verlassen von einer anhaltenden Orchestrierung – sanftes Anhalten und vollständiges Beenden
Wie "Fortfahren als Neu" funktioniert
Anstatt Endlosschleifen zu verwenden, setzen Orchestratorfunktionen ihren Status zurück, indem sie die Methode continue-as-new in der Orchestrierungstriggerbindung aufrufen. Diese Methode verwendet einen JSON-serialisierbaren Parameter, der zur neuen Eingabe für die nächste Orchestratorfunktionsgenerierung wird.
Beim Aufrufen continue-as-newwird die Orchestrierungsinstanz mit dem neuen Eingabewert neu gestartet. Die gleiche Instanz-ID wird beibehalten, aber der Verlauf der Orchestratorfunktion wird zurückgesetzt.
Anstatt Endlosschleifen zu verwenden, setzen Orchestrierungen ihren Zustand zurück, indem sie die continue-as-new-Methode für den Orchestrierungskontext aufrufen. Diese Methode verwendet einen JSON-serialisierbaren Parameter, der zur neuen Eingabe für die nächste Orchestrierungsgenerierung wird.
Beim Aufrufen continue-as-newwird die Orchestrierungsinstanz mit dem neuen Eingabewert neu gestartet. Es wird dieselbe Instanz-ID beibehalten, aber der Verlauf der Orchestrierung wird zurückgesetzt.
Überlegungen zur ewigen Orchestrierung
Beachten Sie diese Überlegungen bei der Verwendung der continue-as-new Methode in einer Orchestrierung:
Wenn eine Orchestratorfunktion mithilfe der
continue-as-newMethode zurückgesetzt wird, verwaltet das Durable Task Framework dieselbe Instanz-ID, erstellt aber intern eine neue Ausführungs-ID und verwendet diese. Diese Ausführungs-ID wird nicht extern verfügbar gemacht, ist aber beim Debuggen der Orchestrierungsausführung hilfreich.Wenn während der Ausführung eine unbehandelte Ausnahme auftritt, tritt die Orchestrierung in einen fehlerhaften Zustand ein, und die Ausführung wird beendet. Ein Aufruf von
continue-as-newaus einemfinally-Block startet die Orchestrierung nach einer nicht abgefangenen Ausnahme nicht neu.Die Ergebnisse unvollständiger Aufgaben werden verworfen, wenn eine Orchestrierung
continue-as-newaufruft. Wenn beispielsweise ein Timer geplant ist und danncontinue-as-newaufgerufen wird, bevor der Timer ausgelöst wird, wird das Timer-Ereignis verworfen.Optionalerweise können Sie unverarbeitete externe Ereignisse über
continue-as-newNeustarts hinweg beibehalten. In C#ContinueAsNewbleiben unverarbeitete Ereignisse standardmäßig erhalten. In Java behältcontinueAsNewereignisse standardmäßig bei. In Python behältcontinue_as_newkeine Ereignisse bei, es sei denn,save_events=True. In JavaScript ist eincontinueAsNewParameter (saveEventsentwedertrueoderfalse) erforderlich, um dieses Verhalten zu steuern.
Beachten Sie diese Überlegungen bei der Verwendung der continue-as-new Methode in einer Orchestrierung:
Wenn eine Orchestrierung mit der
continue-as-new-Methode zurückgesetzt wird, behalten die Durable Task-SDKs dieselbe Instanz-ID bei, erstellen aber intern eine neue Ausführungs-ID. Diese Ausführungs-ID wird nicht extern verfügbar gemacht, kann aber beim Debuggen der Orchestrierungsausführung hilfreich sein.Wenn während der Ausführung eine unbehandelte Ausnahme auftritt, tritt die Orchestrierung in einen fehlerhaften Zustand ein, und die Ausführung wird beendet. Ein Aufruf
continue-as-newaus einemfinallyBlock heraus startet die Orchestrierung nach einer nicht abgefangenen Ausnahme nicht neu.Die Ergebnisse unvollständiger Aufgaben werden verworfen, wenn eine Orchestrierung
continue-as-newaufruft. Wenn beispielsweise ein Timer geplant ist und danncontinue-as-newaufgerufen wird, bevor der Timer ausgelöst wird, wird das Timer-Ereignis verworfen.Optionalerweise können Sie unverarbeitete externe Ereignisse über
continue-as-newNeustarts hinweg beibehalten. In .NET und Java behältcontinue-as-newstandardmäßig nicht verarbeitete Ereignisse bei. In Python behältcontinue_as_newkeine Ereignisse bei, es sei denn,save_events=True. In JavaScript ist eincontinueAsNewParameter (saveEventsentwedertrueoderfalse) erforderlich, um dieses Verhalten zu steuern. In allen Fällen werden unverarbeitete Ereignisse ausgeliefert, wenn die Orchestrierung das nächste MalwaitForExternalEventoderwait_for_external_eventaufruft.
Beispiel für regelmäßige Arbeit
Ein gängiger Anwendungsfall für dauerhafte Orchestrierungen ist periodische Hintergrundtätigkeiten, z. B. Bereinigungsaufträge.
Warum wird kein Timertrigger verwendet? Ein CRON-basierter Timertrigger wird zu festen Zeiten ausgeführt, unabhängig davon, ob die vorherige Ausführung abgeschlossen ist. Eine dauerhafte Orchestrierung wartet, bis die Arbeit abgeschlossen ist, bevor die nächste Iteration geplant wird, damit keine Überschneidungen auftreten.
| Approach | Zeitplan (1-Stunden-Intervall, 30-Minuten-Auftrag) | Überlappungsrisiko |
|---|---|---|
| Zeitgeber-Trigger (CRON) | 1:00, 2:00, 3:00 | Ja – wenn der Auftrag das Intervall überschreitet |
| Ewige Orchestrierung | 1:00, 2:30, 4:00 | Nein – nächste Ausführung wartet auf den Abschluss |
[FunctionName("Periodic_Cleanup_Loop")]
public static async Task Run(
[OrchestrationTrigger] IDurableOrchestrationContext context)
{
await context.CallActivityAsync("DoCleanup", null);
// sleep for one hour between cleanups
DateTime nextCleanup = context.CurrentUtcDateTime.AddHours(1);
await context.CreateTimer(nextCleanup, CancellationToken.None);
context.ContinueAsNew(null);
}
public class PeriodicCleanupLoop : TaskOrchestrator<object?, object?>
{
public override async Task<object?> RunAsync(TaskOrchestrationContext context, object? input)
{
await context.CallActivityAsync("DoCleanup");
// sleep for one hour between cleanups
await context.CreateTimer(TimeSpan.FromHours(1), CancellationToken.None);
context.ContinueAsNew(null);
return null;
}
}
Beginnen Sie einen ewigen Prozess der Orchestrierung
Verwenden Sie die Methode start-new oder schedule-new, um eine dauerhafte Orchestrierung wie jede andere Orchestrierungsfunktion zu starten. Um sicherzustellen, dass jeweils nur eine Instanz ausgeführt wird, verwenden Sie eine feste Instanz-ID. Weitere Informationen finden Sie unter Singleton-Orchestrierungen.
[FunctionName("Trigger_Eternal_Orchestration")]
public static async Task<HttpResponseMessage> OrchestrationTrigger(
[HttpTrigger(AuthorizationLevel.Function, "post", Route = null)] HttpRequestMessage request,
[DurableClient] IDurableOrchestrationClient client)
{
string instanceId = "StaticId";
await client.StartNewAsync("Periodic_Cleanup_Loop", instanceId);
return client.CreateCheckStatusResponse(request, instanceId);
}
Verwenden Sie die client-Methode 'schedule-new', um eine endlose Orchestrierung wie jede andere Orchestrierung zu starten. Um sicherzustellen, dass jeweils nur eine Instanz ausgeführt wird, verwenden Sie eine feste Instanz-ID. Weitere Informationen finden Sie unter Singleton-Orchestrierungen.
string instanceId = "StaticId";
await client.ScheduleNewOrchestrationInstanceAsync(
"PeriodicCleanupLoop",
null,
new StartOrchestrationOptions { InstanceId = instanceId });
Austritt aus einer ewigen Orchestrierung
Wenn eine Orchestratorfunktion schließlich abgeschlossen werden muss, rufen Sie continue-as-new nicht auf und lassen Sie die Funktion einfach enden.
Wenn sich eine Orchestratorfunktion in einer Endlosschleife befindet und beendet werden muss, verwenden Sie die Beendigungs-API der Orchestrierungsclientbindung, um sie zu beenden.
await client.TerminateAsync(instanceId, "Cleanup no longer needed");
Weitere Informationen finden Sie unter Instanzverwaltung.
Wenn eine Orchestrierung schließlich abgeschlossen werden muss, rufen Sie nicht continue-as-new auf und lassen Sie zu, dass die Orchestrierung beendet wird.
Wenn sich eine Orchestrierung in einer Endlosschleife befindet und beendet werden muss, verwenden Sie die Beenden-API auf dem Client für dauerhafte Aufgaben, um diese zu beenden.
await client.TerminateInstanceAsync(instanceId, "Cleanup no longer needed");