@cubist-labs/cubesigner-sdk 0.1.26 → 0.1.77
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +94 -33
- package/dist/src/ethers/index.d.ts +25 -5
- package/dist/src/ethers/index.js +58 -16
- package/dist/src/fido.d.ts +76 -0
- package/dist/src/fido.js +148 -0
- package/dist/src/index.d.ts +148 -35
- package/dist/src/index.js +320 -53
- package/dist/src/key.d.ts +64 -8
- package/dist/src/key.js +91 -19
- package/dist/src/org.d.ts +98 -9
- package/dist/src/org.js +144 -29
- package/dist/src/paginator.d.ts +76 -0
- package/dist/src/paginator.js +99 -0
- package/dist/src/role.d.ts +20 -8
- package/dist/src/role.js +7 -5
- package/dist/src/schema.d.ts +2395 -393
- package/dist/src/schema.js +1 -1
- package/dist/src/session/cognito_manager.d.ts +59 -0
- package/dist/src/session/cognito_manager.js +111 -0
- package/dist/src/session/session_manager.d.ts +15 -0
- package/dist/src/session/session_manager.js +21 -2
- package/dist/src/session/session_storage.js +1 -1
- package/dist/src/session/signer_session_manager.d.ts +24 -12
- package/dist/src/session/signer_session_manager.js +45 -20
- package/dist/src/signer_session.d.ts +136 -38
- package/dist/src/signer_session.js +187 -80
- package/dist/src/util.d.ts +20 -0
- package/dist/src/util.js +31 -2
- package/package.json +12 -7
- package/src/ethers/index.ts +88 -16
- package/src/fido.ts +166 -0
- package/src/index.ts +366 -77
- package/src/key.ts +112 -16
- package/src/org.ts +200 -37
- package/src/paginator.ts +122 -0
- package/src/role.ts +24 -11
- package/src/schema.ts +2458 -449
- package/src/session/{management_session_manager.ts → cognito_manager.ts} +13 -15
- package/src/session/session_manager.ts +25 -1
- package/src/session/session_storage.ts +1 -1
- package/src/session/signer_session_manager.ts +57 -27
- package/src/signer_session.ts +266 -89
- package/src/util.ts +41 -0
- package/src/session/oidc_session_manager.ts +0 -193
package/dist/src/index.js
CHANGED
|
@@ -36,33 +36,76 @@ var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (
|
|
|
36
36
|
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
|
|
37
37
|
return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
|
|
38
38
|
};
|
|
39
|
-
var
|
|
39
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
40
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
41
|
+
};
|
|
42
|
+
var _TotpChallenge_cs, _TotpChallenge_totpInfo, _CubeSigner_env, _CubeSigner_orgId;
|
|
40
43
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
41
|
-
exports.ethers = exports.CubeSigner = void 0;
|
|
44
|
+
exports.ethers = exports.CubeSigner = exports.TotpChallenge = void 0;
|
|
42
45
|
const env_1 = require("./env");
|
|
43
46
|
const org_1 = require("./org");
|
|
44
47
|
const session_storage_1 = require("./session/session_storage");
|
|
48
|
+
const signer_session_manager_1 = require("./session/signer_session_manager");
|
|
45
49
|
const signer_session_1 = require("./signer_session");
|
|
46
|
-
const
|
|
47
|
-
const oidc_session_manager_1 = require("./session/oidc_session_manager");
|
|
50
|
+
const cognito_manager_1 = require("./session/cognito_manager");
|
|
48
51
|
const util_1 = require("./util");
|
|
49
52
|
const path = __importStar(require("path"));
|
|
53
|
+
const openapi_fetch_1 = __importDefault(require("openapi-fetch"));
|
|
54
|
+
const fido_1 = require("./fido");
|
|
55
|
+
/** TOTP challenge that must be answered before user's TOTP is updated */
|
|
56
|
+
class TotpChallenge {
|
|
57
|
+
/** The id of the challenge */
|
|
58
|
+
get totpId() {
|
|
59
|
+
return __classPrivateFieldGet(this, _TotpChallenge_totpInfo, "f").totp_id;
|
|
60
|
+
}
|
|
61
|
+
/** The new TOTP configuration */
|
|
62
|
+
get totpUrl() {
|
|
63
|
+
return __classPrivateFieldGet(this, _TotpChallenge_totpInfo, "f").totp_url;
|
|
64
|
+
}
|
|
65
|
+
/**
|
|
66
|
+
* @param {CubeSigner} cs Used when answering the challenge.
|
|
67
|
+
* @param {TotpInfo} totpInfo TOTP challenge information.
|
|
68
|
+
*/
|
|
69
|
+
constructor(cs, totpInfo) {
|
|
70
|
+
_TotpChallenge_cs.set(this, void 0);
|
|
71
|
+
_TotpChallenge_totpInfo.set(this, void 0);
|
|
72
|
+
__classPrivateFieldSet(this, _TotpChallenge_cs, cs, "f");
|
|
73
|
+
__classPrivateFieldSet(this, _TotpChallenge_totpInfo, totpInfo, "f");
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Answer the challenge with the code that corresponds to this `this.totpUrl`.
|
|
77
|
+
* @param {string} code 6-digit code that corresponds to this `this.totpUrl`.
|
|
78
|
+
*/
|
|
79
|
+
async answer(code) {
|
|
80
|
+
await __classPrivateFieldGet(this, _TotpChallenge_cs, "f").resetTotpComplete(this.totpId, code);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
exports.TotpChallenge = TotpChallenge;
|
|
84
|
+
_TotpChallenge_cs = new WeakMap(), _TotpChallenge_totpInfo = new WeakMap();
|
|
50
85
|
/** CubeSigner client */
|
|
51
86
|
class CubeSigner {
|
|
52
87
|
/** @return {EnvInterface} The CubeSigner environment of this client */
|
|
53
88
|
get env() {
|
|
54
89
|
return __classPrivateFieldGet(this, _CubeSigner_env, "f");
|
|
55
90
|
}
|
|
91
|
+
/**
|
|
92
|
+
* Set the organization ID
|
|
93
|
+
* @param {string} orgId The new organization id.
|
|
94
|
+
*/
|
|
95
|
+
setOrgId(orgId) {
|
|
96
|
+
__classPrivateFieldSet(this, _CubeSigner_orgId, orgId, "f");
|
|
97
|
+
}
|
|
56
98
|
/**
|
|
57
99
|
* Loads an existing management session and creates a CubeSigner instance.
|
|
58
|
-
*
|
|
100
|
+
*
|
|
101
|
+
* @param {CognitoSessionStorage} storage Optional session storage to load
|
|
59
102
|
* the session from. If not specified, the management session from the config
|
|
60
103
|
* directory will be loaded.
|
|
61
104
|
* @return {Promise<CubeSigner>} New CubeSigner instance
|
|
62
105
|
*/
|
|
63
106
|
static async loadManagementSession(storage) {
|
|
64
107
|
const defaultFilePath = path.join((0, util_1.configDir)(), "management-session.json");
|
|
65
|
-
const sessionMgr = await
|
|
108
|
+
const sessionMgr = await cognito_manager_1.CognitoSessionManager.loadFromStorage(storage ?? new session_storage_1.JsonFileSessionStorage(defaultFilePath));
|
|
66
109
|
return new CubeSigner({
|
|
67
110
|
sessionMgr,
|
|
68
111
|
});
|
|
@@ -77,82 +120,213 @@ class CubeSigner {
|
|
|
77
120
|
static async loadSignerSession(storage) {
|
|
78
121
|
const defaultFilePath = path.join((0, util_1.configDir)(), "signer-session.json");
|
|
79
122
|
const sss = storage ?? new session_storage_1.JsonFileSessionStorage(defaultFilePath);
|
|
80
|
-
|
|
81
|
-
return await signer_session_1.SignerSession.loadSignerSession(new CubeSigner({ env }), sss);
|
|
82
|
-
}
|
|
83
|
-
/**
|
|
84
|
-
* Loads a signer session from OIDC storage
|
|
85
|
-
* @param {OidcSessionStorage} storage The storage to load from
|
|
86
|
-
* @return {Promise<SignerSession>} New signer session
|
|
87
|
-
*/
|
|
88
|
-
static async loadOidcSession(storage) {
|
|
89
|
-
const env = (await storage.retrieve()).env;
|
|
90
|
-
return await signer_session_1.SignerSession.loadOidcSession(new CubeSigner({ env }), storage);
|
|
123
|
+
return await signer_session_1.SignerSession.loadSignerSession(sss);
|
|
91
124
|
}
|
|
92
125
|
/**
|
|
93
126
|
* Create a new CubeSigner instance.
|
|
94
|
-
* @param {CubeSignerOptions} options The options for the CubeSigner instance.
|
|
127
|
+
* @param {CubeSignerOptions} options The optional configuraiton options for the CubeSigner instance.
|
|
95
128
|
*/
|
|
96
129
|
constructor(options) {
|
|
97
130
|
_CubeSigner_env.set(this, void 0);
|
|
98
|
-
|
|
99
|
-
|
|
131
|
+
_CubeSigner_orgId.set(this, void 0);
|
|
132
|
+
let env = options?.env;
|
|
133
|
+
if (options?.sessionMgr) {
|
|
100
134
|
this.sessionMgr = options.sessionMgr;
|
|
101
135
|
env = env ?? this.sessionMgr.env;
|
|
102
136
|
}
|
|
103
137
|
__classPrivateFieldSet(this, _CubeSigner_env, env ?? env_1.envs["gamma"], "f");
|
|
138
|
+
__classPrivateFieldSet(this, _CubeSigner_orgId, options?.orgId, "f");
|
|
104
139
|
}
|
|
105
140
|
/**
|
|
106
|
-
* Authenticate an OIDC user and create a new
|
|
141
|
+
* Authenticate an OIDC user and create a new session manager for them.
|
|
107
142
|
* @param {string} oidcToken The OIDC token
|
|
108
143
|
* @param {string} orgId The id of the organization that the user is in
|
|
109
144
|
* @param {List<string>} scopes The scopes of the resulting session
|
|
110
|
-
* @param {
|
|
111
|
-
* @
|
|
145
|
+
* @param {RatchetConfig} lifetimes Lifetimes of the new session.
|
|
146
|
+
* @param {SignerSessionStorage?} storage Optional signer session storage (defaults to in-memory storage)
|
|
147
|
+
* @return {Promise<SignerSessionManager>} The signer session manager
|
|
112
148
|
*/
|
|
113
|
-
async
|
|
114
|
-
|
|
149
|
+
async oidcAuth(oidcToken, orgId, scopes, lifetimes, storage) {
|
|
150
|
+
const resp = await this.oidcLogin(oidcToken, orgId, scopes, lifetimes);
|
|
151
|
+
return await signer_session_manager_1.SignerSessionManager.createFromSessionInfo(this.env, orgId, resp.data(), storage);
|
|
115
152
|
}
|
|
116
153
|
/**
|
|
117
|
-
*
|
|
118
|
-
*
|
|
119
|
-
* @
|
|
120
|
-
* @param {List<string>} scopes The scopes of the resulting session
|
|
121
|
-
* @param {OidcSessionStorage} storage The signer session storage
|
|
122
|
-
* @return {Promise<SignerSession>} The signer session
|
|
154
|
+
* Retrieves information about the current user.
|
|
155
|
+
*
|
|
156
|
+
* @return {Promise<UserInfo>} User information.
|
|
123
157
|
*/
|
|
124
|
-
async createOidcSession(oidcToken, orgId, scopes, storage) {
|
|
125
|
-
const mgr = await this.createOidcManager(oidcToken, orgId, scopes, storage);
|
|
126
|
-
return await CubeSigner.loadOidcSession(mgr.storage);
|
|
127
|
-
}
|
|
128
|
-
/** Retrieves information about the current user. */
|
|
129
158
|
async aboutMe() {
|
|
130
|
-
const
|
|
131
|
-
|
|
132
|
-
|
|
159
|
+
const client = await this.management();
|
|
160
|
+
const resp = __classPrivateFieldGet(this, _CubeSigner_orgId, "f")
|
|
161
|
+
? await client.get("/v0/org/{org_id}/user/me", {
|
|
162
|
+
params: { path: { org_id: __classPrivateFieldGet(this, _CubeSigner_orgId, "f") } },
|
|
163
|
+
parseAs: "json",
|
|
164
|
+
})
|
|
165
|
+
: await client.get("/v0/about_me", {
|
|
166
|
+
parseAs: "json",
|
|
167
|
+
});
|
|
133
168
|
const data = (0, util_1.assertOk)(resp);
|
|
134
169
|
return data;
|
|
135
170
|
}
|
|
136
171
|
/**
|
|
137
|
-
*
|
|
138
|
-
*
|
|
172
|
+
* Retrieves existing MFA request.
|
|
173
|
+
*
|
|
174
|
+
* @param {string} orgId Organization ID
|
|
175
|
+
* @param {string} mfaId MFA request ID
|
|
176
|
+
* @return {Promise<MfaRequestInfo>} MFA request information
|
|
139
177
|
*/
|
|
140
|
-
async
|
|
141
|
-
const resp = await (await this.management()).
|
|
142
|
-
|
|
178
|
+
async mfaGet(orgId, mfaId) {
|
|
179
|
+
const resp = await (await this.management()).get("/v0/org/{org_id}/mfa/{mfa_id}", {
|
|
180
|
+
params: { path: { org_id: orgId, mfa_id: mfaId } },
|
|
143
181
|
});
|
|
144
182
|
return (0, util_1.assertOk)(resp);
|
|
145
183
|
}
|
|
184
|
+
/**
|
|
185
|
+
* List pending MFA requests accessible to the current user.
|
|
186
|
+
* @param {string} orgId Organization ID
|
|
187
|
+
* @return {Promise<MfaRequestInfo[]>} The MFA requests.
|
|
188
|
+
*/
|
|
189
|
+
async mfaList(orgId) {
|
|
190
|
+
const resp = await (await this.management()).get("/v0/org/{org_id}/mfa", {
|
|
191
|
+
params: { path: { org_id: orgId } },
|
|
192
|
+
});
|
|
193
|
+
return (0, util_1.assertOk)(resp).mfa_requests;
|
|
194
|
+
}
|
|
195
|
+
/**
|
|
196
|
+
* Approve a pending MFA request.
|
|
197
|
+
*
|
|
198
|
+
* @param {string} orgId The org id of the MFA request
|
|
199
|
+
* @param {string} mfaId The id of the MFA request
|
|
200
|
+
* @return {Promise<MfaRequestInfo>} The result of the MFA request
|
|
201
|
+
*/
|
|
202
|
+
async mfaApprove(orgId, mfaId) {
|
|
203
|
+
const resp = await (await this.management()).patch("/v0/org/{org_id}/mfa/{mfa_id}", {
|
|
204
|
+
params: { path: { org_id: orgId, mfa_id: mfaId } },
|
|
205
|
+
});
|
|
206
|
+
return (0, util_1.assertOk)(resp);
|
|
207
|
+
}
|
|
208
|
+
/**
|
|
209
|
+
* Initiate adding a new FIDO device. MFA may be required.
|
|
210
|
+
* @param {string} name The name of the new device.
|
|
211
|
+
* @param {MfaReceipt} mfaReceipt Optional MFA receipt to include in HTTP headers
|
|
212
|
+
* @return {Promise<SignResponse<AddFidoChallenge>>} A challenge that must be answered in order to complete FIDO registration.
|
|
213
|
+
*/
|
|
214
|
+
async addFidoStart(name, mfaReceipt) {
|
|
215
|
+
const orgId = __classPrivateFieldGet(this, _CubeSigner_orgId, "f") || mfaReceipt?.mfaOrgId;
|
|
216
|
+
if (!orgId) {
|
|
217
|
+
throw new Error("Org ID must be set");
|
|
218
|
+
}
|
|
219
|
+
const addFidoFn = async (headers) => {
|
|
220
|
+
const client = await this.management();
|
|
221
|
+
const resp = await client.post("/v0/org/{org_id}/user/me/fido", {
|
|
222
|
+
headers,
|
|
223
|
+
params: { path: { org_id: orgId } },
|
|
224
|
+
body: { name },
|
|
225
|
+
parseAs: "json",
|
|
226
|
+
});
|
|
227
|
+
const x = (0, util_1.assertOk)(resp);
|
|
228
|
+
// TODO: add mapFn to SignResponse
|
|
229
|
+
if (x.accepted?.MfaRequired) {
|
|
230
|
+
return x;
|
|
231
|
+
}
|
|
232
|
+
else {
|
|
233
|
+
return new fido_1.AddFidoChallenge(this, x);
|
|
234
|
+
}
|
|
235
|
+
};
|
|
236
|
+
return await signer_session_1.SignResponse.create(addFidoFn, mfaReceipt);
|
|
237
|
+
}
|
|
238
|
+
/**
|
|
239
|
+
* Complete a previously initiated request to add a new FIDO device.
|
|
240
|
+
* @param {string} challengeId The ID of the challenge returned by the remote end.
|
|
241
|
+
* @param {PublicKeyCredential} credential The answer to the challenge.
|
|
242
|
+
*/
|
|
243
|
+
async addFidoComplete(challengeId, credential) {
|
|
244
|
+
const orgId = __classPrivateFieldGet(this, _CubeSigner_orgId, "f");
|
|
245
|
+
if (!orgId) {
|
|
246
|
+
throw new Error("Org ID must be set");
|
|
247
|
+
}
|
|
248
|
+
const client = await this.management();
|
|
249
|
+
const resp = await client.patch("/v0/org/{org_id}/user/me/fido", {
|
|
250
|
+
params: { path: { org_id: orgId } },
|
|
251
|
+
body: {
|
|
252
|
+
challenge_id: challengeId,
|
|
253
|
+
credential,
|
|
254
|
+
},
|
|
255
|
+
parseAs: "json",
|
|
256
|
+
});
|
|
257
|
+
(0, util_1.assertOk)(resp);
|
|
258
|
+
}
|
|
259
|
+
/**
|
|
260
|
+
* Creates a request to change user's TOTP. This request returns a new TOTP challenge
|
|
261
|
+
* that must be answered by calling `resetTotpComplete`
|
|
262
|
+
*
|
|
263
|
+
* @param {MfaReceipt} mfaReceipt MFA receipt to include in HTTP headers
|
|
264
|
+
*/
|
|
265
|
+
async resetTotpStart(mfaReceipt) {
|
|
266
|
+
const resetTotpFn = async (headers) => {
|
|
267
|
+
const orgId = __classPrivateFieldGet(this, _CubeSigner_orgId, "f") || mfaReceipt?.mfaOrgId;
|
|
268
|
+
const client = await this.management();
|
|
269
|
+
const resp = orgId
|
|
270
|
+
? await client.post("/v0/org/{org_id}/user/me/totp", {
|
|
271
|
+
headers,
|
|
272
|
+
params: { path: { org_id: orgId } },
|
|
273
|
+
body: null,
|
|
274
|
+
parseAs: "json",
|
|
275
|
+
})
|
|
276
|
+
: await client.post("/v0/user/me/totp", {
|
|
277
|
+
headers,
|
|
278
|
+
body: null,
|
|
279
|
+
parseAs: "json",
|
|
280
|
+
});
|
|
281
|
+
const x = (0, util_1.assertOk)(resp);
|
|
282
|
+
// TODO: add mapFn to SignResponse
|
|
283
|
+
if (x.accepted?.MfaRequired) {
|
|
284
|
+
return x;
|
|
285
|
+
}
|
|
286
|
+
else {
|
|
287
|
+
return new TotpChallenge(this, x);
|
|
288
|
+
}
|
|
289
|
+
};
|
|
290
|
+
return await signer_session_1.SignResponse.create(resetTotpFn, mfaReceipt);
|
|
291
|
+
}
|
|
292
|
+
/**
|
|
293
|
+
* Answer the TOTP challenge issued by `resetTotpStart`. If successful, user's
|
|
294
|
+
* TOTP configuration will be updated to that of the TOTP challenge.
|
|
295
|
+
*
|
|
296
|
+
* @param {string} totpId - The ID of the TOTP challenge
|
|
297
|
+
* @param {string} code - The TOTP code that should verify against the TOTP configuration from the challenge.
|
|
298
|
+
*/
|
|
299
|
+
async resetTotpComplete(totpId, code) {
|
|
300
|
+
const client = await this.management();
|
|
301
|
+
const resp = __classPrivateFieldGet(this, _CubeSigner_orgId, "f")
|
|
302
|
+
? await client.patch("/v0/org/{org_id}/user/me/totp", {
|
|
303
|
+
parseAs: "json",
|
|
304
|
+
params: { path: { org_id: __classPrivateFieldGet(this, _CubeSigner_orgId, "f") } },
|
|
305
|
+
body: { totp_id: totpId, code },
|
|
306
|
+
})
|
|
307
|
+
: await client.patch("/v0/user/me/totp", {
|
|
308
|
+
parseAs: "json",
|
|
309
|
+
body: { totp_id: totpId, code },
|
|
310
|
+
});
|
|
311
|
+
(0, util_1.assertOk)(resp);
|
|
312
|
+
}
|
|
146
313
|
/**
|
|
147
314
|
* Verifies a given TOTP code against the current user's TOTP configuration.
|
|
148
315
|
* Throws an error if the verification fails.
|
|
149
316
|
* @param {string} code Current TOTP code
|
|
150
317
|
*/
|
|
151
318
|
async verifyTotp(code) {
|
|
152
|
-
const
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
319
|
+
const client = await this.management();
|
|
320
|
+
const resp = __classPrivateFieldGet(this, _CubeSigner_orgId, "f")
|
|
321
|
+
? await client.post("/v0/org/{org_id}/user/me/totp/verify", {
|
|
322
|
+
params: { path: { org_id: __classPrivateFieldGet(this, _CubeSigner_orgId, "f") } },
|
|
323
|
+
body: { code },
|
|
324
|
+
parseAs: "json",
|
|
325
|
+
})
|
|
326
|
+
: await client.post("/v0/user/me/totp/verify", {
|
|
327
|
+
body: { code },
|
|
328
|
+
parseAs: "json",
|
|
329
|
+
});
|
|
156
330
|
(0, util_1.assertOk)(resp);
|
|
157
331
|
}
|
|
158
332
|
/** Retrieves information about an organization.
|
|
@@ -167,6 +341,18 @@ class CubeSigner {
|
|
|
167
341
|
const data = (0, util_1.assertOk)(resp);
|
|
168
342
|
return new org_1.Org(this, data);
|
|
169
343
|
}
|
|
344
|
+
/**
|
|
345
|
+
* Deletes a given key.
|
|
346
|
+
* @param {string} orgId - Organization id
|
|
347
|
+
* @param {string} keyId - Key id
|
|
348
|
+
*/
|
|
349
|
+
async deleteKey(orgId, keyId) {
|
|
350
|
+
const resp = await (await this.management()).del("/v0/org/{org_id}/keys/{key_id}", {
|
|
351
|
+
params: { path: { org_id: orgId, key_id: keyId } },
|
|
352
|
+
parseAs: "json",
|
|
353
|
+
});
|
|
354
|
+
(0, util_1.assertOk)(resp);
|
|
355
|
+
}
|
|
170
356
|
/** Get the management client.
|
|
171
357
|
* @return {Client} The client.
|
|
172
358
|
* @internal
|
|
@@ -177,9 +363,88 @@ class CubeSigner {
|
|
|
177
363
|
}
|
|
178
364
|
return await this.sessionMgr.client();
|
|
179
365
|
}
|
|
366
|
+
/**
|
|
367
|
+
* Obtain a proof of authentication.
|
|
368
|
+
*
|
|
369
|
+
* @param {string} orgId The id of the organization that the user is in
|
|
370
|
+
* @return {Promise<IdentityProof>} Proof of authentication
|
|
371
|
+
*/
|
|
372
|
+
async proveIdentity(orgId) {
|
|
373
|
+
const client = await this.management();
|
|
374
|
+
const resp = await client.post("/v0/org/{org_id}/identity/prove", {
|
|
375
|
+
params: { path: { org_id: orgId } },
|
|
376
|
+
parseAs: "json",
|
|
377
|
+
});
|
|
378
|
+
return (0, util_1.assertOk)(resp);
|
|
379
|
+
}
|
|
380
|
+
/**
|
|
381
|
+
* Exchange an OIDC token for a proof of authentication.
|
|
382
|
+
*
|
|
383
|
+
* @param {string} oidcToken The OIDC token
|
|
384
|
+
* @param {string} orgId The id of the organization that the user is in
|
|
385
|
+
* @return {Promise<IdentityProof>} Proof of authentication
|
|
386
|
+
*/
|
|
387
|
+
async oidcProveIdentity(oidcToken, orgId) {
|
|
388
|
+
const client = (0, openapi_fetch_1.default)({
|
|
389
|
+
baseUrl: this.env.SignerApiRoot,
|
|
390
|
+
headers: {
|
|
391
|
+
Authorization: oidcToken,
|
|
392
|
+
},
|
|
393
|
+
});
|
|
394
|
+
const resp = await client.post("/v0/org/{org_id}/identity/prove/oidc", {
|
|
395
|
+
params: { path: { org_id: orgId } },
|
|
396
|
+
parseAs: "json",
|
|
397
|
+
});
|
|
398
|
+
return (0, util_1.assertOk)(resp);
|
|
399
|
+
}
|
|
400
|
+
/**
|
|
401
|
+
* Checks if a given identity proof is valid.
|
|
402
|
+
*
|
|
403
|
+
* @param {string} orgId The id of the organization that the user is in.
|
|
404
|
+
* @param {IdentityProof} identityProof The proof of authentication.
|
|
405
|
+
*/
|
|
406
|
+
async verifyIdentity(orgId, identityProof) {
|
|
407
|
+
const resp = await (await this.management()).post("/v0/org/{org_id}/identity/verify", {
|
|
408
|
+
params: { path: { org_id: orgId } },
|
|
409
|
+
body: identityProof,
|
|
410
|
+
parseAs: "json",
|
|
411
|
+
});
|
|
412
|
+
(0, util_1.assertOk)(resp);
|
|
413
|
+
}
|
|
414
|
+
/**
|
|
415
|
+
* Exchange an OIDC token for a CubeSigner session token.
|
|
416
|
+
* @param {string} oidcToken The OIDC token
|
|
417
|
+
* @param {string} orgId The id of the organization that the user is in
|
|
418
|
+
* @param {List<string>} scopes The scopes of the resulting session
|
|
419
|
+
* @param {RatchetConfig} lifetimes Lifetimes of the new session.
|
|
420
|
+
* @param {MfaReceipt} mfaReceipt Optional MFA receipt (id + confirmation code)
|
|
421
|
+
* @return {Promise<SignResponse<OidcAuthResponse>>} The session data.
|
|
422
|
+
*/
|
|
423
|
+
async oidcLogin(oidcToken, orgId, scopes, lifetimes, mfaReceipt) {
|
|
424
|
+
const client = (0, openapi_fetch_1.default)({
|
|
425
|
+
baseUrl: this.env.SignerApiRoot,
|
|
426
|
+
headers: {
|
|
427
|
+
Authorization: oidcToken,
|
|
428
|
+
},
|
|
429
|
+
});
|
|
430
|
+
const loginFn = async (headers) => {
|
|
431
|
+
const resp = await client.post("/v0/org/{org_id}/oidc", {
|
|
432
|
+
params: { path: { org_id: orgId } },
|
|
433
|
+
headers,
|
|
434
|
+
body: {
|
|
435
|
+
scopes,
|
|
436
|
+
tokens: lifetimes,
|
|
437
|
+
},
|
|
438
|
+
parseAs: "json",
|
|
439
|
+
});
|
|
440
|
+
return (0, util_1.assertOk)(resp);
|
|
441
|
+
};
|
|
442
|
+
const h1 = mfaReceipt ? signer_session_1.SignResponse.getMfaHeaders(mfaReceipt) : undefined;
|
|
443
|
+
return new signer_session_1.SignResponse(loginFn, await loginFn(h1));
|
|
444
|
+
}
|
|
180
445
|
}
|
|
181
446
|
exports.CubeSigner = CubeSigner;
|
|
182
|
-
_CubeSigner_env = new WeakMap();
|
|
447
|
+
_CubeSigner_env = new WeakMap(), _CubeSigner_orgId = new WeakMap();
|
|
183
448
|
/** Organizations */
|
|
184
449
|
__exportStar(require("./org"), exports);
|
|
185
450
|
/** Keys */
|
|
@@ -188,6 +453,10 @@ __exportStar(require("./key"), exports);
|
|
|
188
453
|
__exportStar(require("./role"), exports);
|
|
189
454
|
/** Env */
|
|
190
455
|
__exportStar(require("./env"), exports);
|
|
456
|
+
/** Fido */
|
|
457
|
+
__exportStar(require("./fido"), exports);
|
|
458
|
+
/** Pagination */
|
|
459
|
+
__exportStar(require("./paginator"), exports);
|
|
191
460
|
/** Sessions */
|
|
192
461
|
__exportStar(require("./signer_session"), exports);
|
|
193
462
|
/** Session storage */
|
|
@@ -195,11 +464,9 @@ __exportStar(require("./session/session_storage"), exports);
|
|
|
195
464
|
/** Session manager */
|
|
196
465
|
__exportStar(require("./session/session_manager"), exports);
|
|
197
466
|
/** Management session manager */
|
|
198
|
-
__exportStar(require("./session/
|
|
199
|
-
/** OIDC session manager */
|
|
200
|
-
__exportStar(require("./session/oidc_session_manager"), exports);
|
|
467
|
+
__exportStar(require("./session/cognito_manager"), exports);
|
|
201
468
|
/** Signer session manager */
|
|
202
469
|
__exportStar(require("./session/signer_session_manager"), exports);
|
|
203
470
|
/** Export ethers.js Signer */
|
|
204
471
|
exports.ethers = __importStar(require("./ethers"));
|
|
205
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSwrQkFBMkM7QUFFM0MsK0JBQTRCO0FBQzVCLCtEQUF5RjtBQUV6RixxREFBaUQ7QUFDakQscUZBRzhDO0FBQzlDLHlFQUF3RjtBQUN4RixpQ0FBNkM7QUFDN0MsMkNBQTZCO0FBYzdCLHdCQUF3QjtBQUN4QixNQUFhLFVBQVU7SUFJckIsdUVBQXVFO0lBQ3ZFLElBQUksR0FBRztRQUNMLE9BQU8sdUJBQUEsSUFBSSx1QkFBSyxDQUFDO0lBQ25CLENBQUM7SUFFRDs7Ozs7O09BTUc7SUFDSCxNQUFNLENBQUMsS0FBSyxDQUFDLHFCQUFxQixDQUFDLE9BQWtDO1FBQ25FLE1BQU0sZUFBZSxHQUFHLElBQUksQ0FBQyxJQUFJLENBQUMsSUFBQSxnQkFBUyxHQUFFLEVBQUUseUJBQXlCLENBQUMsQ0FBQztRQUMxRSxNQUFNLFVBQVUsR0FBRyxNQUFNLHFEQUF3QixDQUFDLGVBQWUsQ0FDL0QsT0FBTyxJQUFJLElBQUksd0NBQXNCLENBQUMsZUFBZSxDQUFDLENBQ3ZELENBQUM7UUFDRixPQUFPLElBQUksVUFBVSxDQUFvQjtZQUN2QyxVQUFVO1NBQ1gsQ0FBQyxDQUFDO0lBQ0wsQ0FBQztJQUVEOzs7Ozs7T0FNRztJQUNILE1BQU0sQ0FBQyxLQUFLLENBQUMsaUJBQWlCLENBQUMsT0FBOEI7UUFDM0QsTUFBTSxlQUFlLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQyxJQUFBLGdCQUFTLEdBQUUsRUFBRSxxQkFBcUIsQ0FBQyxDQUFDO1FBQ3RFLE1BQU0sR0FBRyxHQUFHLE9BQU8sSUFBSSxJQUFJLHdDQUFzQixDQUFDLGVBQWUsQ0FBQyxDQUFDO1FBQ25FLE1BQU0sR0FBRyxHQUFHLENBQUMsTUFBTSxHQUFHLENBQUMsUUFBUSxFQUFFLENBQUMs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ZSB9IGZyb20gXCIuL2VudlwiO1xuaW1wb3J0IHsgY29tcG9uZW50cywgQ2xpZW50IH0gZnJvbSBcIi4vY2xpZW50XCI7XG5pbXBvcnQgeyBPcmcgfSBmcm9tIFwiLi9vcmdcIjtcbmltcG9ydCB7IEpzb25GaWxlU2Vzc2lvblN0b3JhZ2UsIE1lbW9yeVNlc3Npb25TdG9yYWdlIH0gZnJvbSBcIi4vc2Vzc2lvbi9zZXNzaW9uX3N0b3JhZ2VcIjtcbmltcG9ydCB7IFNpZ25lclNlc3Npb25TdG9yYWdlIH0gZnJvbSBcIi4vc2Vzc2lvbi9zaWduZXJfc2Vzc2lvbl9tYW5hZ2VyXCI7XG5pbXBvcnQgeyBTaWduZXJTZXNzaW9uIH0gZnJvbSBcIi4vc2lnbmVyX3Nlc3Npb25cIjtcbmltcG9ydCB7XG4gIE1hbmFnZW1lbnRTZXNzaW9uTWFuYWdlcixcbiAgTWFuYWdlbWVudFNlc3Npb25TdG9yYWdlLFxufSBmcm9tIFwiLi9zZXNzaW9uL21hbmFnZW1lbnRfc2Vzc2lvbl9tYW5hZ2VyXCI7XG5pbXBvcnQgeyBPaWRjU2Vzc2lvbk1hbmFnZXIsIE9pZGNTZXNzaW9uU3RvcmFnZSB9IGZyb20gXCIuL3Nlc3Npb24vb2lkY19zZXNzaW9uX21hbmFnZXJcIjtcbmltcG9ydCB7IGFzc2VydE9rLCBjb25maWdEaXIgfSBmcm9tIFwiLi91dGlsXCI7XG5pbXBvcnQgKiBhcyBwYXRoIGZyb20gXCJwYXRoXCI7XG5cbi8qKiBDdWJlU2lnbmVyIGNvbnN0cnVjdG9yIG9wdGlvbnMgKi9cbmV4cG9ydCBpbnRlcmZhY2UgQ3ViZVNpZ25lck9wdGlvbnMge1xuICAvKiogVGhlIGVudmlyb25tZW50IHRvIHVzZSAqL1xuICBlbnY/OiBFbnZJbnRlcmZhY2U7XG4gIC8qKiBUaGUgbWFuYWdlbWVudCBhdXRob3JpemF0aW9uIHRva2VuICovXG4gIHNlc3Npb25NZ3I/OiBNYW5hZ2VtZW50U2Vzc2lvbk1hbmFnZXIgfCBPaWRjU2Vzc2lvbk1hbmFnZXI7XG59XG5cbmV4cG9ydCB0eXBlIFVzZXJJbmZvID0gY29tcG9uZW50c1tcInNjaGVtYXNcIl1bXCJVc2VySW5mb1wiXTtcbmV4cG9ydCB0eXBlIFRvdHBJbmZvID0gY29tcG9uZW50c1tcInJlc3BvbnNlc1wiXVtcIlRvdHBJbmZvXCJdW1wiY29udGVudFwiXVtcImFwcGxpY2F0aW9uL2pzb25cIl07XG5leHBvcnQgdHlwZSBDb25maWd1cmVkTWZhID0gY29tcG9uZW50c1tcInNjaGVtYXNcIl1bXCJDb25maWd1cmVkTWZhXCJdO1xuXG4vKiogQ3ViZVNpZ25lciBjbGllbnQgKi9cbmV4cG9ydCBjbGFzcyBDdWJlU2lnbmVyIHtcbiAgcmVhZG9ubHkgI2VudjogRW52SW50ZXJmYWNlO1xuICByZWFkb25seSBzZXNzaW9uTWdyPzogTWFuYWdlbWVudFNlc3Npb25NYW5hZ2VyIHwgT2lkY1Nlc3Npb25NYW5hZ2VyO1xuXG4gIC8qKiBAcmV0dXJuIHtFbnZJbnRlcmZhY2V9IFRoZSBDdWJlU2lnbmVyIGVudmlyb25tZW50IG9mIHRoaXMgY2xpZW50ICovXG4gIGdldCBlbnYoKTogRW52SW50ZXJmYWNlIHtcbiAgICByZXR1cm4gdGhpcy4jZW52O1xuICB9XG5cbiAgLyoqXG4gICAqIExvYWRzIGFuIGV4aXN0aW5nIG1hbmFnZW1lbnQgc2Vzc2lvbiBhbmQgY3JlYXRlcyBhIEN1YmVTaWduZXIgaW5zdGFuY2UuXG4gICAqIEBwYXJhbSB7TWFuYWdlbWVudFNlc3Npb25TdG9yYWdlfSBzdG9yYWdlIE9wdGlvbmFsIHNlc3Npb24gc3RvcmFnZSB0byBsb2FkXG4gICAqIHRoZSBzZXNzaW9uIGZyb20uIElmIG5vdCBzcGVjaWZpZWQsIHRoZSBtYW5hZ2VtZW50IHNlc3Npb24gZnJvbSB0aGUgY29uZmlnXG4gICAqIGRpcmVjdG9yeSB3aWxsIGJlIGxvYWRlZC5cbiAgICogQHJldHVybiB7UHJvbWlzZTxDdWJlU2lnbmVyPn0gTmV3IEN1YmVTaWduZXIgaW5zdGFuY2VcbiAgICovXG4gIHN0YXRpYyBhc3luYyBsb2FkTWFuYWdlbWVudFNlc3Npb24oc3RvcmFnZT86IE1hbmFnZW1lbnRTZXNzaW9uU3RvcmFnZSk6IFByb21pc2U8Q3ViZVNpZ25lcj4ge1xuICAgIGNvbnN0IGRlZmF1bHRGaWxlUGF0aCA9IHBhdGguam9pbihjb25maWdEaXIoKSwgXCJtYW5hZ2VtZW50LXNlc3Npb24uanNvblwiKTtcbiAgICBjb25zdCBzZXNzaW9uTWdyID0gYXdhaXQgTWFuYWdlbWVudFNlc3Npb25NYW5hZ2VyLmxvYWRGcm9tU3RvcmFnZShcbiAgICAgIHN0b3JhZ2UgPz8gbmV3IEpzb25GaWxlU2Vzc2lvblN0b3JhZ2UoZGVmYXVsdEZpbGVQYXRoKSxcbiAgICApO1xuICAgIHJldHVybiBuZXcgQ3ViZVNpZ25lcig8Q3ViZVNpZ25lck9wdGlvbnM+e1xuICAgICAgc2Vzc2lvbk1ncixcbiAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBMb2FkcyBhIHNpZ25lciBzZXNzaW9uIGZyb20gYSBzZXNzaW9uIHN0b3JhZ2UgKGUuZy4sIHNlc3Npb24gZmlsZSkuXG4gICAqIEBwYXJhbSB7U2lnbmVyU2Vzc2lvblN0b3JhZ2V9IHN0b3JhZ2UgT3B0aW9uYWwgc2Vzc2lvbiBzdG9yYWdlIHRvIGxvYWRcbiAgICogdGhlIHNlc3Npb24gZnJvbS4gSWYgbm90IHNwZWNpZmllZCwgdGhlIHNpZ25lciBzZXNzaW9uIGZyb20gdGhlIGNvbmZpZ1xuICAgKiBkaXJlY3Rvcnkgd2lsbCBiZSBsb2FkZWQuXG4gICAqIEByZXR1cm4ge1Byb21pc2U8U2lnbmVyU2Vzc2lvbj59IE5ldyBzaWduZXIgc2Vzc2lvblxuICAgKi9cbiAgc3RhdGljIGFzeW5jIGxvYWRTaWduZXJTZXNzaW9uKHN0b3JhZ2U/OiBTaWduZXJTZXNzaW9uU3RvcmFnZSk6IFByb21pc2U8U2lnbmVyU2Vzc2lvbj4ge1xuICAgIGNvbnN0IGRlZmF1bHRGaWxlUGF0aCA9IHBhdGguam9pbihjb25maWdEaXIoKSwgXCJzaWduZXItc2Vzc2lvbi5qc29uXCIpO1xuICAgIGNvbnN0IHNzcyA9IHN0b3JhZ2UgPz8gbmV3IEpzb25GaWxlU2Vzc2lvblN0b3JhZ2UoZGVmYXVsdEZpbGVQYXRoKTtcbiAgICBjb25zdCBlbnYgPSAoYXdhaXQgc3NzLnJldHJpZXZlKCkpLmVudltcIkRldi1DdWJlU2lnbmVyU3RhY2tcIl07XG4gICAgcmV0dXJuIGF3YWl0IFNpZ25lclNlc3Npb24ubG9hZFNpZ25lclNlc3Npb24obmV3IEN1YmVTaWduZXIoeyBlbnYgfSksIHNzcyk7XG4gIH1cblxuICAvKipcbiAgICogTG9hZHMgYSBzaWduZXIgc2Vzc2lvbiBmcm9tIE9JREMgc3RvcmFnZVxuICAgKiBAcGFyYW0ge09pZGNTZXNzaW9uU3RvcmFnZX0gc3RvcmFnZSBUaGUgc3RvcmFnZSB0byBsb2FkIGZyb21cbiAgICogQHJldHVybiB7UHJvbWlzZTxTaWduZXJTZXNzaW9uPn0gTmV3IHNpZ25lciBzZXNzaW9uXG4gICAqL1xuICBzdGF0aWMgYXN5bmMgbG9hZE9pZGNTZXNzaW9uKHN0b3JhZ2U6IE9pZGNTZXNzaW9uU3RvcmFnZSk6IFByb21pc2U8U2lnbmVyU2Vzc2lvbj4ge1xuICAgIGNvbnN0IGVudiA9IChhd2FpdCBzdG9yYWdlLnJldHJpZXZlKCkpLmVudjtcbiAgICByZXR1cm4gYXdhaXQgU2lnbmVyU2Vzc2lvbi5sb2FkT2lkY1Nlc3Npb24obmV3IEN1YmVTaWduZXIoeyBlbnYgfSksIHN0b3JhZ2UpO1xuICB9XG5cbiAgLyoqXG4gICAqIENyZWF0ZSBhIG5ldyBDdWJlU2lnbmVyIGluc3RhbmNlLlxuICAgKiBAcGFyYW0ge0N1YmVTaWduZXJPcHRpb25zfSBvcHRpb25zIFRoZSBvcHRpb25zIGZvciB0aGUgQ3ViZVNpZ25lciBpbnN0YW5jZS5cbiAgICovXG4gIGNvbnN0cnVjdG9yKG9wdGlvbnM6IEN1YmVTaWduZXJPcHRpb25zKSB7XG4gICAgbGV0IGVudiA9IG9wdGlvbnMuZW52O1xuICAgIGlmIChvcHRpb25zLnNlc3Npb25NZ3IpIHtcbiAgICAgIHRoaXMuc2Vzc2lvbk1nciA9IG9wdGlvbnMuc2Vzc2lvbk1ncjtcbiAgICAgIGVudiA9IGVudiA/PyB0aGlzLnNlc3Npb25NZ3IuZW52O1xuICAgIH1cbiAgICB0aGlzLiNlbnYgPSBlbnYgPz8gZW52c1tcImdhbW1hXCJdO1xuICB9XG5cbiAgLyoqXG4gICAqIEF1dGhlbnRpY2F0ZSBhbiBPSURDIHVzZXIgYW5kIGNyZWF0ZSBhIG5ldyBPSURDIHNlc3Npb24gbWFuYWdlciBmb3IgdGhlbS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9pZGNUb2tlbiBUaGUgT0lEQyB0b2tlblxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIGlkIG9mIHRoZSBvcmdhbml6YXRpb24gdGhhdCB0aGUgdXNlciBpcyBpblxuICAgKiBAcGFyYW0ge0xpc3Q8c3RyaW5nPn0gc2NvcGVzIFRoZSBzY29wZXMgb2YgdGhlIHJlc3VsdGluZyBzZXNzaW9uXG4gICAqIEBwYXJhbSB7T2lkY1Nlc3Npb25TdG9yYWdlfSBzdG9yYWdlIFRoZSBzaWduZXIgc2Vzc2lvbiBzdG9yYWdlXG4gICAqIEByZXR1cm4ge1Byb21pc2U8T2lkY1Nlc3Npb25NYW5hZ2VyPn0gVGhlIE9JREMgc2Vzc2lvbiBtYW5hZ2VyXG4gICAqL1xuICBhc3luYyBjcmVhdGVPaWRjTWFuYWdlcihcbiAgICBvaWRjVG9rZW46IHN0cmluZyxcbiAgICBvcmdJZDogc3RyaW5nLFxuICAgIHNjb3BlczogQXJyYXk8c3RyaW5nPixcbiAgICBzdG9yYWdlPzogT2lkY1Nlc3Npb25TdG9yYWdlLFxuICApOiBQcm9taXNlPE9pZGNTZXNzaW9uTWFuYWdlcj4ge1xuICAgIHJldHVybiBhd2FpdCBPaWRjU2Vzc2lvbk1hbmFnZXIuY3JlYXRlKFxuICAgICAgdGhpcy5lbnYsXG4gICAgICBzdG9yYWdlIHx8IG5ldyBNZW1vcnlTZXNzaW9uU3RvcmFnZSgpLFxuICAgICAgb2lkY1Rva2VuLFxuICAgICAgb3JnSWQsXG4gICAgICBzY29wZXMsXG4gICAgKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBBdXRoZW50aWNhdGUgYW4gT0lEQyB1c2VyIGFuZCBjcmVhdGUgYSBuZXcgc2Vzc2lvbiBmb3IgdGhlbS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9pZGNUb2tlbiBUaGUgT0lEQyB0b2tlblxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIGlkIG9mIHRoZSBvcmdhbml6YXRpb24gdGhhdCB0aGUgdXNlciBpcyBpblxuICAgKiBAcGFyYW0ge0xpc3Q8c3RyaW5nPn0gc2NvcGVzIFRoZSBzY29wZXMgb2YgdGhlIHJlc3VsdGluZyBzZXNzaW9uXG4gICAqIEBwYXJhbSB7T2lkY1Nlc3Npb25TdG9yYWdlfSBzdG9yYWdlIFRoZSBzaWduZXIgc2Vzc2lvbiBzdG9yYWdlXG4gICAqIEByZXR1cm4ge1Byb21pc2U8U2lnbmVyU2Vzc2lvbj59IFRoZSBzaWduZXIgc2Vzc2lvblxuICAgKi9cbiAgYXN5bmMgY3JlYXRlT2lkY1Nlc3Npb24oXG4gICAgb2lkY1Rva2VuOiBzdHJpbmcsXG4gICAgb3JnSWQ6IHN0cmluZyxcbiAgICBzY29wZXM6IEFycmF5PHN0cmluZz4sXG4gICAgc3RvcmFnZT86IE9pZGNTZXNzaW9uU3RvcmFnZSxcbiAgKTogUHJvbWlzZTxTaWduZXJTZXNzaW9uPiB7XG4gICAgY29uc3QgbWdyID0gYXdhaXQgdGhpcy5jcmVhdGVPaWRjTWFuYWdlcihvaWRjVG9rZW4sIG9yZ0lkLCBzY29wZXMsIHN0b3JhZ2UpO1xuICAgIHJldHVybiBhd2FpdCBDdWJlU2lnbmVyLmxvYWRPaWRjU2Vzc2lvbihtZ3Iuc3RvcmFnZSk7XG4gIH1cblxuICAvKiogUmV0cmlldmVzIGluZm9ybWF0aW9uIGFib3V0IHRoZSBjdXJyZW50IHVzZXIuICovXG4gIGFzeW5jIGFib3V0TWUoKTogUHJvbWlzZTxVc2VySW5mbz4ge1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCAoXG4gICAgICBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKVxuICAgICkuZ2V0KFwiL3YwL2Fib3V0X21lXCIsIHtcbiAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgIH0pO1xuICAgIGNvbnN0IGRhdGEgPSBhc3NlcnRPayhyZXNwKTtcbiAgICByZXR1cm4gZGF0YTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGVzIGFuZCBzZXRzIGEgbmV3IFRPVFAgY29uZmlndXJhdGlvbiBmb3IgdGhlIGxvZ2dlZC1pbiB1c2VyLFxuICAgKiBvdmVycmlkaW5nIHRoZSBleGlzdGluZyBvbmUgKGlmIGFueSkuXG4gICAqL1xuICBhc3luYyByZXNldFRvdHAoKTogUHJvbWlzZTxUb3RwSW5mbz4ge1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCAoXG4gICAgICBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKVxuICAgICkucGF0Y2goXCIvdjAvdG90cFwiLCB7XG4gICAgICBwYXJzZUFzOiBcImpzb25cIixcbiAgICB9KTtcbiAgICByZXR1cm4gYXNzZXJ0T2socmVzcCk7XG4gIH1cblxuICAvKipcbiAgICogVmVyaWZpZXMgYSBnaXZlbiBUT1RQIGNvZGUgYWdhaW5zdCB0aGUgY3VycmVudCB1c2VyJ3MgVE9UUCBjb25maWd1cmF0aW9uLlxuICAgKiBUaHJvd3MgYW4gZXJyb3IgaWYgdGhlIHZlcmlmaWNhdGlvbiBmYWlscy5cbiAgICogQHBhcmFtIHtzdHJpbmd9IGNvZGUgQ3VycmVudCBUT1RQIGNvZGVcbiAgICovXG4gIGFzeW5jIHZlcmlmeVRvdHAoY29kZTogc3RyaW5nKSB7XG4gICAgY29uc3QgcmVzcCA9IGF3YWl0IChcbiAgICAgIGF3YWl0IHRoaXMubWFuYWdlbWVudCgpXG4gICAgKS5nZXQoXCIvdjAvdG90cC92ZXJpZnkve2NvZGV9XCIsIHtcbiAgICAgIHBhcmFtczogeyBwYXRoOiB7IGNvZGUgfSB9LFxuICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgfSk7XG4gICAgYXNzZXJ0T2socmVzcCk7XG4gIH1cblxuICAvKiogUmV0cmlldmVzIGluZm9ybWF0aW9uIGFib3V0IGFuIG9yZ2FuaXphdGlvbi5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9yZ0lkIFRoZSBJRCBvciBuYW1lIG9mIHRoZSBvcmdhbml6YXRpb24uXG4gICAqIEByZXR1cm4ge09yZ30gVGhlIG9yZ2FuaXphdGlvbi5cbiAgICogKi9cbiAgYXN5bmMgZ2V0T3JnKG9yZ0lkOiBzdHJpbmcpOiBQcm9taXNlPE9yZz4ge1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCAoXG4gICAgICBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKVxuICAgICkuZ2V0KFwiL3YwL29yZy97b3JnX2lkfVwiLCB7XG4gICAgICBwYXJhbXM6IHsgcGF0aDogeyBvcmdfaWQ6IG9yZ0lkIH0gfSxcbiAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgIH0pO1xuXG4gICAgY29uc3QgZGF0YSA9IGFzc2VydE9rKHJlc3ApO1xuICAgIHJldHVybiBuZXcgT3JnKHRoaXMsIGRhdGEpO1xuICB9XG5cbiAgLyoqIEdldCB0aGUgbWFuYWdlbWVudCBjbGllbnQuXG4gICAqIEByZXR1cm4ge0NsaWVudH0gVGhlIGNsaWVudC5cbiAgICogQGludGVybmFsXG4gICAqICovXG4gIGFzeW5jIG1hbmFnZW1lbnQoKTogUHJvbWlzZTxDbGllbnQ+IHtcbiAgICBpZiAoIXRoaXMuc2Vzc2lvbk1ncikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiTm8gbWFuYWdlbWVudCBzZXNzaW9uIGxvYWRlZFwiKTtcbiAgICB9XG4gICAgcmV0dXJuIGF3YWl0IHRoaXMuc2Vzc2lvbk1nci5jbGllbnQoKTtcbiAgfVxufVxuXG4vKiogT3JnYW5pemF0aW9ucyAqL1xuZXhwb3J0ICogZnJvbSBcIi4vb3JnXCI7XG4vKiogS2V5cyAqL1xuZXhwb3J0ICogZnJvbSBcIi4va2V5XCI7XG4vKiogUm9sZXMgKi9cbmV4cG9ydCAqIGZyb20gXCIuL3JvbGVcIjtcbi8qKiBFbnYgKi9cbmV4cG9ydCAqIGZyb20gXCIuL2VudlwiO1xuLyoqIFNlc3Npb25zICovXG5leHBvcnQgKiBmcm9tIFwiLi9zaWduZXJfc2Vzc2lvblwiO1xuLyoqIFNlc3Npb24gc3RvcmFnZSAqL1xuZXhwb3J0ICogZnJvbSBcIi4vc2Vzc2lvbi9zZXNzaW9uX3N0b3JhZ2VcIjtcbi8qKiBTZXNzaW9uIG1hbmFnZXIgKi9cbmV4cG9ydCAqIGZyb20gXCIuL3Nlc3Npb24vc2Vzc2lvbl9tYW5hZ2VyXCI7XG4vKiogTWFuYWdlbWVudCBzZXNzaW9uIG1hbmFnZXIgKi9cbmV4cG9ydCAqIGZyb20gXCIuL3Nlc3Npb24vbWFuYWdlbWVudF9zZXNzaW9uX21hbmFnZXJcIjtcbi8qKiBPSURDIHNlc3Npb24gbWFuYWdlciAqL1xuZXhwb3J0ICogZnJvbSBcIi4vc2Vzc2lvbi9vaWRjX3Nlc3Npb25fbWFuYWdlclwiO1xuLyoqIFNpZ25lciBzZXNzaW9uIG1hbmFnZXIgKi9cbmV4cG9ydCAqIGZyb20gXCIuL3Nlc3Npb24vc2lnbmVyX3Nlc3Npb25fbWFuYWdlclwiO1xuLyoqIEV4cG9ydCBldGhlcnMuanMgU2lnbmVyICovXG5leHBvcnQgKiBhcyBldGhlcnMgZnJvbSBcIi4vZXRoZXJzXCI7XG4iXX0=
|
|
472
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQSwrQkFBMkM7QUFFM0MsK0JBQTRCO0FBQzVCLCtEQUFtRTtBQUVuRSw2RUFBOEY7QUFDOUYscURBQWlHO0FBQ2pHLCtEQUF5RjtBQUN6RixpQ0FBNkM7QUFDN0MsMkNBQTZCO0FBQzdCLGtFQUF5QztBQUN6QyxpQ0FBb0Y7QUFxQnBGLHlFQUF5RTtBQUN6RSxNQUFhLGFBQWE7SUFHeEIsOEJBQThCO0lBQzlCLElBQUksTUFBTTtRQUNSLE9BQU8sdUJBQUEsSUFBSSwrQkFBVSxDQUFDLE9BQU8sQ0FBQztJQUNoQyxDQUFDO0lBQ0QsaUNBQWlDO0lBQ2pDLElBQUksT0FBTztRQUNULE9BQU8sdUJBQUEsSUFBSSwrQkFBVSxDQUFDLFFBQVEsQ0FBQztJQUNqQyxDQUFDO0lBQ0Q7OztPQUdHO0lBQ0gsWUFBWSxFQUFjLEVBQUUsUUFBa0I7UUFkckMsb0NBQWdCO1FBQ2hCLDBDQUFvQjtRQWMzQix1QkFBQSxJQUFJLHFCQUFPLEVBQUUsTUFBQSxDQUFDO1FBQ2QsdUJBQUEsSUFBSSwyQkFBYSxRQUFRLE1BQUEsQ0FBQztJQUM1QixDQUFDO0lBQ0Q7OztPQUdHO0lBQ0gsS0FBSyxDQUFDLE1BQU0sQ0FBQyxJQUFZO1FBQ3ZCLE1BQU0sdUJBQUEsSUFBSSx5QkFBSSxDQUFDLGlCQUFpQixDQUFDLElBQUksQ0FBQyxNQUFNLEVBQUUsSUFBSSxDQUFDLENBQUM7SUFDdEQsQ0FBQztDQUNGO0FBMUJELHNDQTBCQzs7QUFFRCx3QkFBd0I7QUFDeEIsTUFBYSxVQUFVO0lBS3JCLHVFQUF1RTtJQUN2RSxJQUFJLEdBQUc7UUFDTCxPQUFPLHVCQUFBLElBQUksdUJBQUssQ0FBQztJQUNuQixDQUFDO0lBRUQ7OztPQUdHO0lBQ0gsUUFBUSxDQUFDLEtB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RSxHQUFHLFVBQVUsQ0FBQyxDQUFDLENBQUMsNkJBQVksQ0FBQyxhQUFhLENBQUMsVUFBVSxDQUFDLENBQUMsQ0FBQyxDQUFDLFNBQVMsQ0FBQztRQUMzRSxPQUFPLElBQUksNkJBQVksQ0FBQyxPQUFPLEVBQUUsTUFBTSxPQUFPLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQztJQUN0RCxDQUFDO0NBQ0Y7QUEzWkQsZ0NBMlpDOztBQVlELG9CQUFvQjtBQUNwQix3Q0FBc0I7QUFDdEIsV0FBVztBQUNYLHdDQUFzQjtBQUN0QixZQUFZO0FBQ1oseUNBQXVCO0FBQ3ZCLFVBQVU7QUFDVix3Q0FBc0I7QUFDdEIsV0FBVztBQUNYLHlDQUF1QjtBQUN2QixpQkFBaUI7QUFDakIsOENBQTRCO0FBQzVCLGVBQWU7QUFDZixtREFBaUM7QUFDakMsc0JBQXNCO0FBQ3RCLDREQUEwQztBQUMxQyxzQkFBc0I7QUFDdEIsNERBQTBDO0FBQzFDLGlDQUFpQztBQUNqQyw0REFBMEM7QUFDMUMsNkJBQTZCO0FBQzdCLG1FQUFpRDtBQUNqRCw4QkFBOEI7QUFDOUIsbURBQW1DIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgZW52cywgRW52SW50ZXJmYWNlIH0gZnJvbSBcIi4vZW52XCI7XG5pbXBvcnQgeyBjb21wb25lbnRzLCBDbGllbnQsIHBhdGhzIH0gZnJvbSBcIi4vY2xpZW50XCI7XG5pbXBvcnQgeyBPcmcgfSBmcm9tIFwiLi9vcmdcIjtcbmltcG9ydCB7IEpzb25GaWxlU2Vzc2lvblN0b3JhZ2UgfSBmcm9tIFwiLi9zZXNzaW9uL3Nlc3Npb25fc3RvcmFnZVwiO1xuXG5pbXBvcnQgeyBTaWduZXJTZXNzaW9uU3RvcmFnZSwgU2lnbmVyU2Vzc2lvbk1hbmFnZXIgfSBmcm9tIFwiLi9zZXNzaW9uL3NpZ25lcl9zZXNzaW9uX21hbmFnZXJcIjtcbmltcG9ydCB7IEFjY2VwdGVkUmVzcG9uc2UsIE1mYVJlcXVlc3RJbmZvLCBTaWduUmVzcG9uc2UsIFNpZ25lclNlc3Npb24gfSBmcm9tIFwiLi9zaWduZXJfc2Vzc2lvblwiO1xuaW1wb3J0IHsgQ29nbml0b1Nlc3Npb25NYW5hZ2VyLCBDb2duaXRvU2Vzc2lvblN0b3JhZ2UgfSBmcm9tIFwiLi9zZXNzaW9uL2NvZ25pdG9fbWFuYWdlclwiO1xuaW1wb3J0IHsgYXNzZXJ0T2ssIGNvbmZpZ0RpciB9IGZyb20gXCIuL3V0aWxcIjtcbmltcG9ydCAqIGFzIHBhdGggZnJvbSBcInBhdGhcIjtcbmltcG9ydCBjcmVhdGVDbGllbnQgZnJvbSBcIm9wZW5hcGktZmV0Y2hcIjtcbmltcG9ydCB7IEFkZEZpZG9DaGFsbGVuZ2UsIEFwaUFkZEZpZG9DaGFsbGVuZ2UsIFB1YmxpY0tleUNyZWRlbnRpYWwgfSBmcm9tIFwiLi9maWRvXCI7XG5cbi8qKiBDdWJlU2lnbmVyIGNvbnN0cnVjdG9yIG9wdGlvbnMgKi9cbmV4cG9ydCBpbnRlcmZhY2UgQ3ViZVNpZ25lck9wdGlvbnMge1xuICAvKiogVGhlIGVudmlyb25tZW50IHRvIHVzZSAqL1xuICBlbnY/OiBFbnZJbnRlcmZhY2U7XG4gIC8qKiBUaGUgbWFuYWdlbWVudCBhdXRob3JpemF0aW9uIHRva2VuICovXG4gIHNlc3Npb25NZ3I/OiBDb2duaXRvU2Vzc2lvbk1hbmFnZXIgfCBTaWduZXJTZXNzaW9uTWFuYWdlcjtcbiAgLyoqIE9wdGlvbmFsIG9yZ2FuaXphdGlvbiBpZCAqL1xuICBvcmdJZD86IHN0cmluZztcbn1cblxuZXhwb3J0IHR5cGUgVXNlckluZm8gPSBjb21wb25lbnRzW1wic2NoZW1hc1wiXVtcIlVzZXJJbmZvXCJdO1xuZXhwb3J0IHR5cGUgVG90cEluZm8gPSBjb21wb25lbnRzW1wicmVzcG9uc2VzXCJdW1wiVG90cEluZm9cIl1bXCJjb250ZW50XCJdW1wiYXBwbGljYXRpb24vanNvblwiXTtcbmV4cG9ydCB0eXBlIENvbmZpZ3VyZWRNZmEgPSBjb21wb25lbnRzW1wic2NoZW1hc1wiXVtcIkNvbmZpZ3VyZWRNZmFcIl07XG5leHBvcnQgdHlwZSBSYXRjaGV0Q29uZmlnID0gY29tcG9uZW50c1tcInNjaGVtYXNcIl1bXCJSYXRjaGV0Q29uZmlnXCJdO1xuZXhwb3J0IHR5cGUgSWRlbnRpdHlQcm9vZiA9IGNvbXBvbmVudHNbXCJzY2hlbWFzXCJdW1wiSWRlbnRpdHlQcm9vZlwiXTtcblxudHlwZSBPaWRjQXV0aFJlc3BvbnNlID1cbiAgcGF0aHNbXCIvdjAvb3JnL3tvcmdfaWR9L29pZGNcIl1bXCJwb3N0XCJdW1wicmVzcG9uc2VzXCJdW1wiMjAwXCJdW1wiY29udGVudFwiXVtcImFwcGxpY2F0aW9uL2pzb25cIl07XG5cbi8qKiBUT1RQIGNoYWxsZW5nZSB0aGF0IG11c3QgYmUgYW5zd2VyZWQgYmVmb3JlIHVzZXIncyBUT1RQIGlzIHVwZGF0ZWQgKi9cbmV4cG9ydCBjbGFzcyBUb3RwQ2hhbGxlbmdlIHtcbiAgcmVhZG9ubHkgI2NzOiBDdWJlU2lnbmVyO1xuICByZWFkb25seSAjdG90cEluZm86IFRvdHBJbmZvO1xuICAvKiogVGhlIGlkIG9mIHRoZSBjaGFsbGVuZ2UgKi9cbiAgZ2V0IHRvdHBJZCgpIHtcbiAgICByZXR1cm4gdGhpcy4jdG90cEluZm8udG90cF9pZDtcbiAgfVxuICAvKiogVGhlIG5ldyBUT1RQIGNvbmZpZ3VyYXRpb24gKi9cbiAgZ2V0IHRvdHBVcmwoKSB7XG4gICAgcmV0dXJuIHRoaXMuI3RvdHBJbmZvLnRvdHBfdXJsO1xuICB9XG4gIC8qKlxuICAgKiBAcGFyYW0ge0N1YmVTaWduZXJ9IGNzIFVzZWQgd2hlbiBhbnN3ZXJpbmcgdGhlIGNoYWxsZW5nZS5cbiAgICogQHBhcmFtIHtUb3RwSW5mb30gdG90cEluZm8gVE9UUCBjaGFsbGVuZ2UgaW5mb3JtYXRpb24uXG4gICAqL1xuICBjb25zdHJ1Y3RvcihjczogQ3ViZVNpZ25lciwgdG90cEluZm86IFRvdHBJbmZvKSB7XG4gICAgdGhpcy4jY3MgPSBjcztcbiAgICB0aGlzLiN0b3RwSW5mbyA9IHRvdHBJbmZvO1xuICB9XG4gIC8qKlxuICAgKiBBbnN3ZXIgdGhlIGNoYWxsZW5nZSB3aXRoIHRoZSBjb2RlIHRoYXQgY29ycmVzcG9uZHMgdG8gdGhpcyBgdGhpcy50b3RwVXJsYC5cbiAgICogQHBhcmFtIHtzdHJpbmd9IGNvZGUgNi1kaWdpdCBjb2RlIHRoYXQgY29ycmVzcG9uZHMgdG8gdGhpcyBgdGhpcy50b3RwVXJsYC5cbiAgICovXG4gIGFzeW5jIGFuc3dlcihjb2RlOiBzdHJpbmcpIHtcbiAgICBhd2FpdCB0aGlzLiNjcy5yZXNldFRvdHBDb21wbGV0ZSh0aGlzLnRvdHBJZCwgY29kZSk7XG4gIH1cbn1cblxuLyoqIEN1YmVTaWduZXIgY2xpZW50ICovXG5leHBvcnQgY2xhc3MgQ3ViZVNpZ25lciB7XG4gIHJlYWRvbmx5ICNlbnY6IEVudkludGVyZmFjZTtcbiAgcmVhZG9ubHkgc2Vzc2lvbk1ncj86IENvZ25pdG9TZXNzaW9uTWFuYWdlciB8IFNpZ25lclNlc3Npb25NYW5hZ2VyO1xuICAjb3JnSWQ/OiBzdHJpbmc7XG5cbiAgLyoqIEByZXR1cm4ge0VudkludGVyZmFjZX0gVGhlIEN1YmVTaWduZXIgZW52aXJvbm1lbnQgb2YgdGhpcyBjbGllbnQgKi9cbiAgZ2V0IGVudigpOiBFbnZJbnRlcmZhY2Uge1xuICAgIHJldHVybiB0aGlzLiNlbnY7XG4gIH1cblxuICAvKipcbiAgICogU2V0IHRoZSBvcmdhbml6YXRpb24gSURcbiAgICogQHBhcmFtIHtzdHJpbmd9IG9yZ0lkIFRoZSBuZXcgb3JnYW5pemF0aW9uIGlkLlxuICAgKi9cbiAgc2V0T3JnSWQob3JnSWQ6IHN0cmluZykge1xuICAgIHRoaXMuI29yZ0lkID0gb3JnSWQ7XG4gIH1cblxuICAvKipcbiAgICogTG9hZHMgYW4gZXhpc3RpbmcgbWFuYWdlbWVudCBzZXNzaW9uIGFuZCBjcmVhdGVzIGEgQ3ViZVNpZ25lciBpbnN0YW5jZS5cbiAgICpcbiAgICogQHBhcmFtIHtDb2duaXRvU2Vzc2lvblN0b3JhZ2V9IHN0b3JhZ2UgT3B0aW9uYWwgc2Vzc2lvbiBzdG9yYWdlIHRvIGxvYWRcbiAgICogdGhlIHNlc3Npb24gZnJvbS4gSWYgbm90IHNwZWNpZmllZCwgdGhlIG1hbmFnZW1lbnQgc2Vzc2lvbiBmcm9tIHRoZSBjb25maWdcbiAgICogZGlyZWN0b3J5IHdpbGwgYmUgbG9hZGVkLlxuICAgKiBAcmV0dXJuIHtQcm9taXNlPEN1YmVTaWduZXI+fSBOZXcgQ3ViZVNpZ25lciBpbnN0YW5jZVxuICAgKi9cbiAgc3RhdGljIGFzeW5jIGxvYWRNYW5hZ2VtZW50U2Vzc2lvbihzdG9yYWdlPzogQ29nbml0b1Nlc3Npb25TdG9yYWdlKTogUHJvbWlzZTxDdWJlU2lnbmVyPiB7XG4gICAgY29uc3QgZGVmYXVsdEZpbGVQYXRoID0gcGF0aC5qb2luKGNvbmZpZ0RpcigpLCBcIm1hbmFnZW1lbnQtc2Vzc2lvbi5qc29uXCIpO1xuICAgIGNvbnN0IHNlc3Npb25NZ3IgPSBhd2FpdCBDb2duaXRvU2Vzc2lvbk1hbmFnZXIubG9hZEZyb21TdG9yYWdlKFxuICAgICAgc3RvcmFnZSA/PyBuZXcgSnNvbkZpbGVTZXNzaW9uU3RvcmFnZShkZWZhdWx0RmlsZVBhdGgpLFxuICAgICk7XG4gICAgcmV0dXJuIG5ldyBDdWJlU2lnbmVyKDxDdWJlU2lnbmVyT3B0aW9ucz57XG4gICAgICBzZXNzaW9uTWdyLFxuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIExvYWRzIGEgc2lnbmVyIHNlc3Npb24gZnJvbSBhIHNlc3Npb24gc3RvcmFnZSAoZS5nLiwgc2Vzc2lvbiBmaWxlKS5cbiAgICogQHBhcmFtIHtTaWduZXJTZXNzaW9uU3RvcmFnZX0gc3RvcmFnZSBPcHRpb25hbCBzZXNzaW9uIHN0b3JhZ2UgdG8gbG9hZFxuICAgKiB0aGUgc2Vzc2lvbiBmcm9tLiBJZiBub3Qgc3BlY2lmaWVkLCB0aGUgc2lnbmVyIHNlc3Npb24gZnJvbSB0aGUgY29uZmlnXG4gICAqIGRpcmVjdG9yeSB3aWxsIGJlIGxvYWRlZC5cbiAgICogQHJldHVybiB7UHJvbWlzZTxTaWduZXJTZXNzaW9uPn0gTmV3IHNpZ25lciBzZXNzaW9uXG4gICAqL1xuICBzdGF0aWMgYXN5bmMgbG9hZFNpZ25lclNlc3Npb24oc3RvcmFnZT86IFNpZ25lclNlc3Npb25TdG9yYWdlKTogUHJvbWlzZTxTaWduZXJTZXNzaW9uPiB7XG4gICAgY29uc3QgZGVmYXVsdEZpbGVQYXRoID0gcGF0aC5qb2luKGNvbmZpZ0RpcigpLCBcInNpZ25lci1zZXNzaW9uLmpzb25cIik7XG4gICAgY29uc3Qgc3NzID0gc3RvcmFnZSA/PyBuZXcgSnNvbkZpbGVTZXNzaW9uU3RvcmFnZShkZWZhdWx0RmlsZVBhdGgpO1xuICAgIHJldHVybiBhd2FpdCBTaWduZXJTZXNzaW9uLmxvYWRTaWduZXJTZXNzaW9uKHNzcyk7XG4gIH1cblxuICAvKipcbiAgICogQ3JlYXRlIGEgbmV3IEN1YmVTaWduZXIgaW5zdGFuY2UuXG4gICAqIEBwYXJhbSB7Q3ViZVNpZ25lck9wdGlvbnN9IG9wdGlvbnMgVGhlIG9wdGlvbmFsIGNvbmZpZ3VyYWl0b24gb3B0aW9ucyBmb3IgdGhlIEN1YmVTaWduZXIgaW5zdGFuY2UuXG4gICAqL1xuICBjb25zdHJ1Y3RvcihvcHRpb25zPzogQ3ViZVNpZ25lck9wdGlvbnMpIHtcbiAgICBsZXQgZW52ID0gb3B0aW9ucz8uZW52O1xuICAgIGlmIChvcHRpb25zPy5zZXNzaW9uTWdyKSB7XG4gICAgICB0aGlzLnNlc3Npb25NZ3IgPSBvcHRpb25zLnNlc3Npb25NZ3I7XG4gICAgICBlbnYgPSBlbnYgPz8gdGhpcy5zZXNzaW9uTWdyLmVudjtcbiAgICB9XG4gICAgdGhpcy4jZW52ID0gZW52ID8/IGVudnNbXCJnYW1tYVwiXTtcbiAgICB0aGlzLiNvcmdJZCA9IG9wdGlvbnM/Lm9yZ0lkO1xuICB9XG5cbiAgLyoqXG4gICAqIEF1dGhlbnRpY2F0ZSBhbiBPSURDIHVzZXIgYW5kIGNyZWF0ZSBhIG5ldyBzZXNzaW9uIG1hbmFnZXIgZm9yIHRoZW0uXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBvaWRjVG9rZW4gVGhlIE9JREMgdG9rZW5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9yZ0lkIFRoZSBpZCBvZiB0aGUgb3JnYW5pemF0aW9uIHRoYXQgdGhlIHVzZXIgaXMgaW5cbiAgICogQHBhcmFtIHtMaXN0PHN0cmluZz59IHNjb3BlcyBUaGUgc2NvcGVzIG9mIHRoZSByZXN1bHRpbmcgc2Vzc2lvblxuICAgKiBAcGFyYW0ge1JhdGNoZXRDb25maWd9IGxpZmV0aW1lcyBMaWZldGltZXMgb2YgdGhlIG5ldyBzZXNzaW9uLlxuICAgKiBAcGFyYW0ge1NpZ25lclNlc3Npb25TdG9yYWdlP30gc3RvcmFnZSBPcHRpb25hbCBzaWduZXIgc2Vzc2lvbiBzdG9yYWdlIChkZWZhdWx0cyB0byBpbi1tZW1vcnkgc3RvcmFnZSlcbiAgICogQHJldHVybiB7UHJvbWlzZTxTaWduZXJTZXNzaW9uTWFuYWdlcj59IFRoZSBzaWduZXIgc2Vzc2lvbiBtYW5hZ2VyXG4gICAqL1xuICBhc3luYyBvaWRjQXV0aChcbiAgICBvaWRjVG9rZW46IHN0cmluZyxcbiAgICBvcmdJZDogc3RyaW5nLFxuICAgIHNjb3BlczogQXJyYXk8c3RyaW5nPixcbiAgICBsaWZldGltZXM/OiBSYXRjaGV0Q29uZmlnLFxuICAgIHN0b3JhZ2U/OiBTaWduZXJTZXNzaW9uU3RvcmFnZSxcbiAgKTogUHJvbWlzZTxTaWduZXJTZXNzaW9uTWFuYWdlcj4ge1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCB0aGlzLm9pZGNMb2dpbihvaWRjVG9rZW4sIG9yZ0lkLCBzY29wZXMsIGxpZmV0aW1lcyk7XG4gICAgcmV0dXJuIGF3YWl0IFNpZ25lclNlc3Npb25NYW5hZ2VyLmNyZWF0ZUZyb21TZXNzaW9uSW5mbyh0aGlzLmVudiwgb3JnSWQsIHJlc3AuZGF0YSgpLCBzdG9yYWdlKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXRyaWV2ZXMgaW5mb3JtYXRpb24gYWJvdXQgdGhlIGN1cnJlbnQgdXNlci5cbiAgICpcbiAgICogQHJldHVybiB7UHJvbWlzZTxVc2VySW5mbz59IFVzZXIgaW5mb3JtYXRpb24uXG4gICAqL1xuICBhc3luYyBhYm91dE1lKCk6IFByb21pc2U8VXNlckluZm8+IHtcbiAgICBjb25zdCBjbGllbnQgPSBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKTtcbiAgICBjb25zdCByZXNwID0gdGhpcy4jb3JnSWRcbiAgICAgID8gYXdhaXQgY2xpZW50LmdldChcIi92MC9vcmcve29yZ19pZH0vdXNlci9tZVwiLCB7XG4gICAgICAgICAgcGFyYW1zOiB7IHBhdGg6IHsgb3JnX2lkOiB0aGlzLiNvcmdJZCB9IH0sXG4gICAgICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgICAgIH0pXG4gICAgICA6IGF3YWl0IGNsaWVudC5nZXQoXCIvdjAvYWJvdXRfbWVcIiwge1xuICAgICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgICB9KTtcbiAgICBjb25zdCBkYXRhID0gYXNzZXJ0T2socmVzcCk7XG4gICAgcmV0dXJuIGRhdGE7XG4gIH1cblxuICAvKipcbiAgICogUmV0cmlldmVzIGV4aXN0aW5nIE1GQSByZXF1ZXN0LlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgT3JnYW5pemF0aW9uIElEXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBtZmFJZCBNRkEgcmVxdWVzdCBJRFxuICAgKiBAcmV0dXJuIHtQcm9taXNlPE1mYVJlcXVlc3RJbmZvPn0gTUZBIHJlcXVlc3QgaW5mb3JtYXRpb25cbiAgICovXG4gIGFzeW5jIG1mYUdldChvcmdJZDogc3RyaW5nLCBtZmFJZDogc3RyaW5nKTogUHJvbWlzZTxNZmFSZXF1ZXN0SW5mbz4ge1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCAoXG4gICAgICBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKVxuICAgICkuZ2V0KFwiL3YwL29yZy97b3JnX2lkfS9tZmEve21mYV9pZH1cIiwge1xuICAgICAgcGFyYW1zOiB7IHBhdGg6IHsgb3JnX2lkOiBvcmdJZCwgbWZhX2lkOiBtZmFJZCB9IH0sXG4gICAgfSk7XG4gICAgcmV0dXJuIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqXG4gICAqIExpc3QgcGVuZGluZyBNRkEgcmVxdWVzdHMgYWNjZXNzaWJsZSB0byB0aGUgY3VycmVudCB1c2VyLlxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgT3JnYW5pemF0aW9uIElEXG4gICAqIEByZXR1cm4ge1Byb21pc2U8TWZhUmVxdWVzdEluZm9bXT59IFRoZSBNRkEgcmVxdWVzdHMuXG4gICAqL1xuICBhc3luYyBtZmFMaXN0KG9yZ0lkOiBzdHJpbmcpOiBQcm9taXNlPE1mYVJlcXVlc3RJbmZvW10+IHtcbiAgICBjb25zdCByZXNwID0gYXdhaXQgKFxuICAgICAgYXdhaXQgdGhpcy5tYW5hZ2VtZW50KClcbiAgICApLmdldChcIi92MC9vcmcve29yZ19pZH0vbWZhXCIsIHtcbiAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogb3JnSWQgfSB9LFxuICAgIH0pO1xuICAgIHJldHVybiBhc3NlcnRPayhyZXNwKS5tZmFfcmVxdWVzdHM7XG4gIH1cblxuICAvKipcbiAgICogQXBwcm92ZSBhIHBlbmRpbmcgTUZBIHJlcXVlc3QuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBvcmdJZCBUaGUgb3JnIGlkIG9mIHRoZSBNRkEgcmVxdWVzdFxuICAgKiBAcGFyYW0ge3N0cmluZ30gbWZhSWQgVGhlIGlkIG9mIHRoZSBNRkEgcmVxdWVzdFxuICAgKiBAcmV0dXJuIHtQcm9taXNlPE1mYVJlcXVlc3RJbmZvPn0gVGhlIHJlc3VsdCBvZiB0aGUgTUZBIHJlcXVlc3RcbiAgICovXG4gIGFzeW5jIG1mYUFwcHJvdmUob3JnSWQ6IHN0cmluZywgbWZhSWQ6IHN0cmluZyk6IFByb21pc2U8TWZhUmVxdWVzdEluZm8+IHtcbiAgICBjb25zdCByZXNwID0gYXdhaXQgKFxuICAgICAgYXdhaXQgdGhpcy5tYW5hZ2VtZW50KClcbiAgICApLnBhdGNoKFwiL3YwL29yZy97b3JnX2lkfS9tZmEve21mYV9pZH1cIiwge1xuICAgICAgcGFyYW1zOiB7IHBhdGg6IHsgb3JnX2lkOiBvcmdJZCwgbWZhX2lkOiBtZmFJZCB9IH0sXG4gICAgfSk7XG4gICAgcmV0dXJuIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqXG4gICAqIEluaXRpYXRlIGFkZGluZyBhIG5ldyBGSURPIGRldmljZS4gTUZBIG1heSBiZSByZXF1aXJlZC5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG5hbWUgVGhlIG5hbWUgb2YgdGhlIG5ldyBkZXZpY2UuXG4gICAqIEBwYXJhbSB7TWZhUmVjZWlwdH0gbWZhUmVjZWlwdCBPcHRpb25hbCBNRkEgcmVjZWlwdCB0byBpbmNsdWRlIGluIEhUVFAgaGVhZGVyc1xuICAgKiBAcmV0dXJuIHtQcm9taXNlPFNpZ25SZXNwb25zZTxBZGRGaWRvQ2hhbGxlbmdlPj59IEEgY2hhbGxlbmdlIHRoYXQgbXVzdCBiZSBhbnN3ZXJlZCBpbiBvcmRlciB0byBjb21wbGV0ZSBGSURPIHJlZ2lzdHJhdGlvbi5cbiAgICovXG4gIGFzeW5jIGFkZEZpZG9TdGFydChcbiAgICBuYW1lOiBzdHJpbmcsXG4gICAgbWZhUmVjZWlwdD86IE1mYVJlY2VpcHQsXG4gICk6IFByb21pc2U8U2lnblJlc3BvbnNlPEFkZEZpZG9DaGFsbGVuZ2U+PiB7XG4gICAgY29uc3Qgb3JnSWQgPSB0aGlzLiNvcmdJZCB8fCBtZmFSZWNlaXB0Py5tZmFPcmdJZDtcbiAgICBpZiAoIW9yZ0lkKSB7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoXCJPcmcgSUQgbXVzdCBiZSBzZXRcIik7XG4gICAgfVxuICAgIGNvbnN0IGFkZEZpZG9GbiA9IGFzeW5jIChoZWFkZXJzPzogSGVhZGVyc0luaXQpID0+IHtcbiAgICAgIGNvbnN0IGNsaWVudCA9IGF3YWl0IHRoaXMubWFuYWdlbWVudCgpO1xuICAgICAgY29uc3QgcmVzcCA9IGF3YWl0IGNsaWVudC5wb3N0KFwiL3YwL29yZy97b3JnX2lkfS91c2VyL21lL2ZpZG9cIiwge1xuICAgICAgICBoZWFkZXJzLFxuICAgICAgICBwYXJhbXM6IHsgcGF0aDogeyBvcmdfaWQ6IG9yZ0lkIH0gfSxcbiAgICAgICAgYm9keTogeyBuYW1lIH0sXG4gICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgfSk7XG4gICAgICBjb25zdCB4ID0gYXNzZXJ0T2socmVzcCk7XG4gICAgICAvLyBUT0RPOiBhZGQgbWFwRm4gdG8gU2lnblJlc3BvbnNlXG4gICAgICBpZiAoKHggYXMgQWNjZXB0ZWRSZXNwb25zZSkuYWNjZXB0ZWQ/Lk1mYVJlcXVpcmVkKSB7XG4gICAgICAgIHJldHVybiB4IGFzIEFjY2VwdGVkUmVzcG9uc2U7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICByZXR1cm4gbmV3IEFkZEZpZG9DaGFsbGVuZ2UodGhpcywgeCBhcyBBcGlBZGRGaWRvQ2hhbGxlbmdlKTtcbiAgICAgIH1cbiAgICB9O1xuICAgIHJldHVybiBhd2FpdCBTaWduUmVzcG9uc2UuY3JlYXRlKGFkZEZpZG9GbiwgbWZhUmVjZWlwdCk7XG4gIH1cblxuICAvKipcbiAgICogQ29tcGxldGUgYSBwcmV2aW91c2x5IGluaXRpYXRlZCByZXF1ZXN0IHRvIGFkZCBhIG5ldyBGSURPIGRldmljZS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IGNoYWxsZW5nZUlkIFRoZSBJRCBvZiB0aGUgY2hhbGxlbmdlIHJldHVybmVkIGJ5IHRoZSByZW1vdGUgZW5kLlxuICAgKiBAcGFyYW0ge1B1YmxpY0tleUNyZWRlbnRpYWx9IGNyZWRlbnRpYWwgVGhlIGFuc3dlciB0byB0aGUgY2hhbGxlbmdlLlxuICAgKi9cbiAgYXN5bmMgYWRkRmlkb0NvbXBsZXRlKGNoYWxsZW5nZUlkOiBzdHJpbmcsIGNyZWRlbnRpYWw6IFB1YmxpY0tleUNyZWRlbnRpYWwpIHtcbiAgICBjb25zdCBvcmdJZCA9IHRoaXMuI29yZ0lkO1xuICAgIGlmICghb3JnSWQpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihcIk9yZyBJRCBtdXN0IGJlIHNldFwiKTtcbiAgICB9XG4gICAgY29uc3QgY2xpZW50ID0gYXdhaXQgdGhpcy5tYW5hZ2VtZW50KCk7XG4gICAgY29uc3QgcmVzcCA9IGF3YWl0IGNsaWVudC5wYXRjaChcIi92MC9vcmcve29yZ19pZH0vdXNlci9tZS9maWRvXCIsIHtcbiAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogb3JnSWQgfSB9LFxuICAgICAgYm9keToge1xuICAgICAgICBjaGFsbGVuZ2VfaWQ6IGNoYWxsZW5nZUlkLFxuICAgICAgICBjcmVkZW50aWFsLFxuICAgICAgfSxcbiAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgIH0pO1xuICAgIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqXG4gICAqIENyZWF0ZXMgYSByZXF1ZXN0IHRvIGNoYW5nZSB1c2VyJ3MgVE9UUC4gVGhpcyByZXF1ZXN0IHJldHVybnMgYSBuZXcgVE9UUCBjaGFsbGVuZ2VcbiAgICogdGhhdCBtdXN0IGJlIGFuc3dlcmVkIGJ5IGNhbGxpbmcgYHJlc2V0VG90cENvbXBsZXRlYFxuICAgKlxuICAgKiBAcGFyYW0ge01mYVJlY2VpcHR9IG1mYVJlY2VpcHQgTUZBIHJlY2VpcHQgdG8gaW5jbHVkZSBpbiBIVFRQIGhlYWRlcnNcbiAgICovXG4gIGFzeW5jIHJlc2V0VG90cFN0YXJ0KG1mYVJlY2VpcHQ/OiBNZmFSZWNlaXB0KTogUHJvbWlzZTxTaWduUmVzcG9uc2U8VG90cENoYWxsZW5nZT4+IHtcbiAgICBjb25zdCByZXNldFRvdHBGbiA9IGFzeW5jIChoZWFkZXJzPzogSGVhZGVyc0luaXQpID0+IHtcbiAgICAgIGNvbnN0IG9yZ0lkID0gdGhpcy4jb3JnSWQgfHwgbWZhUmVjZWlwdD8ubWZhT3JnSWQ7XG4gICAgICBjb25zdCBjbGllbnQgPSBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKTtcbiAgICAgIGNvbnN0IHJlc3AgPSBvcmdJZFxuICAgICAgICA/IGF3YWl0IGNsaWVudC5wb3N0KFwiL3YwL29yZy97b3JnX2lkfS91c2VyL21lL3RvdHBcIiwge1xuICAgICAgICAgICAgaGVhZGVycyxcbiAgICAgICAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogb3JnSWQgfSB9LFxuICAgICAgICAgICAgYm9keTogbnVsbCxcbiAgICAgICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgICAgIH0pXG4gICAgICAgIDogYXdhaXQgY2xpZW50LnBvc3QoXCIvdjAvdXNlci9tZS90b3RwXCIsIHtcbiAgICAgICAgICAgIGhlYWRlcnMsXG4gICAgICAgICAgICBib2R5OiBudWxsLFxuICAgICAgICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgICAgICAgfSk7XG4gICAgICBjb25zdCB4ID0gYXNzZXJ0T2socmVzcCk7XG4gICAgICAvLyBUT0RPOiBhZGQgbWFwRm4gdG8gU2lnblJlc3BvbnNlXG4gICAgICBpZiAoKHggYXMgQWNjZXB0ZWRSZXNwb25zZSkuYWNjZXB0ZWQ/Lk1mYVJlcXVpcmVkKSB7XG4gICAgICAgIHJldHVybiB4IGFzIEFjY2VwdGVkUmVzcG9uc2U7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICByZXR1cm4gbmV3IFRvdHBDaGFsbGVuZ2UodGhpcywgeCBhcyBUb3RwSW5mbyk7XG4gICAgICB9XG4gICAgfTtcbiAgICByZXR1cm4gYXdhaXQgU2lnblJlc3BvbnNlLmNyZWF0ZShyZXNldFRvdHBGbiwgbWZhUmVjZWlwdCk7XG4gIH1cblxuICAvKipcbiAgICogQW5zd2VyIHRoZSBUT1RQIGNoYWxsZW5nZSBpc3N1ZWQgYnkgYHJlc2V0VG90cFN0YXJ0YC4gSWYgc3VjY2Vzc2Z1bCwgdXNlcidzXG4gICAqIFRPVFAgY29uZmlndXJhdGlvbiB3aWxsIGJlIHVwZGF0ZWQgdG8gdGhhdCBvZiB0aGUgVE9UUCBjaGFsbGVuZ2UuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSB0b3RwSWQgLSBUaGUgSUQgb2YgdGhlIFRPVFAgY2hhbGxlbmdlXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBjb2RlIC0gVGhlIFRPVFAgY29kZSB0aGF0IHNob3VsZCB2ZXJpZnkgYWdhaW5zdCB0aGUgVE9UUCBjb25maWd1cmF0aW9uIGZyb20gdGhlIGNoYWxsZW5nZS5cbiAgICovXG4gIGFzeW5jIHJlc2V0VG90cENvbXBsZXRlKHRvdHBJZDogc3RyaW5nLCBjb2RlOiBzdHJpbmcpOiBQcm9taXNlPHZvaWQ+IHtcbiAgICBjb25zdCBjbGllbnQgPSBhd2FpdCB0aGlzLm1hbmFnZW1lbnQoKTtcbiAgICBjb25zdCByZXNwID0gdGhpcy4jb3JnSWRcbiAgICAgID8gYXdhaXQgY2xpZW50LnBhdGNoKFwiL3YwL29yZy97b3JnX2lkfS91c2VyL21lL3RvdHBcIiwge1xuICAgICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogdGhpcy4jb3JnSWQgfSB9LFxuICAgICAgICAgIGJvZHk6IHsgdG90cF9pZDogdG90cElkLCBjb2RlIH0sXG4gICAgICAgIH0pXG4gICAgICA6IGF3YWl0IGNsaWVudC5wYXRjaChcIi92MC91c2VyL21lL3RvdHBcIiwge1xuICAgICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgICAgIGJvZHk6IHsgdG90cF9pZDogdG90cElkLCBjb2RlIH0sXG4gICAgICAgIH0pO1xuICAgIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqXG4gICAqIFZlcmlmaWVzIGEgZ2l2ZW4gVE9UUCBjb2RlIGFnYWluc3QgdGhlIGN1cnJlbnQgdXNlcidzIFRPVFAgY29uZmlndXJhdGlvbi5cbiAgICogVGhyb3dzIGFuIGVycm9yIGlmIHRoZSB2ZXJpZmljYXRpb24gZmFpbHMuXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBjb2RlIEN1cnJlbnQgVE9UUCBjb2RlXG4gICAqL1xuICBhc3luYyB2ZXJpZnlUb3RwKGNvZGU6IHN0cmluZykge1xuICAgIGNvbnN0IGNsaWVudCA9IGF3YWl0IHRoaXMubWFuYWdlbWVudCgpO1xuICAgIGNvbnN0IHJlc3AgPSB0aGlzLiNvcmdJZFxuICAgICAgPyBhd2FpdCBjbGllbnQucG9zdChcIi92MC9vcmcve29yZ19pZH0vdXNlci9tZS90b3RwL3ZlcmlmeVwiLCB7XG4gICAgICAgICAgcGFyYW1zOiB7IHBhdGg6IHsgb3JnX2lkOiB0aGlzLiNvcmdJZCB9IH0sXG4gICAgICAgICAgYm9keTogeyBjb2RlIH0sXG4gICAgICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgICAgIH0pXG4gICAgICA6IGF3YWl0IGNsaWVudC5wb3N0KFwiL3YwL3VzZXIvbWUvdG90cC92ZXJpZnlcIiwge1xuICAgICAgICAgIGJvZHk6IHsgY29kZSB9LFxuICAgICAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgICAgICB9KTtcbiAgICBhc3NlcnRPayhyZXNwKTtcbiAgfVxuXG4gIC8qKiBSZXRyaWV2ZXMgaW5mb3JtYXRpb24gYWJvdXQgYW4gb3JnYW5pemF0aW9uLlxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIElEIG9yIG5hbWUgb2YgdGhlIG9yZ2FuaXphdGlvbi5cbiAgICogQHJldHVybiB7T3JnfSBUaGUgb3JnYW5pemF0aW9uLlxuICAgKiAqL1xuICBhc3luYyBnZXRPcmcob3JnSWQ6IHN0cmluZyk6IFByb21pc2U8T3JnPiB7XG4gICAgY29uc3QgcmVzcCA9IGF3YWl0IChcbiAgICAgIGF3YWl0IHRoaXMubWFuYWdlbWVudCgpXG4gICAgKS5nZXQoXCIvdjAvb3JnL3tvcmdfaWR9XCIsIHtcbiAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogb3JnSWQgfSB9LFxuICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgfSk7XG5cbiAgICBjb25zdCBkYXRhID0gYXNzZXJ0T2socmVzcCk7XG4gICAgcmV0dXJuIG5ldyBPcmcodGhpcywgZGF0YSk7XG4gIH1cblxuICAvKipcbiAgICogRGVsZXRlcyBhIGdpdmVuIGtleS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9yZ0lkIC0gT3JnYW5pemF0aW9uIGlkXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBrZXlJZCAtIEtleSBpZFxuICAgKi9cbiAgYXN5bmMgZGVsZXRlS2V5KG9yZ0lkOiBzdHJpbmcsIGtleUlkOiBzdHJpbmcpIHtcbiAgICBjb25zdCByZXNwID0gYXdhaXQgKFxuICAgICAgYXdhaXQgdGhpcy5tYW5hZ2VtZW50KClcbiAgICApLmRlbChcIi92MC9vcmcve29yZ19pZH0va2V5cy97a2V5X2lkfVwiLCB7XG4gICAgICBwYXJhbXM6IHsgcGF0aDogeyBvcmdfaWQ6IG9yZ0lkLCBrZXlfaWQ6IGtleUlkIH0gfSxcbiAgICAgIHBhcnNlQXM6IFwianNvblwiLFxuICAgIH0pO1xuICAgIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqIEdldCB0aGUgbWFuYWdlbWVudCBjbGllbnQuXG4gICAqIEByZXR1cm4ge0NsaWVudH0gVGhlIGNsaWVudC5cbiAgICogQGludGVybmFsXG4gICAqICovXG4gIGFzeW5jIG1hbmFnZW1lbnQoKTogUHJvbWlzZTxDbGllbnQ+IHtcbiAgICBpZiAoIXRoaXMuc2Vzc2lvbk1ncikge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiTm8gbWFuYWdlbWVudCBzZXNzaW9uIGxvYWRlZFwiKTtcbiAgICB9XG4gICAgcmV0dXJuIGF3YWl0IHRoaXMuc2Vzc2lvbk1nci5jbGllbnQoKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBPYnRhaW4gYSBwcm9vZiBvZiBhdXRoZW50aWNhdGlvbi5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IG9yZ0lkIFRoZSBpZCBvZiB0aGUgb3JnYW5pemF0aW9uIHRoYXQgdGhlIHVzZXIgaXMgaW5cbiAgICogQHJldHVybiB7UHJvbWlzZTxJZGVudGl0eVByb29mPn0gUHJvb2Ygb2YgYXV0aGVudGljYXRpb25cbiAgICovXG4gIGFzeW5jIHByb3ZlSWRlbnRpdHkob3JnSWQ6IHN0cmluZyk6IFByb21pc2U8SWRlbnRpdHlQcm9vZj4ge1xuICAgIGNvbnN0IGNsaWVudCA9IGF3YWl0IHRoaXMubWFuYWdlbWVudCgpO1xuICAgIGNvbnN0IHJlc3AgPSBhd2FpdCBjbGllbnQucG9zdChcIi92MC9vcmcve29yZ19pZH0vaWRlbnRpdHkvcHJvdmVcIiwge1xuICAgICAgcGFyYW1zOiB7IHBhdGg6IHsgb3JnX2lkOiBvcmdJZCB9IH0sXG4gICAgICBwYXJzZUFzOiBcImpzb25cIixcbiAgICB9KTtcbiAgICByZXR1cm4gYXNzZXJ0T2socmVzcCk7XG4gIH1cblxuICAvKipcbiAgICogRXhjaGFuZ2UgYW4gT0lEQyB0b2tlbiBmb3IgYSBwcm9vZiBvZiBhdXRoZW50aWNhdGlvbi5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IG9pZGNUb2tlbiBUaGUgT0lEQyB0b2tlblxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIGlkIG9mIHRoZSBvcmdhbml6YXRpb24gdGhhdCB0aGUgdXNlciBpcyBpblxuICAgKiBAcmV0dXJuIHtQcm9taXNlPElkZW50aXR5UHJvb2Y+fSBQcm9vZiBvZiBhdXRoZW50aWNhdGlvblxuICAgKi9cbiAgYXN5bmMgb2lkY1Byb3ZlSWRlbnRpdHkob2lkY1Rva2VuOiBzdHJpbmcsIG9yZ0lkOiBzdHJpbmcpOiBQcm9taXNlPElkZW50aXR5UHJvb2Y+IHtcbiAgICBjb25zdCBjbGllbnQgPSBjcmVhdGVDbGllbnQ8cGF0aHM+KHtcbiAgICAgIGJhc2VVcmw6IHRoaXMuZW52LlNpZ25lckFwaVJvb3QsXG4gICAgICBoZWFkZXJzOiB7XG4gICAgICAgIEF1dGhvcml6YXRpb246IG9pZGNUb2tlbixcbiAgICAgIH0sXG4gICAgfSk7XG4gICAgY29uc3QgcmVzcCA9IGF3YWl0IGNsaWVudC5wb3N0KFwiL3YwL29yZy97b3JnX2lkfS9pZGVudGl0eS9wcm92ZS9vaWRjXCIsIHtcbiAgICAgIHBhcmFtczogeyBwYXRoOiB7IG9yZ19pZDogb3JnSWQgfSB9LFxuICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgfSk7XG4gICAgcmV0dXJuIGFzc2VydE9rKHJlc3ApO1xuICB9XG5cbiAgLyoqXG4gICAqIENoZWNrcyBpZiBhIGdpdmVuIGlkZW50aXR5IHByb29mIGlzIHZhbGlkLlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIGlkIG9mIHRoZSBvcmdhbml6YXRpb24gdGhhdCB0aGUgdXNlciBpcyBpbi5cbiAgICogQHBhcmFtIHtJZGVudGl0eVByb29mfSBpZGVudGl0eVByb29mIFRoZSBwcm9vZiBvZiBhdXRoZW50aWNhdGlvbi5cbiAgICovXG4gIGFzeW5jIHZlcmlmeUlkZW50aXR5KG9yZ0lkOiBzdHJpbmcsIGlkZW50aXR5UHJvb2Y6IElkZW50aXR5UHJvb2YpIHtcbiAgICBjb25zdCByZXNwID0gYXdhaXQgKFxuICAgICAgYXdhaXQgdGhpcy5tYW5hZ2VtZW50KClcbiAgICApLnBvc3QoXCIvdjAvb3JnL3tvcmdfaWR9L2lkZW50aXR5L3ZlcmlmeVwiLCB7XG4gICAgICBwYXJhbXM6IHsgcGF0aDogeyBvcmdfaWQ6IG9yZ0lkIH0gfSxcbiAgICAgIGJvZHk6IGlkZW50aXR5UHJvb2YsXG4gICAgICBwYXJzZUFzOiBcImpzb25cIixcbiAgICB9KTtcbiAgICBhc3NlcnRPayhyZXNwKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBFeGNoYW5nZSBhbiBPSURDIHRva2VuIGZvciBhIEN1YmVTaWduZXIgc2Vzc2lvbiB0b2tlbi5cbiAgICogQHBhcmFtIHtzdHJpbmd9IG9pZGNUb2tlbiBUaGUgT0lEQyB0b2tlblxuICAgKiBAcGFyYW0ge3N0cmluZ30gb3JnSWQgVGhlIGlkIG9mIHRoZSBvcmdhbml6YXRpb24gdGhhdCB0aGUgdXNlciBpcyBpblxuICAgKiBAcGFyYW0ge0xpc3Q8c3RyaW5nPn0gc2NvcGVzIFRoZSBzY29wZXMgb2YgdGhlIHJlc3VsdGluZyBzZXNzaW9uXG4gICAqIEBwYXJhbSB7UmF0Y2hldENvbmZpZ30gbGlmZXRpbWVzIExpZmV0aW1lcyBvZiB0aGUgbmV3IHNlc3Npb24uXG4gICAqIEBwYXJhbSB7TWZhUmVjZWlwdH0gbWZhUmVjZWlwdCBPcHRpb25hbCBNRkEgcmVjZWlwdCAoaWQgKyBjb25maXJtYXRpb24gY29kZSlcbiAgICogQHJldHVybiB7UHJvbWlzZTxTaWduUmVzcG9uc2U8T2lkY0F1dGhSZXNwb25zZT4+fSBUaGUgc2Vzc2lvbiBkYXRhLlxuICAgKi9cbiAgYXN5bmMgb2lkY0xvZ2luKFxuICAgIG9pZGNUb2tlbjogc3RyaW5nLFxuICAgIG9yZ0lkOiBzdHJpbmcsXG4gICAgc2NvcGVzOiBBcnJheTxzdHJpbmc+LFxuICAgIGxpZmV0aW1lcz86IFJhdGNoZXRDb25maWcsXG4gICAgbWZhUmVjZWlwdD86IE1mYVJlY2VpcHQsXG4gICk6IFByb21pc2U8U2lnblJlc3BvbnNlPE9pZGNBdXRoUmVzcG9uc2U+PiB7XG4gICAgY29uc3QgY2xpZW50ID0gY3JlYXRlQ2xpZW50PHBhdGhzPih7XG4gICAgICBiYXNlVXJsOiB0aGlzLmVudi5TaWduZXJBcGlSb290LFxuICAgICAgaGVhZGVyczoge1xuICAgICAgICBBdXRob3JpemF0aW9uOiBvaWRjVG9rZW4sXG4gICAgICB9LFxuICAgIH0pO1xuICAgIGNvbnN0IGxvZ2luRm4gPSBhc3luYyAoaGVhZGVycz86IEhlYWRlcnNJbml0KSA9PiB7XG4gICAgICBjb25zdCByZXNwID0gYXdhaXQgY2xpZW50LnBvc3QoXCIvdjAvb3JnL3tvcmdfaWR9L29pZGNcIiwge1xuICAgICAgICBwYXJhbXM6IHsgcGF0aDogeyBvcmdfaWQ6IG9yZ0lkIH0gfSxcbiAgICAgICAgaGVhZGVycyxcbiAgICAgICAgYm9keToge1xuICAgICAgICAgIHNjb3BlcyxcbiAgICAgICAgICB0b2tlbnM6IGxpZmV0aW1lcyxcbiAgICAgICAgfSxcbiAgICAgICAgcGFyc2VBczogXCJqc29uXCIsXG4gICAgICB9KTtcbiAgICAgIHJldHVybiBhc3NlcnRPayhyZXNwKTtcbiAgICB9O1xuXG4gICAgY29uc3QgaDEgPSBtZmFSZWNlaXB0ID8gU2lnblJlc3BvbnNlLmdldE1mYUhlYWRlcnMobWZhUmVjZWlwdCkgOiB1bmRlZmluZWQ7XG4gICAgcmV0dXJuIG5ldyBTaWduUmVzcG9uc2UobG9naW5GbiwgYXdhaXQgbG9naW5GbihoMSkpO1xuICB9XG59XG5cbi8qKiBNRkEgcmVjZWlwdCAqL1xuZXhwb3J0IGludGVyZmFjZSBNZmFSZWNlaXB0IHtcbiAgLyoqIE1GQSByZXF1ZXN0IElEICovXG4gIG1mYUlkOiBzdHJpbmc7XG4gIC8qKiBDb3JyZXNwb25kaW5nIG9yZyBJRCAqL1xuICBtZmFPcmdJZDogc3RyaW5nO1xuICAvKiogTUZBIGNvbmZpcm1hdGlvbiBjb2RlICovXG4gIG1mYUNvbmY6IHN0cmluZztcbn1cblxuLyoqIE9yZ2FuaXphdGlvbnMgKi9cbmV4cG9ydCAqIGZyb20gXCIuL29yZ1wiO1xuLyoqIEtleXMgKi9cbmV4cG9ydCAqIGZyb20gXCIuL2tleVwiO1xuLyoqIFJvbGVzICovXG5leHBvcnQgKiBmcm9tIFwiLi9yb2xlXCI7XG4vKiogRW52ICovXG5leHBvcnQgKiBmcm9tIFwiLi9lbnZcIjtcbi8qKiBGaWRvICovXG5leHBvcnQgKiBmcm9tIFwiLi9maWRvXCI7XG4vKiogUGFnaW5hdGlvbiAqL1xuZXhwb3J0ICogZnJvbSBcIi4vcGFnaW5hdG9yXCI7XG4vKiogU2Vzc2lvbnMgKi9cbmV4cG9ydCAqIGZyb20gXCIuL3NpZ25lcl9zZXNzaW9uXCI7XG4vKiogU2Vzc2lvbiBzdG9yYWdlICovXG5leHBvcnQgKiBmcm9tIFwiLi9zZXNzaW9uL3Nlc3Npb25fc3RvcmFnZVwiO1xuLyoqIFNlc3Npb24gbWFuYWdlciAqL1xuZXhwb3J0ICogZnJvbSBcIi4vc2Vzc2lvbi9zZXNzaW9uX21hbmFnZXJcIjtcbi8qKiBNYW5hZ2VtZW50IHNlc3Npb24gbWFuYWdlciAqL1xuZXhwb3J0ICogZnJvbSBcIi4vc2Vzc2lvbi9jb2duaXRvX21hbmFnZXJcIjtcbi8qKiBTaWduZXIgc2Vzc2lvbiBtYW5hZ2VyICovXG5leHBvcnQgKiBmcm9tIFwiLi9zZXNzaW9uL3NpZ25lcl9zZXNzaW9uX21hbmFnZXJcIjtcbi8qKiBFeHBvcnQgZXRoZXJzLmpzIFNpZ25lciAqL1xuZXhwb3J0ICogYXMgZXRoZXJzIGZyb20gXCIuL2V0aGVyc1wiO1xuIl19
|