diff --git a/src/apps/Elsa.Server.Web/Elsa.Server.Web.csproj b/src/apps/Elsa.Server.Web/Elsa.Server.Web.csproj index c0537447d..6fa3939e8 100644 --- a/src/apps/Elsa.Server.Web/Elsa.Server.Web.csproj +++ b/src/apps/Elsa.Server.Web/Elsa.Server.Web.csproj @@ -7,6 +7,7 @@ + diff --git a/src/apps/Elsa.Server.Web/Program.cs b/src/apps/Elsa.Server.Web/Program.cs index 69e723bbb..71ef18012 100644 --- a/src/apps/Elsa.Server.Web/Program.cs +++ b/src/apps/Elsa.Server.Web/Program.cs @@ -17,6 +17,7 @@ using Elsa.Workflows.CommitStates.Strategies; using Elsa.Workflows.IncidentStrategies; using Elsa.Workflows.LogPersistence; using Elsa.Workflows.Options; +using Elsa.Workflows.Runtime.Distributed.Extensions; using Elsa.Workflows.Runtime.Options; using Elsa.Workflows.Runtime.Tasks; using JetBrains.Annotations; @@ -70,6 +71,7 @@ services { runtime.UseEntityFrameworkCore(ef => ef.UseSqlite()); runtime.UseCache(); + runtime.UseDistributedRuntime(); }) .UseWorkflowsApi() .UseScheduling() diff --git a/src/apps/Elsa.Server.Web/appsettings.json b/src/apps/Elsa.Server.Web/appsettings.json index b0bd725e6..f7456f2df 100644 --- a/src/apps/Elsa.Server.Web/appsettings.json +++ b/src/apps/Elsa.Server.Web/appsettings.json @@ -2,7 +2,8 @@ "Logging": { "LogLevel": { "Default": "Warning", - "Microsoft.Hosting.Lifetime": "Information" + "Microsoft.Hosting.Lifetime": "Information", + "Elsa": "Debug" } }, "HostBuilder": { diff --git a/src/common/Elsa.Testing.Shared.Component/Activities/TriggerSignal.cs b/src/common/Elsa.Testing.Shared.Component/Activities/TriggerSignal.cs index 78fd7c47c..e3e9b3ca9 100644 --- a/src/common/Elsa.Testing.Shared.Component/Activities/TriggerSignal.cs +++ b/src/common/Elsa.Testing.Shared.Component/Activities/TriggerSignal.cs @@ -4,9 +4,9 @@ using Elsa.Workflows.Runtime; namespace Elsa.Testing.Shared.Activities; -public class TriggerSignal(object signal) : CodeActivity +public class TriggerSignal(string signal) : CodeActivity { - public object Signal { get; set; } = signal; + public string Signal { get; set; } = signal; protected override void Execute(ActivityExecutionContext context) { diff --git a/test/component/Elsa.Workflows.ComponentTests/Helpers/Models/TestWorkflowExecutionResult.cs b/src/common/Elsa.Testing.Shared.Component/Models/TestWorkflowExecutionResult.cs similarity index 90% rename from test/component/Elsa.Workflows.ComponentTests/Helpers/Models/TestWorkflowExecutionResult.cs rename to src/common/Elsa.Testing.Shared.Component/Models/TestWorkflowExecutionResult.cs index 5db0f9ef8..12ccb0f33 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Helpers/Models/TestWorkflowExecutionResult.cs +++ b/src/common/Elsa.Testing.Shared.Component/Models/TestWorkflowExecutionResult.cs @@ -1,6 +1,7 @@ +using Elsa.Workflows; using Elsa.Workflows.Runtime.Entities; -namespace Elsa.Workflows.ComponentTests.Models; +namespace Elsa.Testing.Shared.Models; /// /// Represents the result of a test workflow execution, including the workflow execution context and activity execution records. diff --git a/test/component/Elsa.Workflows.ComponentTests/Helpers/Services/AsyncWorkflowRunner.cs b/src/common/Elsa.Testing.Shared.Component/Services/AsyncWorkflowRunner.cs similarity index 95% rename from test/component/Elsa.Workflows.ComponentTests/Helpers/Services/AsyncWorkflowRunner.cs rename to src/common/Elsa.Testing.Shared.Component/Services/AsyncWorkflowRunner.cs index 8fb09b3a7..39f79c2b6 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Helpers/Services/AsyncWorkflowRunner.cs +++ b/src/common/Elsa.Testing.Shared.Component/Services/AsyncWorkflowRunner.cs @@ -1,13 +1,12 @@ -using Elsa.Testing.Shared; -using Elsa.Testing.Shared.Services; -using Elsa.Workflows.ComponentTests.Models; +using System.Collections.Concurrent; +using Elsa.Testing.Shared.Models; +using Elsa.Workflows; using Elsa.Workflows.Models; using Elsa.Workflows.Runtime; using Elsa.Workflows.Runtime.Entities; using Elsa.Workflows.Runtime.Messages; -using System.Collections.Concurrent; -namespace Elsa.Workflows.ComponentTests.Services; +namespace Elsa.Testing.Shared.Services; /// /// Provides functionality to execute workflows asynchronously and await their completion for testing purposes. diff --git a/src/modules/Elsa.Workflows.Management/Contracts/IWorkflowInstanceVariableManager.cs b/src/modules/Elsa.Workflows.Management/Contracts/IWorkflowInstanceVariableManager.cs index 440288489..b1ad89ecd 100644 --- a/src/modules/Elsa.Workflows.Management/Contracts/IWorkflowInstanceVariableManager.cs +++ b/src/modules/Elsa.Workflows.Management/Contracts/IWorkflowInstanceVariableManager.cs @@ -1,5 +1,11 @@ +using Elsa.Workflows.Management.Entities; +using Elsa.Workflows.State; + namespace Elsa.Workflows.Management; +/// +/// Defines the operations for managing variables associated with a workflow instance. +/// public interface IWorkflowInstanceVariableManager { /// @@ -8,8 +14,26 @@ public interface IWorkflowInstanceVariableManager /// The ID of the workflow instance. /// /// The cancellation token to cancel the operation. - /// A task that represents the asynchronous operation. The task result contains a collection of instances. - Task> GetVariablesAsync(string workflowInstanceId, IEnumerable? excludeTags = default, CancellationToken cancellationToken = default); + /// A collection of instances. + Task> GetVariablesAsync(string workflowInstanceId, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default); + + /// + /// Retrieves all variables for the specified workflow instance. + /// + /// The workflow instance from which to retrieve variables. + /// A collection of tags to exclude from the variable results, if any. + /// The cancellation token to cancel the operation. + /// A collection of instances. + Task> GetVariablesAsync(WorkflowInstance workflowInstance, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default); + + /// + /// Retrieves all variables for the specified workflow state. + /// + /// The workflow state to retrieve variables from. + /// Optional tags to exclude from the result. + /// The cancellation token to cancel the operation. + /// A collection of instances. + Task> GetVariablesAsync(WorkflowState workflowState, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default); /// /// Retrieves all variables from the specified . @@ -17,8 +41,8 @@ public interface IWorkflowInstanceVariableManager /// The context of the workflow execution. /// /// The cancellation token to cancel the operation. - /// A task that represents the asynchronous operation. The task result contains a collection of instances. - Task> GetVariablesAsync(WorkflowExecutionContext workflowExecutionContext, IEnumerable? excludeTags = default, CancellationToken cancellationToken = default); + /// A collection of instances. + Task> GetVariablesAsync(WorkflowExecutionContext workflowExecutionContext, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default); /// /// Sets the specified variables in the specified workflow instance. diff --git a/src/modules/Elsa.Workflows.Management/Services/WorkflowInstanceVariableManager.cs b/src/modules/Elsa.Workflows.Management/Services/WorkflowInstanceVariableManager.cs index 69fb2fb27..23552c877 100644 --- a/src/modules/Elsa.Workflows.Management/Services/WorkflowInstanceVariableManager.cs +++ b/src/modules/Elsa.Workflows.Management/Services/WorkflowInstanceVariableManager.cs @@ -1,24 +1,39 @@ +using Elsa.Workflows.Management.Entities; +using Elsa.Workflows.State; + namespace Elsa.Workflows.Management.Services; public class WorkflowInstanceVariableManager( - IWorkflowInstanceManager workflowInstanceManager, - IWorkflowDefinitionService workflowDefinitionService, - IServiceProvider serviceProvider, + IWorkflowInstanceManager workflowInstanceManager, + IWorkflowDefinitionService workflowDefinitionService, + IServiceProvider serviceProvider, IWorkflowInstanceVariableReader variableReader, IWorkflowInstanceVariableWriter variableWriter) : IWorkflowInstanceVariableManager { - public async Task> GetVariablesAsync(string workflowInstanceId, IEnumerable? excludeTags = default, CancellationToken cancellationToken = default) + public async Task> GetVariablesAsync(string workflowInstanceId, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default) { var workflowExecutionContext = await GetWorkflowExecutionContextAsync(workflowInstanceId, cancellationToken); if (workflowExecutionContext == null) return []; return await variableReader.GetVariables(workflowExecutionContext, excludeTags, cancellationToken); } - public Task> GetVariablesAsync(WorkflowExecutionContext workflowExecutionContext, IEnumerable? excludeTags = default, CancellationToken cancellationToken = default) + public Task> GetVariablesAsync(WorkflowExecutionContext workflowExecutionContext, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default) { return variableReader.GetVariables(workflowExecutionContext, excludeTags, cancellationToken); } + public async Task> GetVariablesAsync(WorkflowInstance workflowInstance, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default) + { + return await GetVariablesAsync(workflowInstance.WorkflowState, excludeTags, cancellationToken); + } + + public async Task> GetVariablesAsync(WorkflowState workflowState, IEnumerable? excludeTags = null, CancellationToken cancellationToken = default) + { + var workflowExecutionContext = await GetWorkflowExecutionContextAsync(workflowState, cancellationToken); + if (workflowExecutionContext == null) return []; + return await variableReader.GetVariables(workflowExecutionContext, excludeTags, cancellationToken); + } + public async Task> SetVariablesAsync(string workflowInstanceId, IEnumerable variables, CancellationToken cancellationToken = default) { var workflowExecutionContext = await GetWorkflowExecutionContextAsync(workflowInstanceId, cancellationToken); @@ -32,20 +47,26 @@ public class WorkflowInstanceVariableManager( { return variableWriter.SetVariables(workflowExecutionContext, variables, cancellationToken); } - + private async Task GetWorkflowExecutionContextAsync(string workflowInstanceId, CancellationToken cancellationToken) { var workflowInstance = await workflowInstanceManager.FindByIdAsync(workflowInstanceId, cancellationToken); if (workflowInstance == null) return null; - + var workflowState = workflowInstance.WorkflowState; + + return await GetWorkflowExecutionContextAsync(workflowState, cancellationToken); + } + + private async Task GetWorkflowExecutionContextAsync(WorkflowState workflowState, CancellationToken cancellationToken) + { var workflowGraph = await workflowDefinitionService.FindWorkflowGraphAsync(workflowState.DefinitionVersionId, cancellationToken); - + if (workflowGraph == null) return null; - + return await WorkflowExecutionContext.CreateAsync( serviceProvider, workflowGraph, diff --git a/src/modules/Elsa.Workflows.Runtime/Providers/ClrWorkflowsProvider.cs b/src/modules/Elsa.Workflows.Runtime/Providers/ClrWorkflowsProvider.cs index e76ffb413..1f5eda689 100644 --- a/src/modules/Elsa.Workflows.Runtime/Providers/ClrWorkflowsProvider.cs +++ b/src/modules/Elsa.Workflows.Runtime/Providers/ClrWorkflowsProvider.cs @@ -51,6 +51,6 @@ public class ClrWorkflowsProvider( }; var materializerContext = new ClrWorkflowMaterializerContext(workflowBuilder.GetType()); - return new MaterializedWorkflow(workflow, Name, ClrWorkflowMaterializer.MaterializerName, materializerContext); + return new(workflow, Name, ClrWorkflowMaterializer.MaterializerName, materializerContext); } } \ No newline at end of file diff --git a/test/component/Elsa.Workflows.ComponentTests/Helpers/Fixtures/WorkflowServer.cs b/test/component/Elsa.Workflows.ComponentTests/Helpers/Fixtures/WorkflowServer.cs index 44b321da3..aeae8967e 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Helpers/Fixtures/WorkflowServer.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Helpers/Fixtures/WorkflowServer.cs @@ -12,7 +12,6 @@ using Elsa.Testing.Shared.Handlers; using Elsa.Testing.Shared.Services; using Elsa.Workflows.ComponentTests.Decorators; using Elsa.Workflows.ComponentTests.Materializers; -using Elsa.Workflows.ComponentTests.Services; using Elsa.Workflows.ComponentTests.WorkflowProviders; using Elsa.Workflows.Management; using Elsa.Workflows.Runtime.Distributed.Extensions; diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs new file mode 100644 index 000000000..de37ed7c7 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs @@ -0,0 +1,177 @@ +using Elsa.Common.Models; +using Elsa.Testing.Shared; +using Elsa.Testing.Shared.Models; +using Elsa.Testing.Shared.Services; +using Elsa.Workflows.Activities; +using Elsa.Workflows.ComponentTests.Abstractions; +using Elsa.Workflows.ComponentTests.Fixtures; +using Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; +using Elsa.Workflows.Management; +using Elsa.Workflows.Models; +using Microsoft.Extensions.DependencyInjection; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows; + +public class BulkDispatchWorkflowsTests : AppComponentTest +{ + private readonly AsyncWorkflowRunner _workflowRunner; + + public BulkDispatchWorkflowsTests(App app) : base(app) + { + _workflowRunner = Scope.ServiceProvider.GetRequiredService(); + } + + [Fact(DisplayName = "BulkDispatchWorkflows should wait for all child workflows to complete")] + public async Task BulkDispatchAndWait_ShouldWaitForAllChildWorkflowsToComplete() + { + var result = await RunWorkflowAsync(BulkDispatchAndWaitWorkflow.DefinitionId); + + var writeLineExecutionRecords = result.ActivityExecutionRecords.Where(x => x.ActivityType == "Elsa.WriteLine").ToList(); + Assert.Equal(4, writeLineExecutionRecords.Count); + } + + [Fact(DisplayName = "BulkDispatchWorkflows should dispatch and not wait when WaitForCompletion is false")] + public async Task BulkDispatchFireAndForget_ShouldNotWaitForChildWorkflows() + { + var expectedChildCount = 3; + + // Run the main workflow and wait for child workflows to complete + var (result, completedChildWorkflows) = await RunWorkflowAndWaitForChildWorkflowsAsync( + BulkDispatchFireAndForgetWorkflow.DefinitionId, + SlowBulkChildWorkflow.DefinitionId, + expectedChildCount); + + AssertWorkflowFinished(result); + var mainWorkflowCompletedAt = result.WorkflowExecutionContext.UpdatedAt; + + // Assert that all child workflows completed after the main workflow + Assert.Equal(expectedChildCount, completedChildWorkflows.Count); + foreach (var childContext in completedChildWorkflows) + { + Assert.True(childContext.UpdatedAt > mainWorkflowCompletedAt, + $"Child workflow should complete after main workflow. Main: {mainWorkflowCompletedAt}, Child: {childContext.UpdatedAt}"); + } + } + + [Fact(DisplayName = "BulkDispatchWorkflows should use CorrelationIdFunction")] + public async Task BulkDispatchWithCorrelationId_ShouldUseCorrelationIdFunction() + { + var expectedChildCount = 3; + + // Run the main workflow and wait for child workflows to complete + var (result, completedChildWorkflows) = await RunWorkflowAndWaitForChildWorkflowsAsync( + BulkDispatchWithCorrelationIdWorkflow.DefinitionId, + BulkChildWorkflow.DefinitionId, + expectedChildCount); + + AssertWorkflowFinished(result); + + // Assert that all child workflows have the expected correlation IDs based on the CorrelationIdFunction + Assert.Equal(expectedChildCount, completedChildWorkflows.Count); + + var expectedCorrelationIds = new[] { "correlation-1", "correlation-2", "correlation-3" }; + var actualCorrelationIds = completedChildWorkflows.Select(c => c.CorrelationId).OrderBy(c => c).ToList(); + + Assert.Equal(expectedCorrelationIds, actualCorrelationIds); + } + + [Fact(DisplayName = "BulkDispatchWorkflows should execute ChildFaulted ports")] + public async Task BulkDispatchWithChildPorts_ShouldExecuteChildFaultedPortForFaultedWorkflows() + { + var result = await RunWorkflowAsync(BulkDispatchWithChildPortsWorkflow.DefinitionId); + AssertWorkflowFinished(result); + + var faultedCount = await GetWorkflowVariableAsync(result, "FaultedCount"); + Assert.Equal(3, faultedCount); + } + + [Fact(DisplayName = "BulkDispatchWorkflows should complete immediately when Items is empty")] + public async Task BulkDispatchWithEmptyItems_ShouldCompleteImmediately() + { + var result = await RunWorkflowAsync(BulkDispatchEmptyItemsWorkflow.DefinitionId); + AssertWorkflowFinished(result); + } + + [Fact(DisplayName = "BulkDispatchWorkflows should throw when workflow definition not found")] + public async Task BulkDispatchWithInvalidWorkflowDefinitionId_ShouldThrow() + { + var result = await RunWorkflowAsync(BulkDispatchInvalidDefinitionWorkflow.DefinitionId); + Assert.Equal(WorkflowSubStatus.Faulted, result.WorkflowExecutionContext.SubStatus); + } + + [Fact(DisplayName = "BulkDispatchWorkflows child workflows should receive current item")] + public async Task BulkDispatchWorkflows_ChildWorkflowsShouldReceiveCurrentItem() + { + var result = await RunWorkflowAsync(MixFruitsWorkflow.DefinitionId); + AssertWorkflowFinished(result); + + var writeLineExecutionRecords = result.ActivityExecutionRecords.Where(x => x.ActivityType == "Elsa.WriteLine").ToList(); + Assert.Equal(3, writeLineExecutionRecords.Count); + + var writtenTexts = writeLineExecutionRecords + .Select(x => x.ActivityState?[nameof(WriteLine.Text)] as string) + .ToList(); + + Assert.Contains("Mixing Apple", writtenTexts); + Assert.Contains("Mixing Banana", writtenTexts); + Assert.Contains("Mixing Cherry", writtenTexts); + } + + private Task RunWorkflowAsync(string workflowDefinitionId) + { + return _workflowRunner.RunAndAwaitWorkflowCompletionAsync(WorkflowDefinitionHandle.ByDefinitionId(workflowDefinitionId, VersionOptions.Published)); + } + + private static void AssertWorkflowFinished(TestWorkflowExecutionResult result) + { + Assert.Equal(WorkflowSubStatus.Finished, result.WorkflowExecutionContext.SubStatus); + } + + private async Task GetWorkflowVariableAsync(TestWorkflowExecutionResult result, string variableName) + { + var variableManager = Scope.ServiceProvider.GetRequiredService(); + var variables = await variableManager.GetVariablesAsync(result.WorkflowExecutionContext); + return (T?)variables.FirstOrDefault(v => v.Variable.Name == variableName)?.Value; + } + + private async Task<(TestWorkflowExecutionResult Result, List CompletedChildWorkflows)> RunWorkflowAndWaitForChildWorkflowsAsync( + string parentWorkflowDefinitionId, + string childWorkflowDefinitionId, + int expectedChildCount) + { + var workflowEvents = Scope.ServiceProvider.GetRequiredService(); + var completedChildWorkflows = new List(); + var childWorkflowCompletionTcs = new TaskCompletionSource(); + + // Subscribe to child workflow completion events + void OnWorkflowStateCommitted(object? sender, WorkflowStateCommittedEventArgs e) + { + if (e.WorkflowExecutionContext.Workflow.Identity.DefinitionId != childWorkflowDefinitionId || + e.WorkflowExecutionContext.Status != WorkflowStatus.Finished) + { + return; + } + + completedChildWorkflows.Add(e.WorkflowExecutionContext); + if (completedChildWorkflows.Count == expectedChildCount) + childWorkflowCompletionTcs.TrySetResult(); + } + + workflowEvents.WorkflowStateCommitted += OnWorkflowStateCommitted; + + try + { + // Run the main workflow + var result = await RunWorkflowAsync(parentWorkflowDefinitionId); + + // Wait for all child workflows to complete + await childWorkflowCompletionTcs.Task; + + return (result, completedChildWorkflows); + } + finally + { + workflowEvents.WorkflowStateCommitted -= OnWorkflowStateCommitted; + } + } +} \ No newline at end of file diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkChildWorkflow.cs similarity index 60% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkChildWorkflow.cs index 42d91876d..6734738f3 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkChildWorkflow.cs @@ -1,12 +1,11 @@ using Elsa.Extensions; using Elsa.Workflows.Activities; -using Elsa.Workflows.ComponentTests.Activities; using JetBrains.Annotations; -namespace Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; [UsedImplicitly] -public class FruitWorkflow : WorkflowBase +public class BulkChildWorkflow : WorkflowBase { public static readonly string DefinitionId = Guid.NewGuid().ToString(); @@ -14,13 +13,13 @@ public class FruitWorkflow : WorkflowBase { builder.WithDefinitionId(DefinitionId); var item = builder.WithInput("Item"); + builder.Root = new Sequence { Activities = { - new WriteLine(x => $"Mixing {x.GetInput(item)}"), - new TriggerSignal(x => x.GetInput(item)) + new WriteLine(context => $"Processing item: {context.GetInput(item)}") } }; } -} \ No newline at end of file +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchAndWaitWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchAndWaitWorkflow.cs new file mode 100644 index 000000000..07dc906bd --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchAndWaitWorkflow.cs @@ -0,0 +1,26 @@ +using Elsa.Workflows.Activities; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +public class BulkDispatchAndWaitWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + builder.Root = new Sequence + { + Activities = + { + new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(BulkChildWorkflow.DefinitionId), + Items = new(new object[] { 1, 2, 3 }), + WaitForCompletion = new(true) + }, + new WriteLine("Done") + } + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchEmptyItemsWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchEmptyItemsWorkflow.cs new file mode 100644 index 000000000..21ce9b79d --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchEmptyItemsWorkflow.cs @@ -0,0 +1,21 @@ +using JetBrains.Annotations; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +[UsedImplicitly] +public class BulkDispatchEmptyItemsWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = nameof(BulkDispatchEmptyItemsWorkflow); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + + builder.Root = new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(BulkChildWorkflow.DefinitionId), + Items = new(Array.Empty()), + WaitForCompletion = new(true) + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchFireAndForgetWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchFireAndForgetWorkflow.cs new file mode 100644 index 000000000..50e9a2692 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchFireAndForgetWorkflow.cs @@ -0,0 +1,17 @@ +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +public class BulkDispatchFireAndForgetWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + builder.Root = new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(SlowBulkChildWorkflow.DefinitionId), + Items = new(new object[] { "A", "B", "C" }), + WaitForCompletion = new(false) + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchInvalidDefinitionWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchInvalidDefinitionWorkflow.cs new file mode 100644 index 000000000..4a3a41be8 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchInvalidDefinitionWorkflow.cs @@ -0,0 +1,31 @@ +using Elsa.Workflows.Activities; +using Elsa.Workflows.IncidentStrategies; +using JetBrains.Annotations; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +[UsedImplicitly] +public class BulkDispatchInvalidDefinitionWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = nameof(BulkDispatchInvalidDefinitionWorkflow); + public static readonly string InvalidChildWorkflowId = "NonExistentWorkflow"; + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + builder.WorkflowOptions.IncidentStrategyType = typeof(FaultStrategy); + + builder.Root = new Sequence + { + Activities = + { + new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(InvalidChildWorkflowId), + Items = new(() => new object[] { 1 }), + WaitForCompletion = new(true) + } + } + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithChildPortsWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithChildPortsWorkflow.cs new file mode 100644 index 000000000..745c4ae58 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithChildPortsWorkflow.cs @@ -0,0 +1,46 @@ +using Elsa.Extensions; +using Elsa.Workflows.Activities; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +public class BulkDispatchWithChildPortsWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + + var completedCountVariable = builder.WithVariable("CompletedCount", 0).WithWorkflowStorage(); + var faultedCountVariable = builder.WithVariable("FaultedCount", 0).WithWorkflowStorage(); + + builder.Root = new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(FaultingChildWorkflow.DefinitionId), + Items = new(new object[] { 1, 2, 3 }), + WaitForCompletion = new(true), + ChildCompleted = new Sequence + { + Activities = + { + new SetVariable + { + Variable = completedCountVariable, + Value = new(context => completedCountVariable.Get(context) + 1) + } + } + }, + ChildFaulted = new Sequence + { + Activities = + { + new SetVariable + { + Variable = faultedCountVariable, + Value = new(context => faultedCountVariable.Get(context) + 1) + } + } + } + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithCorrelationIdWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithCorrelationIdWorkflow.cs new file mode 100644 index 000000000..db33aa478 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/BulkDispatchWithCorrelationIdWorkflow.cs @@ -0,0 +1,23 @@ +using Elsa.Expressions.JavaScript.Models; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +public class BulkDispatchWithCorrelationIdWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + + var items = new object[] { 1, 2, 3 }; + + builder.Root = new Runtime.Activities.BulkDispatchWorkflows + { + WorkflowDefinitionId = new(BulkChildWorkflow.DefinitionId), + Items = new(items), + CorrelationIdFunction = new(JavaScriptExpression.Create("`correlation-${getItem()}`")), + WaitForCompletion = new(true) + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs similarity index 86% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs index b72d8af6f..45a29434a 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/EmployeeGreetingWorkflow.cs @@ -2,7 +2,7 @@ using Elsa.Extensions; using Elsa.Workflows.Activities; using JetBrains.Annotations; -namespace Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; [UsedImplicitly] public class EmployeeGreetingWorkflow : WorkflowBase diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FaultingChildWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FaultingChildWorkflow.cs new file mode 100644 index 000000000..00c7f33a0 --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FaultingChildWorkflow.cs @@ -0,0 +1,28 @@ +using Elsa.Workflows.Activities; +using Elsa.Workflows.IncidentStrategies; +using JetBrains.Annotations; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +[UsedImplicitly] +public class FaultingChildWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + builder.WorkflowOptions.IncidentStrategyType = typeof(FaultStrategy); + + builder.Root = new Sequence + { + Activities = + { + new Fault + { + Message = new("Child workflow failed") + } + } + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs new file mode 100644 index 000000000..a19003d7b --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/FruitWorkflow.cs @@ -0,0 +1,18 @@ +using Elsa.Extensions; +using Elsa.Workflows.Activities; +using JetBrains.Annotations; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +[UsedImplicitly] +public class FruitWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + var item = builder.WithInput("Item"); + builder.Root = new WriteLine(x => $"Mixing {x.GetInput(item)}"); + } +} \ No newline at end of file diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs similarity index 91% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs index 10602f28f..74cf84e1a 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/GreetEmployeesWorkflow.cs @@ -1,7 +1,7 @@ using Elsa.Testing.Shared.Activities; using Elsa.Workflows.Activities; -namespace Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; public class GreetEmployeesWorkflow : WorkflowBase { diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs similarity index 88% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs index 6b4ed9fc3..2feef9ec0 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/MixFruitsWorkflow.cs @@ -1,6 +1,6 @@ using Elsa.Workflows.Activities; -namespace Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; public class MixFruitsWorkflow : WorkflowBase { diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/SlowBulkChildWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/SlowBulkChildWorkflow.cs new file mode 100644 index 000000000..2197cec7e --- /dev/null +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/BulkDispatchWorkflows/Workflows/SlowBulkChildWorkflow.cs @@ -0,0 +1,27 @@ +using Elsa.Extensions; +using Elsa.Scheduling.Activities; +using Elsa.Workflows.Activities; +using JetBrains.Annotations; + +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.BulkDispatchWorkflows.Workflows; + +[UsedImplicitly] +public class SlowBulkChildWorkflow : WorkflowBase +{ + public static readonly string DefinitionId = Guid.NewGuid().ToString(); + + protected override void Build(IWorkflowBuilder builder) + { + builder.WithDefinitionId(DefinitionId); + var item = builder.WithInput("Item"); + + builder.Root = new Sequence + { + Activities = + { + Delay.FromMilliseconds(10), + new WriteLine(context => $"Processing item: {context.GetInput(item)}") + } + }; + } +} diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/DispatchWorkflowsTests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/DispatchWorkflowsTests.cs similarity index 94% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/DispatchWorkflowsTests.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/DispatchWorkflowsTests.cs index 39edc2ad9..ed0ee76b7 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/DispatchWorkflowsTests.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/DispatchWorkflowsTests.cs @@ -3,7 +3,7 @@ using Elsa.Testing.Shared; using Elsa.Testing.Shared.Services; using Elsa.Workflows.ComponentTests.Abstractions; using Elsa.Workflows.ComponentTests.Fixtures; -using Elsa.Workflows.ComponentTests.Scenarios.DispatchWorkflows.Workflows; +using Elsa.Workflows.ComponentTests.Scenarios.Activities.DispatchWorkflows.Workflows; using Elsa.Workflows.Models; using Elsa.Workflows.Runtime; using Elsa.Workflows.Runtime.Messages; diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/ChildWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/ChildWorkflow.cs similarity index 86% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/ChildWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/ChildWorkflow.cs index 4cb55a868..29bb09ab4 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/ChildWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/ChildWorkflow.cs @@ -2,7 +2,7 @@ using Elsa.Scheduling.Activities; using Elsa.Workflows.Activities; using JetBrains.Annotations; -namespace Elsa.Workflows.ComponentTests.Scenarios.DispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.DispatchWorkflows.Workflows; [UsedImplicitly] public class ChildWorkflow : WorkflowBase diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs similarity index 88% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs index c51b85eb0..ece71edab 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/DispatchWorkflows/Workflows/DispatchAndWaitWorkflow.cs @@ -2,7 +2,7 @@ using Elsa.Testing.Shared.Activities; using Elsa.Workflows.Activities; using Elsa.Workflows.Runtime.Activities; -namespace Elsa.Workflows.ComponentTests.Scenarios.DispatchWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.DispatchWorkflows.Workflows; public class DispatchAndWaitWorkflow : WorkflowBase { diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/ExecuteWorkflowsTests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/ExecuteWorkflowsTests.cs similarity index 80% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/ExecuteWorkflowsTests.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/ExecuteWorkflowsTests.cs index c47025d46..87bd3e1a1 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/ExecuteWorkflowsTests.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/ExecuteWorkflowsTests.cs @@ -1,13 +1,13 @@ using Elsa.Common.Models; using Elsa.Workflows.ComponentTests.Abstractions; using Elsa.Workflows.ComponentTests.Fixtures; -using Elsa.Workflows.ComponentTests.Scenarios.ExecuteWorkflows.Workflows; +using Elsa.Workflows.ComponentTests.Scenarios.Activities.ExecuteWorkflows.Workflows; using Elsa.Workflows.Models; using Elsa.Workflows.Runtime; using Elsa.Workflows.Runtime.Messages; using Microsoft.Extensions.DependencyInjection; -namespace Elsa.Workflows.ComponentTests.Scenarios.ExecuteWorkflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.ExecuteWorkflows; public class ExecuteWorkflowsTests : AppComponentTest { @@ -22,7 +22,7 @@ public class ExecuteWorkflowsTests : AppComponentTest public async Task ExecuteWorkflow_ShouldExecuteWorkflow() { var workflowClient = await _workflowRuntime.CreateClientAsync(); - await workflowClient.CreateInstanceAsync(new CreateWorkflowInstanceRequest + await workflowClient.CreateInstanceAsync(new() { WorkflowDefinitionHandle = WorkflowDefinitionHandle.ByDefinitionId(MainWorkflow.DefinitionId, VersionOptions.Published) }); diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/MainWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/MainWorkflow.cs similarity index 92% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/MainWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/MainWorkflow.cs index 754fb81df..b9ea5a22f 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/MainWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/MainWorkflow.cs @@ -3,7 +3,7 @@ using Elsa.Workflows.Activities; using Elsa.Workflows.Runtime; using Elsa.Workflows.Runtime.Activities; -namespace Elsa.Workflows.ComponentTests.Scenarios.ExecuteWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.ExecuteWorkflows.Workflows; public class MainWorkflow : WorkflowBase { diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs similarity index 91% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs index e685e2f3d..1e3eb9d93 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ExecuteWorkflows/Workflows/SubroutineWorkflow.cs @@ -3,7 +3,7 @@ using Elsa.Workflows.Activities; using Elsa.Workflows.Management.Activities.SetOutput; using JetBrains.Annotations; -namespace Elsa.Workflows.ComponentTests.Scenarios.ExecuteWorkflows.Workflows; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.ExecuteWorkflows.Workflows; [UsedImplicitly] public class SubroutineWorkflow : WorkflowBase diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Tests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Tests.cs similarity index 98% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Tests.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Tests.cs index 605e2da56..863e27f8a 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Tests.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Tests.cs @@ -2,7 +2,7 @@ using Elsa.Workflows.ComponentTests.Fixtures; using Microsoft.Extensions.DependencyInjection; -namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.FlowJoins; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.FlowJoin; public class Tests(App app) : AppComponentTest(app) { diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Workflows.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Workflows.cs similarity index 71% rename from test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Workflows.cs rename to test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Workflows.cs index a3750bb0d..29ff1ed5d 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoins/Workflows.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/FlowJoin/Workflows.cs @@ -1,16 +1,16 @@ using Elsa.Workflows.Activities.Flowchart.Activities; -namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.FlowJoins; +namespace Elsa.Workflows.ComponentTests.Scenarios.Activities.FlowJoin; public class SingleJoinWorkflow : WorkflowBase { protected override void Build(IWorkflowBuilder builder) { - builder.Root = new Elsa.Workflows.Activities.Flowchart.Activities.Flowchart + builder.Root = new Flowchart { Activities = { - new FlowJoin() + new Workflows.Activities.Flowchart.Activities.FlowJoin() } }; } diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ForEach/ForEachWorkflowTests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ForEach/ForEachWorkflowTests.cs index 3657edbb2..f8e67d079 100644 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ForEach/ForEachWorkflowTests.cs +++ b/test/component/Elsa.Workflows.ComponentTests/Scenarios/Activities/ForEach/ForEachWorkflowTests.cs @@ -1,8 +1,8 @@ using Elsa.Common.Models; +using Elsa.Testing.Shared.Services; using Elsa.Workflows.ComponentTests.Abstractions; using Elsa.Workflows.ComponentTests.Fixtures; using Elsa.Workflows.ComponentTests.Scenarios.Activities.ForEach.Workflows; -using Elsa.Workflows.ComponentTests.Services; using Elsa.Workflows.Models; using Microsoft.Extensions.DependencyInjection; diff --git a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs b/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs deleted file mode 100644 index f522ee010..000000000 --- a/test/component/Elsa.Workflows.ComponentTests/Scenarios/BulkDispatchWorkflows/BulkDispatchWorkflowsTests.cs +++ /dev/null @@ -1,56 +0,0 @@ -using Elsa.Common.Models; -using Elsa.Testing.Shared.Services; -using Elsa.Workflows.ComponentTests.Abstractions; -using Elsa.Workflows.ComponentTests.Fixtures; -using Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows.Workflows; -using Elsa.Workflows.Models; -using Elsa.Workflows.Runtime; -using Elsa.Workflows.Runtime.Messages; -using Microsoft.Extensions.DependencyInjection; - -namespace Elsa.Workflows.ComponentTests.Scenarios.BulkDispatchWorkflows; - -public class BulkDispatchWorkflowsTests : AppComponentTest -{ - private readonly SignalManager _signalManager; - private readonly IWorkflowRuntime _workflowRuntime; - - public BulkDispatchWorkflowsTests(App app) : base(app) - { - _workflowRuntime = Scope.ServiceProvider.GetRequiredService(); - _signalManager = Scope.ServiceProvider.GetRequiredService(); - } - - // /// - // /// Dispatches and waits for child workflows to complete. - // /// - // [Fact(Skip = "This test is flaky and needs to be fixed.")] - // public async Task DispatchAndWaitWorkflow_ShouldWaitForChildWorkflowToComplete() - // { - // var workflowClient = await _workflowRuntime.CreateClientAsync(); - // await workflowClient.CreateInstanceAsync(new CreateWorkflowInstanceRequest - // { - // WorkflowDefinitionHandle = WorkflowDefinitionHandle.ByDefinitionId(GreetEmployeesWorkflow.DefinitionId, VersionOptions.Published) - // }); - // await workflowClient.RunInstanceAsync(RunWorkflowInstanceRequest.Empty); - // await _signalManager.WaitAsync("Completed"); - // } - - /// - /// Individual items are sent as input to child workflows. - /// - [Fact] - public async Task DispatchWorkflows_ChildWorkflowsShouldReceiveCurrentItem() - { - var workflowClient = await _workflowRuntime.CreateClientAsync(); - var request = new CreateAndRunWorkflowInstanceRequest - { - WorkflowDefinitionHandle = WorkflowDefinitionHandle.ByDefinitionId(MixFruitsWorkflow.DefinitionId, VersionOptions.Published) - }; - await workflowClient.CreateAndRunInstanceAsync(request); - - await _signalManager.WaitAsync("Apple"); - await _signalManager.WaitAsync("Banana"); - await _signalManager.WaitAsync("Cherry"); - } -} \ No newline at end of file