From ba08d97b38262e4aa9b23f20a688944549501dda Mon Sep 17 00:00:00 2001 From: Sipke Schoorstra Date: Sat, 15 Mar 2025 20:01:02 +0100 Subject: [PATCH 1/2] Refactor activity execution state handling with IDisposable Introduce `EnterExecution` method to manage activity execution state using a `using` block for cleaner and safer resource handling. Removed manual flags for tracking execution state, streamlining workflow logic and improving maintainability. --- .../Contexts/ActivityExecutionContext.cs | 5 +++++ .../Activities/DefaultActivityInvokerMiddleware.cs | 13 ++++--------- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/src/modules/Elsa.Workflows.Core/Contexts/ActivityExecutionContext.cs b/src/modules/Elsa.Workflows.Core/Contexts/ActivityExecutionContext.cs index ceae56077..c57964cc7 100644 --- a/src/modules/Elsa.Workflows.Core/Contexts/ActivityExecutionContext.cs +++ b/src/modules/Elsa.Workflows.Core/Contexts/ActivityExecutionContext.cs @@ -177,6 +177,11 @@ public partial class ActivityExecutionContext : IExecutionContext, IDisposable } } + public IDisposable EnterExecution() + { + return new WorkflowExecutionState(this); + } + /// /// Sets the current status of the activity. /// diff --git a/src/modules/Elsa.Workflows.Core/Middleware/Activities/DefaultActivityInvokerMiddleware.cs b/src/modules/Elsa.Workflows.Core/Middleware/Activities/DefaultActivityInvokerMiddleware.cs index 0912b677e..ca430fb5f 100644 --- a/src/modules/Elsa.Workflows.Core/Middleware/Activities/DefaultActivityInvokerMiddleware.cs +++ b/src/modules/Elsa.Workflows.Core/Middleware/Activities/DefaultActivityInvokerMiddleware.cs @@ -48,10 +48,9 @@ public class DefaultActivityInvokerMiddleware(ActivityMiddlewareDelegate next, I context.AddExecutionLogEntry("Precondition Failed", "Cannot execute at this time"); return; } - + // Mark workflow and activity as executing. - context.WorkflowExecutionContext.IsExecuting = true; - context.IsExecuting = true; + using var executionState = context.EnterExecution(); // Conditionally commit the workflow state. if (ShouldCommit(context, ActivityLifetimeEvent.ActivityExecuting)) @@ -87,10 +86,6 @@ public class DefaultActivityInvokerMiddleware(ActivityMiddlewareDelegate next, I workflowExecutionContext.Bookmarks.AddRange(context.Bookmarks); logger.LogDebug("Added {BookmarkCount} bookmarks to the workflow execution context", context.Bookmarks.Count); } - - // Mark activity as executed. - context.IsExecuting = false; - context.WorkflowExecutionContext.IsExecuting = false; // Conditionally commit the workflow state. if (ShouldCommit(context, ActivityLifetimeEvent.ActivityExecuted)) @@ -151,8 +146,8 @@ public class DefaultActivityInvokerMiddleware(ActivityMiddlewareDelegate next, I { var workflowStrategyName = context.WorkflowExecutionContext.Workflow.Options.CommitStrategyName; var workflowStrategy = string.IsNullOrWhiteSpace(workflowStrategyName) ? null : commitStrategyRegistry.FindWorkflowStrategy(workflowStrategyName); - - if(workflowStrategy == null) + + if (workflowStrategy == null) return false; var workflowLifetimeEvent = lifetimeEvent == ActivityLifetimeEvent.ActivityExecuting ? WorkflowLifetimeEvent.ActivityExecuting : WorkflowLifetimeEvent.ActivityExecuted; From fe65476bf2d7d2119ddaf6e8ce185adbed550d62 Mon Sep 17 00:00:00 2001 From: Sipke Schoorstra Date: Sat, 15 Mar 2025 20:03:22 +0100 Subject: [PATCH 2/2] Add WorkflowExecutionState to manage execution context state Introduce `WorkflowExecutionState` to encapsulate execution state changes for workflows. This ensures proper handling of execution flags during the lifetime of the state object and resets them upon disposal. --- .../Models/WorkflowExecutionState.cs | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 src/modules/Elsa.Workflows.Core/Models/WorkflowExecutionState.cs diff --git a/src/modules/Elsa.Workflows.Core/Models/WorkflowExecutionState.cs b/src/modules/Elsa.Workflows.Core/Models/WorkflowExecutionState.cs new file mode 100644 index 000000000..1d8e48dad --- /dev/null +++ b/src/modules/Elsa.Workflows.Core/Models/WorkflowExecutionState.cs @@ -0,0 +1,17 @@ +namespace Elsa.Workflows; + +internal class WorkflowExecutionState : IDisposable +{ + private readonly ActivityExecutionContext _activityExecutionContext; + + public WorkflowExecutionState(ActivityExecutionContext activityExecutionContext) + { + _activityExecutionContext = activityExecutionContext; + _activityExecutionContext.IsExecuting = activityExecutionContext.WorkflowExecutionContext.IsExecuting = true; + } + + public void Dispose() + { + _activityExecutionContext.IsExecuting = _activityExecutionContext.WorkflowExecutionContext.IsExecuting = false; + } +} \ No newline at end of file