Remove Timesheet Approval Workflow sample

This commit is contained in:
Sipke Schoorstra 2020-10-23 14:23:45 +02:00
parent a0cf3d9d34
commit ef9c0e2f5d
20 changed files with 0 additions and 361 deletions

View file

@ -72,8 +72,6 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Elsa.Samples.HelloWorldHttp
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Elsa.Samples.CustomActivities", "src\samples\Elsa.Samples.CustomActivities\Elsa.Samples.CustomActivities.csproj", "{554C21D7-10BE-48E6-B0EF-9FCA43B32A0F}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Elsa.Samples.TimesheetApproval", "src\samples\Elsa.Samples.TimesheetApproval\Elsa.Samples.TimesheetApproval.csproj", "{1678743A-9095-4683-8DCD-5763F41924E2}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Elsa.DistributedLocking.Redis", "src\providers\Elsa.DistributedLocking.Redis\Elsa.DistributedLocking.Redis.csproj", "{EBD49CCA-5400-4C36-B5DF-7B28190AA323}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Elsa.Samples.DistributedLock", "src\samples\Elsa.Samples.DistributedLock\Elsa.Samples.DistributedLock.csproj", "{4D162E3C-0962-43B9-B193-6E806249F81B}"
@ -182,10 +180,6 @@ Global
{554C21D7-10BE-48E6-B0EF-9FCA43B32A0F}.Debug|Any CPU.Build.0 = Debug|Any CPU
{554C21D7-10BE-48E6-B0EF-9FCA43B32A0F}.Release|Any CPU.ActiveCfg = Release|Any CPU
{554C21D7-10BE-48E6-B0EF-9FCA43B32A0F}.Release|Any CPU.Build.0 = Release|Any CPU
{1678743A-9095-4683-8DCD-5763F41924E2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{1678743A-9095-4683-8DCD-5763F41924E2}.Debug|Any CPU.Build.0 = Debug|Any CPU
{1678743A-9095-4683-8DCD-5763F41924E2}.Release|Any CPU.ActiveCfg = Release|Any CPU
{1678743A-9095-4683-8DCD-5763F41924E2}.Release|Any CPU.Build.0 = Release|Any CPU
{EBD49CCA-5400-4C36-B5DF-7B28190AA323}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{EBD49CCA-5400-4C36-B5DF-7B28190AA323}.Debug|Any CPU.Build.0 = Debug|Any CPU
{EBD49CCA-5400-4C36-B5DF-7B28190AA323}.Release|Any CPU.ActiveCfg = Release|Any CPU
@ -254,7 +248,6 @@ Global
{E224F8CF-F9F5-4E99-B405-758F3C02C47A} = {5E5E1E84-DDBC-40D6-B891-0D563A15A44A}
{A11D79AE-F4C9-4595-9B73-0E0AB221B90D} = {5E5E1E84-DDBC-40D6-B891-0D563A15A44A}
{554C21D7-10BE-48E6-B0EF-9FCA43B32A0F} = {5E5E1E84-DDBC-40D6-B891-0D563A15A44A}
{1678743A-9095-4683-8DCD-5763F41924E2} = {5E5E1E84-DDBC-40D6-B891-0D563A15A44A}
{4D162E3C-0962-43B9-B193-6E806249F81B} = {5E5E1E84-DDBC-40D6-B891-0D563A15A44A}
{7CD5C8D5-EC78-4A99-A514-F01CA7197AC8} = {DA71CDAA-8DD3-4D5F-9FBD-8E4B37A2D925}
{E20238CE-5C64-4F87-8753-3B4E1EC9A740} = {7CD5C8D5-EC78-4A99-A514-F01CA7197AC8}

View file

@ -1,11 +0,0 @@
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\..\core\Elsa\Elsa.csproj" />
</ItemGroup>
</Project>

View file

@ -1,14 +0,0 @@
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.Hosting;
namespace Elsa.Samples.TimesheetApproval
{
public class Program
{
public static void Main(string[] args) => CreateHostBuilder(args).Build().Run();
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>(); });
}
}

View file

@ -1,8 +0,0 @@
using Elsa.Services;
namespace Elsa.Samples.TimesheetApproval.Activities
{
public class TimesheetApproved : Activity
{
}
}

View file

@ -1,8 +0,0 @@
using Elsa.Services;
namespace Elsa.Samples.TimesheetApproval.Activities
{
public class TimesheetRejected : Activity
{
}
}

View file

@ -1,18 +0,0 @@
using Elsa.ActivityResults;
using Elsa.Samples.TimesheetApproval.Models;
using Elsa.Services;
using Elsa.Services.Models;
namespace Elsa.Samples.TimesheetApproval.Activities
{
public class TimesheetSubmitted : Activity
{
protected override IActivityExecutionResult OnExecute(ActivityExecutionContext context)
{
var timesheet = (Timesheet) context.Input;
context.SetVariable("Timesheet", timesheet);
return Done();
}
}
}

View file

@ -1,10 +0,0 @@
using Elsa.Samples.TimesheetApproval.Models;
using Elsa.Services.Models;
namespace Elsa.Samples.TimesheetApproval.Extensions
{
public static class ActivityContextExtensions
{
public static Timesheet GetTimesheet(this ActivityExecutionContext context) => context.GetVariable<Timesheet>("Timesheet");
}
}

View file

@ -1,25 +0,0 @@
using System.Threading;
using System.Threading.Tasks;
using Elsa.Samples.TimesheetApproval.Messages;
using Elsa.Samples.TimesheetApproval.Models;
using Elsa.Services;
using MediatR;
namespace Elsa.Samples.TimesheetApproval.Handlers
{
public class TimesheetEventsHandler : INotificationHandler<TimesheetSubmitted>
{
private readonly IWorkflowScheduler _workflowScheduler;
public TimesheetEventsHandler(IWorkflowScheduler workflowScheduler)
{
_workflowScheduler = workflowScheduler;
}
public async Task Handle(TimesheetSubmitted notification, CancellationToken cancellationToken) =>
await TriggerWorkflowsAsync<Activities.TimesheetSubmitted>(notification.Timesheet, cancellationToken);
private async Task TriggerWorkflowsAsync<T>(Timesheet timesheet, CancellationToken cancellationToken) where T:IActivity =>
await _workflowScheduler.TriggerWorkflowsAsync(typeof(T).Name, timesheet, timesheet.TimesheetId, cancellationToken: cancellationToken);
}
}

View file

@ -1,11 +0,0 @@
using Elsa.Samples.TimesheetApproval.Models;
namespace Elsa.Samples.TimesheetApproval.Messages
{
public class TimesheetApproved : TimesheetMessage
{
public TimesheetApproved(Timesheet timesheet) : base(timesheet)
{
}
}
}

View file

@ -1,14 +0,0 @@
using Elsa.Samples.TimesheetApproval.Models;
namespace Elsa.Samples.TimesheetApproval.Messages
{
public abstract class TimesheetMessage
{
protected TimesheetMessage(Timesheet timesheet)
{
Timesheet = timesheet;
}
public Timesheet Timesheet { get; }
}
}

View file

@ -1,11 +0,0 @@
using Elsa.Samples.TimesheetApproval.Models;
namespace Elsa.Samples.TimesheetApproval.Messages
{
public class TimesheetRejected : TimesheetMessage
{
public TimesheetRejected(Timesheet timesheet) : base(timesheet)
{
}
}
}

View file

@ -1,12 +0,0 @@
using Elsa.Samples.TimesheetApproval.Models;
using MediatR;
namespace Elsa.Samples.TimesheetApproval.Messages
{
public class TimesheetSubmitted : TimesheetMessage, INotification
{
public TimesheetSubmitted(Timesheet timesheet) : base(timesheet)
{
}
}
}

View file

@ -1,11 +0,0 @@
namespace Elsa.Samples.TimesheetApproval.Models
{
public class Timesheet
{
public int Id { get; set; }
public string TimesheetId { get; set; }
public string User { get; set; }
public float TotalHours { get; set; }
public TimesheetStatus Status { get; set; } = TimesheetStatus.Draft;
}
}

View file

@ -1,10 +0,0 @@
namespace Elsa.Samples.TimesheetApproval.Models
{
public enum TimesheetStatus
{
Draft,
Submitted,
Rejected,
Approved
}
}

View file

@ -1,12 +0,0 @@
{
"profiles": {
"Elsa.Samples.TimesheetApproval": {
"commandName": "Project",
"launchBrowser": false,
"applicationUrl": "http://localhost:9292",
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
}
}
}
}

View file

@ -1,51 +0,0 @@
using System;
using System.Threading;
using System.Threading.Tasks;
using Elsa.Samples.TimesheetApproval.Messages;
using Elsa.Samples.TimesheetApproval.Models;
using MediatR;
using YesSql;
namespace Elsa.Samples.TimesheetApproval.Services
{
public class TimesheetManager
{
private readonly ISession _session;
private readonly IMediator _mediator;
public TimesheetManager(ISession session, IMediator mediator)
{
_session = session;
_mediator = mediator;
}
public async Task SubmitTimesheet(Timesheet timesheet, CancellationToken cancellationToken = default)
{
timesheet.Status = TimesheetStatus.Submitted;
await SaveAsync(timesheet, cancellationToken);
await _mediator.Publish(new TimesheetSubmitted(timesheet), cancellationToken);
}
public async Task ApproveTimesheet(Timesheet timesheet, CancellationToken cancellationToken = default)
{
timesheet.Status = TimesheetStatus.Approved;
await SaveAsync(timesheet, cancellationToken);
await _mediator.Publish(new TimesheetApproved(timesheet), cancellationToken);
}
public async Task RejectTimesheet(Timesheet timesheet, CancellationToken cancellationToken = default)
{
timesheet.Status = TimesheetStatus.Rejected;
await SaveAsync(timesheet, cancellationToken);
await _mediator.Publish(new TimesheetRejected(timesheet), cancellationToken);
}
public async Task SaveAsync(Timesheet timesheet, CancellationToken cancellationToken = default)
{
if (timesheet.TimesheetId == null)
timesheet.TimesheetId = Guid.NewGuid().ToString("N");
_session.Save(timesheet);
}
}
}

View file

@ -1,58 +0,0 @@
using Elsa.Samples.TimesheetApproval.Services;
using Elsa.Samples.TimesheetApproval.Workflows;
using Microsoft.AspNetCore.Builder;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using YesSql.Provider.Sqlite;
namespace Elsa.Samples.TimesheetApproval
{
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
public void ConfigureServices(IServiceCollection services)
{
// Read configuration.
var connectionString = Configuration.GetConnectionString("SqLite");
var elsaSection = Configuration.GetSection("Elsa");
// Add API controller services.
services.AddControllers();
// Add custom application services.
services
.AddScoped<TimesheetManager>();
// Add Elsa services
services.AddElsa(
elsa => elsa.UsePersistence(config => config.UseSqLite(connectionString)));
// Add activities and their services.
services
.AddHttpActivities(options => options.Bind(elsaSection.GetSection("Http")))
.AddEmailActivities(options => options.Bind(elsaSection.GetSection("Smtp")))
.AddTimerActivities(options => options.Bind(elsaSection.GetSection("BackgroundRunner")))
.AddActivity<Activities.TimesheetSubmitted>()
.AddActivity<Activities.TimesheetApproved>()
.AddActivity<Activities.TimesheetRejected>();
// Add workflows.
services.AddWorkflow<TimesheetApprovalWorkflow>();
}
public void Configure(IApplicationBuilder app)
{
app
.UseRouting()
.UseEndpoints(endpoints => endpoints.MapControllers())
.UseHttpActivities()
.UseWelcomePage();
}
}
}

View file

@ -1,29 +0,0 @@
using Elsa.Activities.Http;
using Elsa.Activities.Http.Services;
using Elsa.Builders;
using Elsa.Samples.TimesheetApproval.Activities;
using Elsa.Samples.TimesheetApproval.Extensions;
namespace Elsa.Samples.TimesheetApproval.Workflows
{
public class TimesheetApprovalWorkflow : IWorkflow
{
public void Build(IWorkflowBuilder workflow)
{
workflow
.StartWith<TimesheetSubmitted>()
.SendEmail(email => email
.WithRecipient("manager@acme.com")
.WithSubject(context => $"Timesheet received from {context.GetTimesheet().User}")
.WithBody(context =>
{
var timesheet = context.GetTimesheet();
var user = timesheet.User;
var hours = timesheet.TotalHours;
var urlProvider = context.GetService<IAbsoluteUrlProvider>();
var timesheetUrl = urlProvider.ToAbsoluteUrl($"/api/timesheets/{timesheet.TimesheetId}");
return $"Hi!<br>User {user} just submitted their timesheet with a total of {hours} hours. Please <a href=\"{timesheetUrl}\">review</a> and then <a hre\"\">Approve</a> or <a href=\"\">Reject</a>";
}));
}
}
}

View file

@ -1,26 +0,0 @@
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
}
},
"AllowedHosts": "*",
"ConnectionStrings": {
"SqLite": "Data Source=elsa.db;Cache=Shared"
},
"Elsa": {
"Http": {
"BaseUrl": "http://localhost:9292"
},
"Smtp": {
"Host": "localhost",
"Port": "2525",
"DefaultSender": "noreply@acme.com"
},
"Timers": {
"SweepInterval": "00:00:30"
}
}
}

View file

@ -1,15 +0,0 @@
version: '3.7'
services:
mongodb:
image: mongo
ports:
- "27017:27017"
volumes:
- /var/lib/mongodb:/var/lib/mongodb
smtp4dev:
image: rnwood/smtp4dev:linux-amd64-3.1.0-ci0856
ports:
- "3000:80"
- "2525:25"