Skip to Content
DocsClientsDotnetExternal TasksExternal Task Workers

External Task Workers

External Task Workers ermöglichen die Verarbeitung von External Tasks aus BPMN-Prozessen. Der .NET Client bietet zwei Ansätze: manuelle Verarbeitung und ASP.NET Core Hosting Integration.

Übersicht

Was sind External Tasks?

External Tasks sind BPMN Service Tasks mit type="external" Attribut. Sie ermöglichen die asynchrone Verarbeitung von Aufgaben durch externe Worker.

<bpmn:serviceTask id="Task_ProcessPayment" name="Process Payment"> <bpmn:extensionElements> <processcube:properties> <processcube:property name="module" value="ProcessPaymentWorker" /> </processcube:properties> </bpmn:extensionElements> </bpmn:serviceTask>

Schnellstart

Einfacher Worker

using ProcessCube.Engine; using ProcessCube.Engine.ExternalTaskWorkers; var engineAddress = "http://localhost:8000"; // Worker erstellen var worker = ExternalTaskWorkerBuilder .Create(engineAddress) .WithTopic("ProcessPayment") .UseHandlerMethod(async (externalTask) => { // Task-Payload auslesen var input = externalTask.Tokens[TokenType.OnEnter].GetPayload<PaymentInput>(); Console.WriteLine($"Processing payment: {input.PaymentId}"); // Geschäftslogik ausführen var result = await ProcessPaymentAsync(input); // Ergebnis zurückgeben return new PaymentResult( result.TransactionId, result.Status ); }) .Build(); // Worker starten await worker.StartAsync(); Console.WriteLine("Worker gestartet. Drücke Enter zum Beenden..."); Console.ReadLine(); // Worker stoppen await worker.StopAsync(); async Task<(string TransactionId, string Status)> ProcessPaymentAsync(PaymentInput input) { // Payment-Logik hier await Task.Delay(1000); return (Guid.NewGuid().ToString(), "Success"); } internal sealed record PaymentInput(string PaymentId, decimal Amount); internal sealed record PaymentResult(string TransactionId, string Status);

External Task Workers prüfen kontinuierlich (Polling) die Engine auf neue Tasks und verarbeiten diese automatisch.

Worker-Lifecycle

  1. Fetch: Worker fragt Engine nach verfügbaren External Tasks
  2. Lock: Task wird für den Worker reserviert (Lock Duration)
  3. Execute: Handler-Methode verarbeitet den Task
  4. Complete: Ergebnis wird an Engine zurückgeliefert
  5. Repeat: Worker fragt erneut nach Tasks

Worker-Settings

var worker = ExternalTaskWorkerBuilder .Create(engineAddress) .WithTopic("ProcessOrder") .WithSettings(settings => { settings.MaxParallelWorkerCount = 5; settings.LockDuration = TimeSpan.FromMinutes(2); settings.LongPollingDuration = TimeSpan.FromSeconds(30); settings.IdleBetweenFetchesDuration = TimeSpan.FromSeconds(5); }) .UseHandlerMethod(async (externalTask) => { // Handler-Logik return new { status = "completed" }; }) .Build();

Worker-Settings Parameter

ParameterDefaultBeschreibung
MaxParallelWorkerCount1Anzahl paralleler Task-Verarbeitungen
LockDuration100sZeit, die ein Task blockiert ist
LongPollingDuration30sWartezeit beim Polling
IdleBetweenFetchesDuration0sPause zwischen Polling-Zyklen
HasSensitivePayloadfalseUnterbindet Logging von Payloads

Mehrere Topics verarbeiten

var paymentWorker = ExternalTaskWorkerBuilder .Create(engineAddress) .WithTopic("ProcessPayment") .UseHandlerMethod(HandlePaymentAsync) .Build(); var shippingWorker = ExternalTaskWorkerBuilder .Create(engineAddress) .WithTopic("ArrangeShipping") .UseHandlerMethod(HandleShippingAsync) .Build(); // Beide Workers starten await Task.WhenAll( paymentWorker.StartAsync(), shippingWorker.StartAsync() );

Fehlerbehandlung

var worker = ExternalTaskWorkerBuilder .Create(engineAddress) .WithTopic("ProcessOrder") .UseHandlerMethod(async (externalTask) => { try { var input = externalTask.Tokens[TokenType.OnEnter].GetPayload<OrderInput>(); // Verarbeitung var result = await ProcessOrderAsync(input); return new OrderResult(result.OrderId, "Completed"); } catch (Exception ex) { Console.WriteLine($"Fehler bei Task-Verarbeitung: {ex.Message}"); // Exception wird automatisch an Engine gemeldet // Task wird als fehlgeschlagen markiert throw; } }) .Build();

Wenn der Handler eine Exception wirft, wird der External Task als fehlgeschlagen markiert und kann später wiederholt werden.

Mit Authentifizierung

using ProcessCube.Engine.Client.Identity; var identityProvider = new ClientCredentialsIdentityProvider( authorityAddress: "http://localhost:11235", clientId: "worker-service", clientSecret: "secret-key", scope: "engine_etw" ); var identity = await identityProvider.GetIdentityAsync(); var worker = ExternalTaskWorkerBuilder .Create(engineAddress, identity) .WithTopic("ProcessPayment") .UseHandlerMethod(HandlePaymentAsync) .Build(); await worker.StartAsync();

Nächste Schritte

Erkunden Sie die verschiedenen Ansätze zur Worker-Implementierung: