Skip to content

Commit 4ae61ea

Browse files
authored
WFS-468 Vacation request sample (#2)
1 parent a605754 commit 4ae61ea

File tree

7 files changed

+341
-2
lines changed

7 files changed

+341
-2
lines changed

README.md

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
# Callback API Sample
2+
3+
This is a sample of a Web Api server for working with the WorkflowServer Callback API.
4+
Callback API allows hosting your code of Actions, Conditions or Rules on third-party servers.
5+
Callback server should be connected in the admin panel on the Callback API page.
6+
More details on the [workflowserver.io](https://workflowserver.io/documentation/callback-api).
7+
8+
## What's inside
9+
10+
- **ApiController** – controller that implements all possible requests from Callback API of WFS 3.0.0.
11+
- **ActionProvider, ConditionProvider, IdentityProvider** – a sample of the implementation of API functions.
12+
- **VacationRequest** is a schema that implements this API.
13+
14+
## How to start
15+
16+
- Download, deploy and start WorkflowServer. More details on the [workflowserver.io](https://workflowserver.io/documentation/how-to-launch)
17+
- Deploy and start this Web Api Server.
18+
- Go to the WorkflowServer, in the sidebar go to "Api" -> "Callback API". Set up a connection properties to this API.
19+
More details on the [workflowserver.io](https://workflowserver.io/documentation/callback-api)
20+
- In the sidebar, go to "Workflow" -> "Scheme Management" -> "Create".
21+
Create a scheme, name it "VacationRequest" and upload the `Schemes/VacationRequest.xml` file from API project to the Scheme.
22+
- You can now test this sample with the WorkflowApi.
23+
Just create an instance, you can change the initial parameters if you like. Use the Workflow API to execute commands.
24+
Learn more about [workflowserver.io](https://workflowserver.io/documentation/workflow-api)

WorkflowServer.CallbackApi/Controllers/ApiController.cs

Lines changed: 58 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
namespace WorkflowServer.CallbackApi.Controllers;
88

99
/// <summary>
10-
/// This controller implements all possible requests from Callback API of WFS 3.0.0.
10+
/// This controller implements all possible requests from Callback API of Workflow Server 3.0.0.
1111
/// Callback API allows hosting your code of Actions, Conditions or Rules on third-party servers.
1212
/// Callback server should be connected in the admin panel on the Callback API page.
1313
/// More details on the <see href="https://workflowserver.io/documentation/callback-api">workflowserver.io</see>
@@ -23,17 +23,28 @@ public ApiController(ILogger<ApiController> logger)
2323
_actionProvider = new ActionProvider();
2424
_conditionProvider = new ConditionProvider();
2525
_identityProvider = new IdentityProvider();
26+
27+
//The parameters will not be saved, this is an example. You should add the provider as a dependency injection.
2628
_parameterProvider = new ParameterProvider();
2729
}
2830

2931
#region Actions & Conditions Execution
3032

33+
/// <summary>
34+
/// Returns a list of actions that can be executed on the callback server.
35+
/// When the Workflow Server should execute an Action with a certain name,
36+
/// it calls the action execution method on the server that has returned this
37+
/// name in response to the request for the list of actions.
38+
/// </summary>
3139
[HttpGet]
3240
public Task<IActionResult> GetActions(string schemeCode, string token)
3341
{
3442
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok(_actionProvider.ActionNames)));
3543
}
3644

45+
/// <summary>
46+
/// Request to execute the action. Which of callback servers is called to execute this method, depends on the list of actions returned.
47+
/// </summary>
3748
[HttpPost]
3849
public async Task<IActionResult> ExecuteAction(InstanceRequest request)
3950
{
@@ -42,12 +53,22 @@ public async Task<IActionResult> ExecuteAction(InstanceRequest request)
4253
return Ok(ApiResponse.Ok());
4354
}
4455

56+
/// <summary>
57+
/// Returns a list of conditions that can be executed on the callback server.
58+
/// When the Workflow Server should execute a condition with a certain name,
59+
/// it calls the condition execution method on the server that has returned
60+
/// this name in response to the request for the list of conditions.
61+
/// </summary>
4562
[HttpGet]
4663
public Task<IActionResult> GetConditions(string schemeCode, string token)
4764
{
4865
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok(_conditionProvider.ConditionNames)));
4966
}
5067

68+
/// <summary>
69+
/// Request to execute the condition. Which of the callback servers
70+
/// is called to execute this method, depends on the list of conditions returned.
71+
/// </summary>
5172
[HttpPost]
5273
public async Task<IActionResult> ExecuteCondition(InstanceRequest request)
5374
{
@@ -63,19 +84,31 @@ public async Task<IActionResult> ExecuteCondition(InstanceRequest request)
6384

6485
#region Authorization Rules Execution
6586

87+
/// <summary>
88+
/// Returns a list of Authorization Rules that can be executed on the callback server.
89+
/// When the Workflow Server should execute an Authorization Rule with a certain name,
90+
/// it calls the Authorization Rule execution method on the server that has returned
91+
/// this name in response to the request for the list of Authorization Rules.
92+
/// </summary>
6693
[HttpGet]
6794
public Task<IActionResult> GetRules(string schemeCode, string token)
6895
{
6996
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok(_identityProvider.RuleNames)));
7097
}
7198

99+
/// <summary>
100+
/// Check if the User has the access to the command.
101+
/// </summary>
72102
[HttpPost]
73103
public async Task<IActionResult> CheckRule(CheckRuleRequest request)
74104
{
75105
var result = await _identityProvider.RuleCheck(request.Name, request.IdentityId, request.Parameter, request.ProcessInstance);
76106
return Ok(ApiResponse.Ok(result));
77107
}
78108

109+
/// <summary>
110+
/// Returns the list of all Users who have the access.
111+
/// </summary>
79112
[HttpPost]
80113
public async Task<IActionResult> GetIdentities(InstanceRequest request)
81114
{
@@ -89,6 +122,11 @@ public async Task<IActionResult> GetIdentities(InstanceRequest request)
89122

90123
#region Remote Scheme Generation
91124

125+
/// <summary>
126+
/// Workflow Engine (is a part of WorkflowServer) supports scheme generation. If you include this method, then,
127+
/// to initialize a new scheme, the Workflow Server calls it on all the connected
128+
/// servers with the settings containing the address of this method.
129+
/// </summary>
92130
[HttpPost]
93131
public Task<IActionResult> Generate(GenerateRequest request)
94132
{
@@ -103,6 +141,10 @@ public Task<IActionResult> Generate(GenerateRequest request)
103141

104142
#region Event Handlers
105143

144+
/// <summary>
145+
/// The ProcessStatusChanged event is called only after switching to
146+
/// the statuses of Idled and Finalized. It is not called for subprocesses.
147+
/// </summary>
106148
[HttpPost]
107149
public Task<IActionResult> ProcessStatusChanged(StatusChangedRequest request)
108150
{
@@ -114,6 +156,9 @@ public Task<IActionResult> ProcessStatusChanged(StatusChangedRequest request)
114156
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok()));
115157
}
116158

159+
/// <summary>
160+
/// The ProcessActivityChanged event.
161+
/// </summary>
117162
[HttpPost]
118163
public Task<IActionResult> ProcessActivityChanged(ActivityChangedRequest request)
119164
{
@@ -125,6 +170,9 @@ public Task<IActionResult> ProcessActivityChanged(ActivityChangedRequest request
125170
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok()));
126171
}
127172

173+
/// <summary>
174+
/// The processLogs event.
175+
/// </summary>
128176
[HttpPost]
129177
public Task<IActionResult> ProcessLog(LogRequest request)
130178
{
@@ -137,19 +185,28 @@ public Task<IActionResult> ProcessLog(LogRequest request)
137185

138186
#region Parameters Providing
139187

188+
/// <summary>
189+
/// Used to get parameters list.
190+
/// </summary>
140191
[HttpGet]
141192
public Task<IActionResult> GetParameterNames(string schemeCode, string token)
142193
{
143194
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok(_parameterProvider.GetNames)));
144195
}
145196

197+
/// <summary>
198+
/// The method returns a JSON serialized parameter value.
199+
/// </summary>
146200
[HttpPost]
147201
public Task<IActionResult> GetParameter(ParameterRequest request)
148202
{
149203
var result = _parameterProvider.GetParameter(request.Name);
150204
return Task.FromResult<IActionResult>(Ok(ApiResponse.Ok(result)));
151205
}
152206

207+
/// <summary>
208+
/// Used for set parameter value.
209+
/// </summary>
153210
[HttpPost]
154211
public Task<IActionResult> SetParameter(ParameterRequest request)
155212
{
Lines changed: 184 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,184 @@
1+
<Process Name="VacationRequest" CanBeInlined="false" Tags="" LogEnabled="true">
2+
<Designer X="-110" Y="-60" />
3+
<Actors>
4+
<Actor Name="Manager" Rule="isUser" Value="@Manager" />
5+
<Actor Name="Author" Rule="isUser" Value="@Author" />
6+
<Actor Name="BigBoss" Rule="InRole" Value="Big Boss" />
7+
<Actor Name="Accountant" Rule="InRole" Value="Accountant" />
8+
</Actors>
9+
<Parameters>
10+
<Parameter Name="Comment" Type="String" Purpose="Temporary" />
11+
<Parameter Name="Author" Type="String" Purpose="Persistence" InitialValue="John" />
12+
<Parameter Name="Manager" Type="String" Purpose="Persistence" InitialValue="Margo" />
13+
<Parameter Name="Sum" Type="Int32" Purpose="Persistence" InitialValue="100" />
14+
</Parameters>
15+
<Commands>
16+
<Command Name="StartSigning">
17+
<InputParameters>
18+
<ParameterRef Name="Comment" IsRequired="false" DefaultValue="" NameRef="Comment" />
19+
</InputParameters>
20+
</Command>
21+
<Command Name="Approve">
22+
<InputParameters>
23+
<ParameterRef Name="Comment" IsRequired="false" DefaultValue="" NameRef="Comment" />
24+
</InputParameters>
25+
</Command>
26+
<Command Name="Reject">
27+
<InputParameters>
28+
<ParameterRef Name="Comment" IsRequired="false" DefaultValue="" NameRef="Comment" />
29+
</InputParameters>
30+
</Command>
31+
<Command Name="Paid">
32+
<InputParameters>
33+
<ParameterRef Name="Comment" IsRequired="false" DefaultValue="" NameRef="Comment" />
34+
</InputParameters>
35+
</Command>
36+
</Commands>
37+
<Timers>
38+
<Timer Name="SendToBigBoss" Type="Interval" Value="10minutes" NotOverrideIfExists="false" />
39+
</Timers>
40+
<Activities>
41+
<Activity Name="VacationRequestCreated" State="VacationRequestCreated" IsInitial="true" IsFinal="false" IsForSetState="true" IsAutoSchemeUpdate="true">
42+
<Implementation>
43+
<ActionRef Order="1" NameRef="JsonBackup">
44+
<ActionParameter><![CDATA[StartBackup]]></ActionParameter>
45+
</ActionRef>
46+
</Implementation>
47+
<Designer X="20" Y="160" Hidden="false" />
48+
</Activity>
49+
<Activity Name="ManagerSigning" State="ManagerSigning" IsInitial="false" IsFinal="false" IsForSetState="true" IsAutoSchemeUpdate="true">
50+
<Designer X="360" Y="160" Hidden="false" />
51+
</Activity>
52+
<Activity Name="BigBossSigning" State="BigBossSigning" IsInitial="false" IsFinal="false" IsForSetState="true" IsAutoSchemeUpdate="true">
53+
<Designer X="640" Y="160" Hidden="false" />
54+
</Activity>
55+
<Activity Name="AccountingReview" State="AccountingReview" IsInitial="false" IsFinal="false" IsForSetState="true" IsAutoSchemeUpdate="true">
56+
<Designer X="630" Y="320" Hidden="false" />
57+
</Activity>
58+
<Activity Name="RequestApproved" State="RequestApproved" IsInitial="false" IsFinal="true" IsForSetState="true" IsAutoSchemeUpdate="true">
59+
<Implementation>
60+
<ActionRef Order="1" NameRef="JsonBackup">
61+
<ActionParameter><![CDATA[FinalBackup]]></ActionParameter>
62+
</ActionRef>
63+
</Implementation>
64+
<Designer X="900" Y="320" Hidden="false" />
65+
</Activity>
66+
</Activities>
67+
<Transitions>
68+
<Transition Name="ManagerSigning_Draft_1" To="VacationRequestCreated" From="ManagerSigning" Classifier="Reverse" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
69+
<Restrictions>
70+
<Restriction Type="Allow" NameRef="Manager" />
71+
</Restrictions>
72+
<Triggers>
73+
<Trigger Type="Command" NameRef="Reject" />
74+
</Triggers>
75+
<Conditions>
76+
<Condition Type="Always" />
77+
</Conditions>
78+
<Designer X="269" Y="205" Hidden="false" />
79+
</Transition>
80+
<Transition Name="BigBossSigning_Activity_1_1" To="AccountingReview" From="BigBossSigning" Classifier="Direct" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
81+
<Restrictions>
82+
<Restriction Type="Allow" NameRef="BigBoss" />
83+
</Restrictions>
84+
<Triggers>
85+
<Trigger Type="Command" NameRef="Approve" />
86+
</Triggers>
87+
<Conditions>
88+
<Condition Type="Always" />
89+
</Conditions>
90+
<Designer Hidden="false" />
91+
</Transition>
92+
<Transition Name="ManagerSigning_Approved_1" To="AccountingReview" From="ManagerSigning" Classifier="Direct" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
93+
<Restrictions>
94+
<Restriction Type="Allow" NameRef="Manager" />
95+
</Restrictions>
96+
<Triggers>
97+
<Trigger Type="Command" NameRef="Approve" />
98+
</Triggers>
99+
<Conditions>
100+
<Condition Type="Otherwise" />
101+
</Conditions>
102+
<Designer X="453" Y="271" Hidden="false" />
103+
</Transition>
104+
<Transition Name="ManagerSigning_BigBossSigning_1" To="BigBossSigning" From="ManagerSigning" Classifier="Direct" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
105+
<Restrictions>
106+
<Restriction Type="Allow" NameRef="Manager" />
107+
</Restrictions>
108+
<Triggers>
109+
<Trigger Type="Command" NameRef="Approve" />
110+
</Triggers>
111+
<Conditions>
112+
<Condition Type="Expression" ConditionInversion="false">
113+
<Expression><![CDATA[@Sum > 100]]></Expression>
114+
</Condition>
115+
</Conditions>
116+
<Designer X="562" Y="177" Hidden="false" />
117+
</Transition>
118+
<Transition Name="Draft_ManagerSigning_1" To="ManagerSigning" From="VacationRequestCreated" Classifier="Direct" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
119+
<Restrictions>
120+
<Restriction Type="Allow" NameRef="Author" />
121+
</Restrictions>
122+
<Triggers>
123+
<Trigger Type="Command" NameRef="StartSigning" />
124+
</Triggers>
125+
<Conditions>
126+
<Condition Type="Always" />
127+
</Conditions>
128+
<Designer X="269" Y="170" Hidden="false" />
129+
</Transition>
130+
<Transition Name="BigBossSigning_ManagerSigning_1" To="ManagerSigning" From="BigBossSigning" Classifier="Reverse" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
131+
<Restrictions>
132+
<Restriction Type="Allow" NameRef="BigBoss" />
133+
</Restrictions>
134+
<Triggers>
135+
<Trigger Type="Command" NameRef="Reject" />
136+
</Triggers>
137+
<Conditions>
138+
<Condition Type="Always" />
139+
</Conditions>
140+
<Designer X="563" Y="204" Hidden="false" />
141+
</Transition>
142+
<Transition Name="ManagerSigning_BigBossSigning_2" To="BigBossSigning" From="ManagerSigning" Classifier="NotSpecified" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
143+
<Triggers>
144+
<Trigger Type="Timer" NameRef="SendToBigBoss" />
145+
</Triggers>
146+
<Conditions>
147+
<Condition Type="Always" />
148+
</Conditions>
149+
<Designer X="557" Y="120" Hidden="false" />
150+
</Transition>
151+
<Transition Name="Accountant_Activity_1_1" To="RequestApproved" From="AccountingReview" Classifier="Direct" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
152+
<Restrictions>
153+
<Restriction Type="Allow" NameRef="Accountant" />
154+
</Restrictions>
155+
<Triggers>
156+
<Trigger Type="Command" NameRef="Paid" />
157+
</Triggers>
158+
<Conditions>
159+
<Condition Type="Always" />
160+
</Conditions>
161+
<Designer Hidden="false" />
162+
</Transition>
163+
<Transition Name="Accountant_ManagerSigning_1" To="ManagerSigning" From="AccountingReview" Classifier="Reverse" AllowConcatenationType="And" RestrictConcatenationType="And" ConditionsConcatenationType="And" DisableParentStateControl="false">
164+
<Restrictions>
165+
<Restriction Type="Allow" NameRef="Accountant" />
166+
</Restrictions>
167+
<Triggers>
168+
<Trigger Type="Command" NameRef="Reject" />
169+
</Triggers>
170+
<Conditions>
171+
<Condition Type="Always" />
172+
</Conditions>
173+
<Designer X="395" Y="343" Hidden="false" />
174+
</Transition>
175+
</Transitions>
176+
<Localization>
177+
<Localize Type="State" IsDefault="True" Culture="en-US" ObjectName="ManagerSigning" Value="Manager signing" />
178+
<Localize Type="State" IsDefault="True" Culture="en-US" ObjectName="BigBossSigning" Value="BigBoss signing" />
179+
<Localize Type="Command" IsDefault="True" Culture="en-US" ObjectName="StartSigning" Value="Start signing" />
180+
<Localize Type="State" IsDefault="True" Culture="en-US" ObjectName="AccountingReview" Value="Accounting review" />
181+
<Localize Type="State" IsDefault="True" Culture="en-US" ObjectName="VacationRequestCreated" Value="Vacation request created" />
182+
<Localize Type="State" IsDefault="True" Culture="en-US" ObjectName="RequestApproved" Value="Request approved" />
183+
</Localization>
184+
</Process>
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
namespace WorkflowServer.CallbackApi.VacationRequest;
2+
3+
public class User
4+
{
5+
public User(string id, string name, params string[] roles)
6+
{
7+
Id = id;
8+
Name = name;
9+
Roles = roles;
10+
}
11+
12+
public string Id { get; }
13+
public string Name { get; }
14+
public string[] Roles { get; }
15+
}

0 commit comments

Comments
 (0)