Skip to content

Commit 8dc9acd

Browse files
authored
Merge pull request #203 from docusign/added-maestro-examples
Added new maestro code examples
2 parents 42cd99b + 32d9faf commit 8dc9acd

29 files changed

+1785
-49
lines changed

ExamplesAPIType.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,12 @@ public enum ExamplesApiType
6161
/// </summary>")]
6262
[Description("nav")]
6363
Navigator = 8,
64+
65+
/// <summary>
66+
/// Maestro
67+
/// </summary>")]
68+
[Description("mae")]
69+
Maestro = 9,
6470
}
6571

6672
public static class ExamplesApiTypeExtensions

ExamplesApiTypeExtensions.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,12 @@ public enum ExamplesApiType
6767
/// </summary>")]
6868
[Description("nav")]
6969
Navigator = 9,
70+
71+
/// <summary>
72+
/// Maestro
73+
/// </summary>")]
74+
[Description("mae")]
75+
Maestro = 10,
7076
}
7177

7278
public static class ExamplesApiTypeExtensions

JWTAuth.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,14 @@ public static OAuthToken AuthenticateWithJwt(string api, string clientId, string
5050
});
5151
}
5252

53+
if (apiType == ExamplesApiType.Maestro)
54+
{
55+
scopes.AddRange(new List<string>
56+
{
57+
"aow_manage",
58+
});
59+
}
60+
5361
if (apiType == ExamplesApiType.Monitor)
5462
{
5563
scopes.AddRange(new List<string>

launcher-csharp/Common/RequestItemsService.cs

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -23,17 +23,17 @@ public class RequestItemsService : IRequestItemsService
2323

2424
private static Guid? organizationId;
2525

26-
#nullable enable
26+
#nullable enable
2727
private static string? authenticatedUserEmail;
28-
#nullable disable
28+
#nullable disable
2929

3030
private readonly IHttpContextAccessor httpContextAccessor;
3131

3232
private readonly IMemoryCache cache;
3333

34-
#nullable enable
34+
#nullable enable
3535
private readonly string? id;
36-
#nullable disable
36+
#nullable disable
3737

3838
private OAuthToken authToken;
3939

@@ -54,27 +54,27 @@ public RequestItemsService(IHttpContextAccessor httpContextAccessor, IMemoryCach
5454

5555
public IConfiguration Configuration { get; set; }
5656

57-
#nullable enable
57+
#nullable enable
5858
public string? EgName
5959
{
6060
get => this.cache.Get<string>(this.GetKey("EgName"));
6161
set => this.cache.Set(this.GetKey("EgName"), value);
6262
}
63-
#nullable disable
63+
#nullable disable
6464

6565
public Session Session
6666
{
6767
get => this.cache.Get<Session>(this.GetKey("Session"));
6868
set => this.cache.Set(this.GetKey("Session"), value);
6969
}
7070

71-
#nullable enable
71+
#nullable enable
7272
public User? User
7373
{
7474
get => this.cache.Get<User>(this.GetKey("User"));
7575
set => this.cache.Set(this.GetKey("User"), value);
7676
}
77-
#nullable disable
77+
#nullable disable
7878

7979
public Guid? OrganizationId
8080
{
@@ -305,6 +305,10 @@ public string IdentifyApiOfCodeExample(string eg)
305305
{
306306
currentApiType = ExamplesApiType.Navigator.ToString();
307307
}
308+
else if (eg.Contains(ExamplesApiType.Maestro.ToKeywordString()))
309+
{
310+
currentApiType = ExamplesApiType.Maestro.ToString();
311+
}
308312
else
309313
{
310314
currentApiType = ExamplesApiType.ESignature.ToString();

launcher-csharp/ConnectedFields/Views/Eg001SetConnectedFields/cf001.cshtml

Lines changed: 52 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -23,40 +23,55 @@
2323
">SetConnectedFields.cs</a>"))
2424
</p>
2525

26-
<form class="eg" action="" method="post" data-busy="form">
27-
<div class="form-group">
28-
<label for="signerEmail">
29-
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerEmailInputNumber].InputName)
30-
</label>
31-
<input type="email" class="form-control" id="signerEmail" name="signerEmail" aria-describedby="emailHelp"
32-
placeholder="@ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerEmailInputNumber].InputPlaceholder"
33-
required value="@ViewBag.Locals.DsConfig.SignerEmail" />
34-
<small id="emailHelp"
35-
class="form-text text-muted">@Html.Raw(ViewBag.SupportingTexts.HelpingTexts.EmailWontBeShared)</small>
36-
</div>
37-
<div class="form-group">
38-
<label for="signerName">
39-
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerNameInputNumber].InputName)
40-
</label>
41-
<input type="text" class="form-control" id="signerName"
42-
placeholder="@ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerNameInputNumber].InputPlaceholder"
43-
name="signerName" value="@ViewBag.Locals.DsConfig.SignerName" required />
44-
</div>
45-
<div class="form-group">
46-
<label for="apps">
47-
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[extensionsInputNumber].InputName)
48-
</label>
49-
50-
<select id="appId" name="appId" class="form-control">
51-
@foreach (var app in apps)
52-
{
53-
var appId = app.AppId;
54-
var applicationName = app.Tabs?[0]?.ExtensionData?.ApplicationName;
55-
56-
<option value="@appId">@applicationName</option>
57-
}
58-
</select>
59-
</div>
60-
<input type="hidden" name="_csrf" value="<%- csrfToken %>">
61-
<button type="submit" class="btn btn-primary">@Html.Raw(ViewBag.SupportingTexts.SubmitButton)</button>
62-
</form>
26+
@if (apps.Count != 0)
27+
{
28+
<form class="eg" action="" method="post" data-busy="form">
29+
<div class="form-group">
30+
<label for="signerEmail">
31+
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerEmailInputNumber].InputName)
32+
</label>
33+
<input type="email" class="form-control" id="signerEmail" name="signerEmail" aria-describedby="emailHelp"
34+
placeholder="@ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerEmailInputNumber].InputPlaceholder"
35+
required value="@ViewBag.Locals.DsConfig.SignerEmail"/>
36+
<small id="emailHelp"
37+
class="form-text text-muted">@Html.Raw(ViewBag.SupportingTexts.HelpingTexts.EmailWontBeShared)</small>
38+
</div>
39+
<div class="form-group">
40+
<label for="signerName">
41+
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerNameInputNumber].InputName)
42+
</label>
43+
<input type="text" class="form-control" id="signerName"
44+
placeholder="@ViewBag.CodeExampleText.Forms[formNumber].Inputs[signerNameInputNumber].InputPlaceholder"
45+
name="signerName" value="@ViewBag.Locals.DsConfig.SignerName" required/>
46+
</div>
47+
<div class="form-group">
48+
<label for="apps">
49+
@Html.Raw(ViewBag.CodeExampleText.Forms[formNumber].Inputs[extensionsInputNumber].InputName)
50+
</label>
51+
52+
<select id="appId" name="appId" class="form-control">
53+
@foreach (var app in apps)
54+
{
55+
var appId = app.AppId;
56+
var applicationName = app.Tabs?[0]?.ExtensionData?.ApplicationName;
57+
58+
<option value="@appId">@applicationName</option>
59+
}
60+
</select>
61+
</div>
62+
<input type="hidden" name="_csrf" value="<%- csrfToken %>">
63+
<button type="submit" class="btn btn-primary">@Html.Raw(ViewBag.SupportingTexts.SubmitButton)</button>
64+
</form>
65+
}
66+
else
67+
{
68+
<p>
69+
@Html.Raw(
70+
ViewBag.CodeExampleText.CustomErrorTexts[0].ErrorMessage
71+
)
72+
</p>
73+
74+
<form class="eg" action="" method="get" data-busy="form">
75+
<button type="submit" class="btn btn-primary">@Html.Raw(ViewBag.SupportingTexts.ContinueButton)</button>
76+
</form>
77+
}
Lines changed: 183 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,183 @@
1+
// <copyright file="Mae001TriggerWorkflowController.cs" company="DocuSign">
2+
// Copyright (c) DocuSign. All rights reserved.
3+
// </copyright>
4+
5+
namespace DocuSign.CodeExamples.Controllers
6+
{
7+
using System;
8+
using System.Linq;
9+
using System.Threading.Tasks;
10+
using DocuSign.CodeExamples.Common;
11+
using DocuSign.CodeExamples.Examples;
12+
using DocuSign.CodeExamples.Models;
13+
using Docusign.IAM.SDK.Models.Components;
14+
using Docusign.IAM.SDK.Models.Errors;
15+
using Microsoft.AspNetCore.Mvc;
16+
17+
[Area("Maestro")]
18+
[Route("mae001")]
19+
public class Mae001TriggerWorkflowController : EgController
20+
{
21+
private const string WorkflowName = "Example workflow - send invite to signer";
22+
23+
public Mae001TriggerWorkflowController(DsConfiguration dsConfig,
24+
LauncherTexts launcherTexts,
25+
IRequestItemsService requestItemsService)
26+
: base(dsConfig, launcherTexts, requestItemsService)
27+
{
28+
this.CodeExampleText = this.GetExampleText(this.EgName, ExamplesApiType.Maestro);
29+
this.ViewBag.title = this.CodeExampleText.ExampleName;
30+
}
31+
32+
public override string EgName => "mae001";
33+
34+
[MustAuthenticate]
35+
[HttpGet]
36+
public override IActionResult Get()
37+
{
38+
var actionResult = base.Get();
39+
if (this.RequestItemsService.EgName == this.EgName)
40+
{
41+
return actionResult;
42+
}
43+
44+
var basePath = this.RequestItemsService.Session.IamBasePath;
45+
var accessToken = this.RequestItemsService.User.AccessToken;
46+
var accountId = this.RequestItemsService.Session.AccountId;
47+
48+
try
49+
{
50+
if (this.RequestItemsService.WorkflowId == null)
51+
{
52+
WorkflowsListSuccess workflowsList = TriggerMaestroWorkflow.GetMaestroWorkflow(
53+
basePath,
54+
accessToken,
55+
accountId).GetAwaiter().GetResult();
56+
57+
if (workflowsList.Data != null || workflowsList.Data.Count > 0)
58+
{
59+
var maestroWorkflow = workflowsList.Data.FirstOrDefault(workflow => workflow.Name == WorkflowName);
60+
61+
this.RequestItemsService.WorkflowId = maestroWorkflow?.Id;
62+
}
63+
}
64+
65+
if (this.RequestItemsService.WorkflowId == null && this.RequestItemsService.TemplateId != null)
66+
{
67+
var workflowId = TriggerMaestroWorkflow.CreateWorkflowAsync(
68+
accessToken,
69+
accountId,
70+
this.RequestItemsService.TemplateId,
71+
this.Config.MaestroWorkflowConfig).GetAwaiter().GetResult();
72+
this.RequestItemsService.WorkflowId = workflowId;
73+
74+
var publishLink = TriggerMaestroWorkflow.PublishWorkflowAsync(
75+
accountId,
76+
workflowId,
77+
accessToken).GetAwaiter().GetResult();
78+
79+
this.RequestItemsService.IsWorkflowPublished = true;
80+
this.ViewBag.ConsentLink = this.CodeExampleText.AdditionalPages[0].ResultsPageText
81+
.Replace("{0}", publishLink);
82+
this.ViewBag.WorkflowId = this.RequestItemsService.WorkflowId;
83+
this.ViewBag.TemplateId = this.RequestItemsService.TemplateId;
84+
85+
return this.View("publishWorkflow");
86+
}
87+
88+
if (this.RequestItemsService.IsWorkflowPublished)
89+
{
90+
var publishLink = TriggerMaestroWorkflow.PublishWorkflowAsync(
91+
accountId,
92+
this.RequestItemsService.WorkflowId,
93+
accessToken).GetAwaiter().GetResult();
94+
95+
if (publishLink != string.Empty)
96+
{
97+
this.ViewBag.ConsentLink = this.CodeExampleText.AdditionalPages[0].ResultsPageText
98+
.Replace("{0}", publishLink);
99+
100+
this.ViewBag.WorkflowId = this.RequestItemsService.WorkflowId;
101+
this.ViewBag.TemplateId = this.RequestItemsService.TemplateId;
102+
return this.View("publishWorkflow");
103+
}
104+
105+
this.RequestItemsService.IsWorkflowPublished = false;
106+
}
107+
108+
this.ViewBag.WorkflowId = this.RequestItemsService.WorkflowId;
109+
this.ViewBag.TemplateId = this.RequestItemsService.TemplateId;
110+
111+
return this.View("mae001");
112+
}
113+
catch (Exception apiException)
114+
{
115+
this.ViewBag.errorCode = string.Empty;
116+
this.ViewBag.errorMessage = apiException.Message;
117+
this.ViewBag.SupportingTexts = this.LauncherTexts.ManifestStructure.SupportingTexts;
118+
this.ViewBag.SupportMessage = this.CodeExampleText.CustomErrorTexts[0].ErrorMessage;
119+
120+
return this.View("Error");
121+
}
122+
}
123+
124+
[HttpPost]
125+
[SetViewBag]
126+
public async Task<IActionResult> Create(
127+
string instanceName,
128+
string signerEmail,
129+
string signerName,
130+
string ccEmail,
131+
string ccName)
132+
{
133+
// Check the token with minimal buffer time.
134+
bool tokenOk = this.CheckToken(3);
135+
if (!tokenOk)
136+
{
137+
// We could store the parameters of the requested operation
138+
// so it could be restarted automatically.
139+
// But since it should be rare to have a token issue here,
140+
// we'll make the user re-enter the form data after
141+
// authentication.
142+
this.RequestItemsService.EgName = this.EgName;
143+
return this.Redirect("/ds/mustAuthenticate");
144+
}
145+
146+
string accessToken = this.RequestItemsService.User.AccessToken;
147+
string basePath = this.RequestItemsService.Session.IamBasePath;
148+
string accountId = this.RequestItemsService.Session.AccountId;
149+
string workflowId = this.RequestItemsService.WorkflowId;
150+
151+
try
152+
{
153+
var instance = await TriggerMaestroWorkflow.TriggerWorkflowInstance(
154+
basePath,
155+
accessToken,
156+
accountId,
157+
workflowId,
158+
signerEmail,
159+
signerName,
160+
ccEmail,
161+
ccName,
162+
instanceName);
163+
164+
this.RequestItemsService.WorkflowId = workflowId;
165+
this.RequestItemsService.InstanceId = instance.InstanceId;
166+
167+
this.ViewBag.h1 = this.CodeExampleText.ExampleName;
168+
this.ViewBag.Url = instance.InstanceUrl;
169+
this.ViewBag.message = string.Format(this.CodeExampleText.ResultsPageText);
170+
171+
return this.View("embed");
172+
}
173+
catch (APIException exception)
174+
{
175+
this.ViewBag.errorCode = exception.StatusCode;
176+
this.ViewBag.SupportingTexts = this.LauncherTexts.ManifestStructure.SupportingTexts;
177+
this.ViewBag.errorMessage = exception.Message;
178+
179+
return this.View("Error");
180+
}
181+
}
182+
}
183+
}

0 commit comments

Comments
 (0)