Skip to content

Commit 8105b66

Browse files
author
nianiB9
authored
Merge pull request #187 from docusign/feature/create-account
Create account example
2 parents e1b00ba + a0e859a commit 8105b66

File tree

8 files changed

+882
-668
lines changed

8 files changed

+882
-668
lines changed

index.js

Lines changed: 384 additions & 381 deletions
Large diffs are not rendered by default.

lib/DSJwtAuth.js

Lines changed: 268 additions & 268 deletions
Large diffs are not rendered by default.
Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
/**
2+
* @file
3+
* Example 013: How to create an account
4+
* @author DocuSign
5+
*/
6+
7+
const path = require('path');
8+
const validator = require('validator');
9+
const dsConfig = require('../../../config/index.js').config;
10+
const { createAccount, getOrganizationPlanItem } = require('../examples/createAccount');
11+
const { getOrganizationId } = require('../getOrganizationId.js');
12+
const { getExampleByNumber } = require('../../manifestService');
13+
const { API_TYPES } = require('../../utils.js');
14+
15+
const eg013CreateAccount = exports;
16+
const exampleNumber = 13;
17+
const eg = `aeg0${exampleNumber}`; // This example reference.
18+
const api = API_TYPES.ADMIN;
19+
const mustAuthenticate = '/ds/mustAuthenticate';
20+
const minimumBufferMin = 3;
21+
22+
/**
23+
* Clone an account
24+
* @param {object} req Request obj
25+
* @param {object} res Response obj
26+
*/
27+
eg013CreateAccount.createController = async (req, res) => {
28+
// Step 1. Check the token
29+
// At this point we should have a good token. But we
30+
// double-check here to enable a better UX to the user.
31+
const isTokenOK = req.dsAuth.checkToken(minimumBufferMin);
32+
if (!isTokenOK) {
33+
req.flash('info', 'Sorry, you need to re-authenticate.');
34+
// Save the current operation so it will be resumed after authentication
35+
req.dsAuth.setEg(req, eg);
36+
return res.redirect(mustAuthenticate);
37+
}
38+
39+
const { body } = req;
40+
const args = {
41+
accessToken: req.user.accessToken,
42+
basePath: dsConfig.adminAPIUrl,
43+
organizationId: req.session.organizationId,
44+
email: validator.escape(body.email),
45+
firstName: validator.escape(body.firstName),
46+
lastName: validator.escape(body.lastName),
47+
subscriptionId: validator.escape(req.session.subscriptionId),
48+
planId: validator.escape(req.session.planId),
49+
};
50+
51+
let results = null;
52+
53+
try {
54+
results = await createAccount(args);
55+
} catch (error) {
56+
// we can pull the DocuSign error code and message from the response body
57+
const errorBody = error?.response?.body || error?.body;
58+
const errorCode = errorBody?.errorCode || errorBody?.error;
59+
const errorMessage = errorBody?.message || errorBody?.error_description;
60+
61+
// In production, may want to provide customized error messages and
62+
// remediation advice to the user.
63+
res.render('pages/error', { err: error, errorCode, errorMessage });
64+
}
65+
if (results) {
66+
const example = getExampleByNumber(res.locals.manifest, exampleNumber, api);
67+
res.render('pages/example_done', {
68+
title: example.ExampleName,
69+
message: example.ResultsPageText,
70+
json: JSON.stringify(results)
71+
});
72+
}
73+
};
74+
75+
/**
76+
* Form page for this application
77+
*/
78+
eg013CreateAccount.getController = async (req, res) => {
79+
// Check that the authentication token is ok with a long buffer time.
80+
// If needed, now is the best time to ask the user to authenticate
81+
// since they have not yet entered any information into the form.
82+
83+
const isTokenOK = req.dsAuth.checkToken();
84+
if (!isTokenOK) {
85+
// Save the current operation so it will be resumed after authentication
86+
req.dsAuth.setEg(req, eg);
87+
return res.redirect(mustAuthenticate);
88+
}
89+
90+
try {
91+
await getOrganizationId(req);
92+
const args = {
93+
accessToken: req.user.accessToken,
94+
basePath: dsConfig.adminAPIUrl,
95+
organizationId: req.session.organizationId
96+
};
97+
98+
const planItem = await getOrganizationPlanItem(args);
99+
req.session.subscriptionId = planItem.subscription_id;
100+
req.session.planId = planItem.plan_id;
101+
102+
const example = getExampleByNumber(res.locals.manifest, exampleNumber, api);
103+
const sourceFile = (path.basename(__filename))[5].toLowerCase() + (path.basename(__filename)).substr(6);
104+
res.render('pages/admin-examples/eg013CreateAccount', {
105+
eg: eg,
106+
csrfToken: req.csrfToken(),
107+
example: example,
108+
sourceFile: sourceFile,
109+
sourceUrl: dsConfig.githubExampleUrl + 'admin/examples/' + sourceFile,
110+
documentation: dsConfig.documentation + eg,
111+
showDoc: dsConfig.documentation,
112+
});
113+
} catch (error) {
114+
const errorCode = error?.response?.body?.errorCode;
115+
const errorMessage = error?.response?.body?.message;
116+
117+
// In production, may want to provide customized error messages and
118+
// remediation advice to the user.
119+
res.render('pages/error', { err: error, errorCode, errorMessage });
120+
}
121+
};

lib/admin/controllers/index.js

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
1-
module.exports.eg001admin = require('./eg001CreateUser');
2-
module.exports.eg002admin = require('./eg002CreateCLMESignUser');
3-
module.exports.eg003admin = require('./eg003BulkExportUserData');
4-
module.exports.eg004admin = require('./eg004ImportUser');
5-
module.exports.eg005admin = require('./eg005AuditUsers');
6-
module.exports.eg006admin = require('./eg006GetUserProfileByEmail');
7-
module.exports.eg007admin = require('./eg007GetUserProfileByUserId');
8-
module.exports.eg008admin = require('./eg008UpdateUserProductPermissionProfile');
9-
module.exports.eg009admin = require('./eg009DeleteUserProductPermissionProfile');
10-
module.exports.eg010admin = require('./eg010DeleteUserDataFromOrganization');
11-
module.exports.eg011admin = require('./eg011DeleteUserDataFromAccount');
12-
module.exports.eg012admin = require('./eg012CloneAccount');
1+
module.exports.eg001admin = require('./eg001CreateUser');
2+
module.exports.eg002admin = require('./eg002CreateCLMESignUser');
3+
module.exports.eg003admin = require('./eg003BulkExportUserData');
4+
module.exports.eg004admin = require('./eg004ImportUser');
5+
module.exports.eg005admin = require('./eg005AuditUsers');
6+
module.exports.eg006admin = require('./eg006GetUserProfileByEmail');
7+
module.exports.eg007admin = require('./eg007GetUserProfileByUserId');
8+
module.exports.eg008admin = require('./eg008UpdateUserProductPermissionProfile');
9+
module.exports.eg009admin = require('./eg009DeleteUserProductPermissionProfile');
10+
module.exports.eg010admin = require('./eg010DeleteUserDataFromOrganization');
11+
module.exports.eg011admin = require('./eg011DeleteUserDataFromAccount');
12+
module.exports.eg012admin = require('./eg012CloneAccount');
13+
module.exports.eg013admin = require('./eg013CreateAccount');

lib/admin/examples/createAccount.js

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
const docusignAdmin = require('docusign-admin');
2+
3+
/**
4+
* This function creates an account
5+
* @param {object} args parameters for account creation
6+
* @returns {docusignAdmin.SubscriptionProvisionModelAssetGroupWorkResult} Summary of creating an account
7+
*/
8+
const createAccount = async (args) => {
9+
//ds-snippet-start:Admin13Step2
10+
const apiClient = new docusignAdmin.ApiClient();
11+
apiClient.setBasePath(args.basePath);
12+
apiClient.addDefaultHeader('Authorization', 'Bearer ' + args.accessToken);
13+
//ds-snippet-end:Admin13Step2
14+
15+
//ds-snippet-start:Admin13Step4
16+
const accountData = docusignAdmin.SubAccountCreateRequest.constructFromObject({
17+
subscriptionDetails: docusignAdmin.SubAccountCreateRequestSubAccountCreationSubscription.constructFromObject({
18+
id: args.subscriptionId,
19+
planId: args.planId,
20+
modules: [],
21+
}),
22+
targetAccount: docusignAdmin.SubAccountCreateRequestSubAccountCreationTargetAccountDetails.constructFromObject({
23+
name: 'CreatedThroughAPI',
24+
countryCode: 'US',
25+
admin: docusignAdmin.SubAccountCreateRequestSubAccountCreationTargetAccountAdmin.constructFromObject({
26+
email: args.email,
27+
firstName: args.firstName,
28+
lastName: args.lastName,
29+
locale: 'en',
30+
}),
31+
}),
32+
});
33+
//ds-snippet-end:Admin13Step4
34+
35+
//ds-snippet-start:Admin13Step5
36+
const assetGroupApi = new docusignAdmin.ProvisionAssetGroupApi(apiClient);
37+
return assetGroupApi.createAssetGroupAccount(accountData, args.organizationId);
38+
//ds-snippet-end:Admin13Step5
39+
};
40+
41+
/**
42+
* Get all plan items and return the first
43+
* @param {object} args parameters for getting the plan items
44+
* @returns {docusignAdmin.OrganizationSubscriptionResponse} Plan item data
45+
*/
46+
const getOrganizationPlanItem = async (args) => {
47+
const apiClient = new docusignAdmin.ApiClient();
48+
apiClient.setBasePath(args.basePath);
49+
apiClient.addDefaultHeader('Authorization', 'Bearer ' + args.accessToken);
50+
51+
//ds-snippet-start:Admin13Step3
52+
const assetGroupApi = new docusignAdmin.ProvisionAssetGroupApi(apiClient);
53+
const planItems = await assetGroupApi.getOrganizationPlanItems(args.organizationId);
54+
//ds-snippet-end:Admin13Step3
55+
56+
return planItems[0];
57+
};
58+
59+
module.exports = { createAccount, getOrganizationPlanItem };

package-lock.json

Lines changed: 7 additions & 6 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@
3333
"body-parser": "^1.20.2",
3434
"cookie-parser": "^1.4.6",
3535
"csurf": "^1.11.0",
36-
"docusign-admin": "^2.3.0",
36+
"docusign-admin": "^3.0.0-rc2",
3737
"docusign-click": "^2.2.0",
3838
"docusign-esign": "^8.0.0",
3939
"docusign-maestro": "1.0.0-rc5",
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<%- include("../../partials/examplesHead") %>
2+
3+
<%- include("../../partials/exampleInfo") %>
4+
5+
<form class="eg" action="" method="post" data-busy="form">
6+
<% if(example.Forms && example.Forms[0].FormName) { %>
7+
<%- example.Forms[0].FormName %>
8+
<% } %>
9+
10+
<div class="form-group">
11+
<label for="email"><%= example.Forms[0].Inputs[0].InputName %></label>
12+
<input type="email" class="form-control" id="email" name="email"
13+
placeholder="<%= example.Forms[0].Inputs[0].InputPlaceholder %>" required>
14+
</div>
15+
<div class="form-group">
16+
<label for="firstName"><%= example.Forms[0].Inputs[1].InputName %></label>
17+
<input type="text" class="form-control" id="firstName" name="firstName"
18+
placeholder="<%= example.Forms[0].Inputs[1].InputPlaceholder %>" required>
19+
</div>
20+
<div class="form-group">
21+
<label for="lastName"><%= example.Forms[0].Inputs[2].InputName %></label>
22+
<input type="text" class="form-control" id="lastName" name="lastName"
23+
placeholder="<%= example.Forms[0].Inputs[2].InputPlaceholder %>" required>
24+
</div>
25+
<input type="hidden" name="_csrf" value="<%- csrfToken %>">
26+
<%- include("../../partials/submitButton") %>
27+
</form>
28+
29+
<%- include("../../partials/examplesFoot") %>

0 commit comments

Comments
 (0)