1 | ;
|
2 | var _a;
|
3 | Object.defineProperty(exports, "__esModule", { value: true });
|
4 | exports.StepFunctionsIntegration = void 0;
|
5 | const jsiiDeprecationWarnings = require("../../.warnings.jsii.js");
|
6 | const JSII_RTTI_SYMBOL_1 = Symbol.for("jsii.rtti");
|
7 | const fs = require("fs");
|
8 | const path = require("path");
|
9 | const iam = require("@aws-cdk/aws-iam");
|
10 | const sfn = require("@aws-cdk/aws-stepfunctions");
|
11 | const core_1 = require("@aws-cdk/core");
|
12 | const integration_1 = require("../integration");
|
13 | const model_1 = require("../model");
|
14 | const aws_1 = require("./aws");
|
15 | /**
|
16 | * Options to integrate with various StepFunction API
|
17 | */
|
18 | class StepFunctionsIntegration {
|
19 | /**
|
20 | * Integrates a Synchronous Express State Machine from AWS Step Functions to an API Gateway method.
|
21 | *
|
22 | * @example
|
23 | *
|
24 | * const stateMachine = new stepfunctions.StateMachine(this, 'MyStateMachine', {
|
25 | * stateMachineType: stepfunctions.StateMachineType.EXPRESS,
|
26 | * definition: stepfunctions.Chain.start(new stepfunctions.Pass(this, 'Pass')),
|
27 | * });
|
28 | *
|
29 | * const api = new apigateway.RestApi(this, 'Api', {
|
30 | * restApiName: 'MyApi',
|
31 | * });
|
32 | * api.root.addMethod('GET', apigateway.StepFunctionsIntegration.startExecution(stateMachine));
|
33 | */
|
34 | static startExecution(stateMachine, options) {
|
35 | try {
|
36 | jsiiDeprecationWarnings._aws_cdk_aws_apigateway_StepFunctionsExecutionIntegrationOptions(options);
|
37 | }
|
38 | catch (error) {
|
39 | if (process.env.JSII_DEBUG !== "1" && error.name === "DeprecationError") {
|
40 | Error.captureStackTrace(error, this.startExecution);
|
41 | }
|
42 | throw error;
|
43 | }
|
44 | return new StepFunctionsExecutionIntegration(stateMachine, options);
|
45 | }
|
46 | }
|
47 | exports.StepFunctionsIntegration = StepFunctionsIntegration;
|
48 | _a = JSII_RTTI_SYMBOL_1;
|
49 | StepFunctionsIntegration[_a] = { fqn: "@aws-cdk/aws-apigateway.StepFunctionsIntegration", version: "1.156.0" };
|
50 | class StepFunctionsExecutionIntegration extends aws_1.AwsIntegration {
|
51 | constructor(stateMachine, options = {}) {
|
52 | super({
|
53 | service: 'states',
|
54 | action: 'StartSyncExecution',
|
55 | options: {
|
56 | credentialsRole: options.credentialsRole,
|
57 | integrationResponses: integrationResponse(),
|
58 | passthroughBehavior: integration_1.PassthroughBehavior.NEVER,
|
59 | requestTemplates: requestTemplates(stateMachine, options),
|
60 | ...options,
|
61 | },
|
62 | });
|
63 | this.stateMachine = stateMachine;
|
64 | }
|
65 | bind(method) {
|
66 | var _b, _c;
|
67 | const bindResult = super.bind(method);
|
68 | const credentialsRole = (_c = (_b = bindResult.options) === null || _b === void 0 ? void 0 : _b.credentialsRole) !== null && _c !== void 0 ? _c : new iam.Role(method, 'StartSyncExecutionRole', {
|
69 | assumedBy: new iam.ServicePrincipal('apigateway.amazonaws.com'),
|
70 | });
|
71 | this.stateMachine.grantStartSyncExecution(credentialsRole);
|
72 | let stateMachineName;
|
73 | if (this.stateMachine instanceof sfn.StateMachine) {
|
74 | const stateMachineType = this.stateMachine.stateMachineType;
|
75 | if (stateMachineType !== sfn.StateMachineType.EXPRESS) {
|
76 | throw new Error('State Machine must be of type "EXPRESS". Please use StateMachineType.EXPRESS as the stateMachineType');
|
77 | }
|
78 | //if not imported, extract the name from the CFN layer to reach the
|
79 | //literal value if it is given (rather than a token)
|
80 | stateMachineName = this.stateMachine.node.defaultChild.stateMachineName;
|
81 | }
|
82 | else {
|
83 | //imported state machine
|
84 | stateMachineName = `StateMachine-${this.stateMachine.stack.node.addr}`;
|
85 | }
|
86 | let deploymentToken;
|
87 | if (stateMachineName !== undefined && !core_1.Token.isUnresolved(stateMachineName)) {
|
88 | deploymentToken = JSON.stringify({ stateMachineName });
|
89 | }
|
90 | for (const methodResponse of METHOD_RESPONSES) {
|
91 | method.addMethodResponse(methodResponse);
|
92 | }
|
93 | return {
|
94 | ...bindResult,
|
95 | options: {
|
96 | ...bindResult.options,
|
97 | credentialsRole,
|
98 | },
|
99 | deploymentToken,
|
100 | };
|
101 | }
|
102 | }
|
103 | /**
|
104 | * Defines the integration response that passes the result on success,
|
105 | * or the error on failure, from the synchronous execution to the caller.
|
106 | *
|
107 | * @returns integrationResponse mapping
|
108 | */
|
109 | function integrationResponse() {
|
110 | const errorResponse = [
|
111 | {
|
112 | /**
|
113 | * Specifies the regular expression (regex) pattern used to choose
|
114 | * an integration response based on the response from the back end.
|
115 | * In this case it will match all '4XX' HTTP Errors
|
116 | */
|
117 | selectionPattern: '4\\d{2}',
|
118 | statusCode: '400',
|
119 | responseTemplates: {
|
120 | 'application/json': `{
|
121 | "error": "Bad request!"
|
122 | }`,
|
123 | },
|
124 | },
|
125 | {
|
126 | /**
|
127 | * Match all '5XX' HTTP Errors
|
128 | */
|
129 | selectionPattern: '5\\d{2}',
|
130 | statusCode: '500',
|
131 | responseTemplates: {
|
132 | 'application/json': '"error": $input.path(\'$.error\')',
|
133 | },
|
134 | },
|
135 | ];
|
136 | const integResponse = [
|
137 | {
|
138 | statusCode: '200',
|
139 | responseTemplates: {
|
140 | /* eslint-disable */
|
141 | 'application/json': [
|
142 | '#set($inputRoot = $input.path(\'$\'))',
|
143 | '#if($input.path(\'$.status\').toString().equals("FAILED"))',
|
144 | '#set($context.responseOverride.status = 500)',
|
145 | '{',
|
146 | '"error": "$input.path(\'$.error\')",',
|
147 | '"cause": "$input.path(\'$.cause\')"',
|
148 | '}',
|
149 | '#else',
|
150 | '$input.path(\'$.output\')',
|
151 | '#end',
|
152 | ].join('\n'),
|
153 | },
|
154 | },
|
155 | ...errorResponse,
|
156 | ];
|
157 | return integResponse;
|
158 | }
|
159 | /**
|
160 | * Defines the request template that will be used for the integration
|
161 | * @param stateMachine
|
162 | * @param options
|
163 | * @returns requestTemplate
|
164 | */
|
165 | function requestTemplates(stateMachine, options) {
|
166 | const templateStr = templateString(stateMachine, options);
|
167 | const requestTemplate = {
|
168 | 'application/json': templateStr,
|
169 | };
|
170 | return requestTemplate;
|
171 | }
|
172 | /**
|
173 | * Reads the VTL template and returns the template string to be used
|
174 | * for the request template.
|
175 | *
|
176 | * @param stateMachine
|
177 | * @param includeRequestContext
|
178 | * @param options
|
179 | * @reutrns templateString
|
180 | */
|
181 | function templateString(stateMachine, options) {
|
182 | var _b, _c, _d, _e;
|
183 | let templateStr;
|
184 | let requestContextStr = '';
|
185 | const includeHeader = (_b = options.headers) !== null && _b !== void 0 ? _b : false;
|
186 | const includeQueryString = (_c = options.querystring) !== null && _c !== void 0 ? _c : true;
|
187 | const includePath = (_d = options.path) !== null && _d !== void 0 ? _d : true;
|
188 | const includeAuthorizer = (_e = options.authorizer) !== null && _e !== void 0 ? _e : false;
|
189 | if (options.requestContext && Object.keys(options.requestContext).length > 0) {
|
190 | requestContextStr = requestContext(options.requestContext);
|
191 | }
|
192 | templateStr = fs.readFileSync(path.join(__dirname, 'stepfunctions.vtl'), { encoding: 'utf-8' });
|
193 | templateStr = templateStr.replace('%STATEMACHINE%', stateMachine.stateMachineArn);
|
194 | templateStr = templateStr.replace('%INCLUDE_HEADERS%', String(includeHeader));
|
195 | templateStr = templateStr.replace('%INCLUDE_QUERYSTRING%', String(includeQueryString));
|
196 | templateStr = templateStr.replace('%INCLUDE_PATH%', String(includePath));
|
197 | templateStr = templateStr.replace('%INCLUDE_AUTHORIZER%', String(includeAuthorizer));
|
198 | templateStr = templateStr.replace('%REQUESTCONTEXT%', requestContextStr);
|
199 | return templateStr;
|
200 | }
|
201 | function requestContext(requestContextObj) {
|
202 | const context = {
|
203 | accountId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.accountId) ? '$context.identity.accountId' : undefined,
|
204 | apiId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.apiId) ? '$context.apiId' : undefined,
|
205 | apiKey: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.apiKey) ? '$context.identity.apiKey' : undefined,
|
206 | authorizerPrincipalId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.authorizerPrincipalId) ? '$context.authorizer.principalId' : undefined,
|
207 | caller: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.caller) ? '$context.identity.caller' : undefined,
|
208 | cognitoAuthenticationProvider: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.cognitoAuthenticationProvider) ? '$context.identity.cognitoAuthenticationProvider' : undefined,
|
209 | cognitoAuthenticationType: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.cognitoAuthenticationType) ? '$context.identity.cognitoAuthenticationType' : undefined,
|
210 | cognitoIdentityId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.cognitoIdentityId) ? '$context.identity.cognitoIdentityId' : undefined,
|
211 | cognitoIdentityPoolId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.cognitoIdentityPoolId) ? '$context.identity.cognitoIdentityPoolId' : undefined,
|
212 | httpMethod: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.httpMethod) ? '$context.httpMethod' : undefined,
|
213 | stage: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.stage) ? '$context.stage' : undefined,
|
214 | sourceIp: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.sourceIp) ? '$context.identity.sourceIp' : undefined,
|
215 | user: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.user) ? '$context.identity.user' : undefined,
|
216 | userAgent: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.userAgent) ? '$context.identity.userAgent' : undefined,
|
217 | userArn: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.userArn) ? '$context.identity.userArn' : undefined,
|
218 | requestId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.requestId) ? '$context.requestId' : undefined,
|
219 | resourceId: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.resourceId) ? '$context.resourceId' : undefined,
|
220 | resourcePath: (requestContextObj === null || requestContextObj === void 0 ? void 0 : requestContextObj.resourcePath) ? '$context.resourcePath' : undefined,
|
221 | };
|
222 | const contextAsString = JSON.stringify(context);
|
223 | // The VTL Template conflicts with double-quotes (") for strings.
|
224 | // Before sending to the template, we replace double-quotes (") with @@ and replace it back inside the .vtl file
|
225 | const doublequotes = '"';
|
226 | const replaceWith = '@@';
|
227 | return contextAsString.split(doublequotes).join(replaceWith);
|
228 | }
|
229 | /**
|
230 | * Method response model for each HTTP code response
|
231 | */
|
232 | const METHOD_RESPONSES = [
|
233 | {
|
234 | statusCode: '200',
|
235 | responseModels: {
|
236 | 'application/json': model_1.Model.EMPTY_MODEL,
|
237 | },
|
238 | },
|
239 | {
|
240 | statusCode: '400',
|
241 | responseModels: {
|
242 | 'application/json': model_1.Model.ERROR_MODEL,
|
243 | },
|
244 | },
|
245 | {
|
246 | statusCode: '500',
|
247 | responseModels: {
|
248 | 'application/json': model_1.Model.ERROR_MODEL,
|
249 | },
|
250 | },
|
251 | ];
|
252 | //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic3RlcGZ1bmN0aW9ucy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbInN0ZXBmdW5jdGlvbnMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7O0FBQUEseUJBQXlCO0FBQ3pCLDZCQUE2QjtBQUM3Qix3Q0FBd0M7QUFDeEMsa0RBQWtEO0FBQ2xELHdDQUFzQztBQUV0QyxnREFBNEY7QUFFNUYsb0NBQWlDO0FBQ2pDLCtCQUF1QztBQThFdkM7O0dBRUc7QUFDSCxNQUFhLHdCQUF3QjtJQUNuQzs7Ozs7Ozs7Ozs7Ozs7T0FjRztJQUNJLE1BQU0sQ0FBQyxjQUFjLENBQUMsWUFBK0IsRUFBRSxPQUFrRDs7Ozs7Ozs7OztRQUM5RyxPQUFPLElBQUksaUNBQWlDLENBQUMsWUFBWSxFQUFFLE9BQU8sQ0FBQyxDQUFDO0tBQ3JFOztBQWxCSCw0REFtQkM7OztBQUVELE1BQU0saUNBQWtDLFNBQVEsb0JBQWM7SUFFNUQsWUFBWSxZQUErQixFQUFFLFVBQW9ELEVBQUU7UUFDakcsS0FBSyxDQUFDO1lBQ0osT0FBTyxFQUFFLFFBQVE7WUFDakIsTUFBTSxFQUFFLG9CQUFvQjtZQUM1QixPQUFPLEVBQUU7Z0JBQ1AsZUFBZSxFQUFFLE9BQU8sQ0FBQyxlQUFlO2dCQUN4QyxvQkFBb0IsRUFBRSxtQkFBbUIsRUFBRTtnQkFDM0MsbUJBQW1CLEVBQUUsaUNBQW1CLENBQUMsS0FBSztnQkFDOUMsZ0JBQWdCLEVBQUUsZ0JBQWdCLENBQUMsWUFBWSxFQUFFLE9BQU8sQ0FBQztnQkFDekQsR0FBRyxPQUFPO2FBQ1g7U0FDRixDQUFDLENBQUM7UUFFSCxJQUFJLENBQUMsWUFBWSxHQUFHLFlBQVksQ0FBQztLQUNsQztJQUVNLElBQUksQ0FBQyxNQUFjOztRQUN4QixNQUFNLFVBQVUsR0FBRyxLQUFLLENBQUMsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1FBRXRDLE1BQU0sZUFBZSxlQUFHLFVBQVUsQ0FBQyxPQUFPLDBDQUFFLGVBQWUsbUNBQUksSUFBSSxHQUFH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IjpbImltcG9ydCAqIGFzIGZzIGZyb20gJ2ZzJztcbmltcG9ydCAqIGFzIHBhdGggZnJvbSAncGF0aCc7XG5pbXBvcnQgKiBhcyBpYW0gZnJvbSAnQGF3cy1jZGsvYXdzLWlhbSc7XG5pbXBvcnQgKiBhcyBzZm4gZnJvbSAnQGF3cy1jZGsvYXdzLXN0ZXBmdW5jdGlvbnMnO1xuaW1wb3J0IHsgVG9rZW4gfSBmcm9tICdAYXdzLWNkay9jb3JlJztcbmltcG9ydCB7IFJlcXVlc3RDb250ZXh0IH0gZnJvbSAnLic7XG5pbXBvcnQgeyBJbnRlZ3JhdGlvbkNvbmZpZywgSW50ZWdyYXRpb25PcHRpb25zLCBQYXNzdGhyb3VnaEJlaGF2aW9yIH0gZnJvbSAnLi4vaW50ZWdyYXRpb24nO1xuaW1wb3J0IHsgTWV0aG9kIH0gZnJvbSAnLi4vbWV0aG9kJztcbmltcG9ydCB7IE1vZGVsIH0gZnJvbSAnLi4vbW9kZWwnO1xuaW1wb3J0IHsgQXdzSW50ZWdyYXRpb24gfSBmcm9tICcuL2F3cyc7XG4vKipcbiAqIE9wdGlvbnMgd2hlbiBjb25maWd1cmluZyBTdGVwIEZ1bmN0aW9ucyBzeW5jaHJvbm91cyBpbnRlZ3JhdGlvbiB3aXRoIFJlc3QgQVBJXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgU3RlcEZ1bmN0aW9uc0V4ZWN1dGlvbkludGVncmF0aW9uT3B0aW9ucyBleHRlbmRzIEludGVncmF0aW9uT3B0aW9ucyB7XG5cbiAgLyoqXG4gICAqIFdoaWNoIGRldGFpbHMgb2YgdGhlIGluY29taW5nIHJlcXVlc3QgbXVzdCBiZSBwYXNzZWQgb250byB0aGUgdW5kZXJseWluZyBzdGF0ZSBtYWNoaW5lLFxuICAgKiBzdWNoIGFzLCBhY2NvdW50IGlkLCB1c2VyIGlkZW50aXR5LCByZXF1ZXN0IGlkLCBldGMuIFRoZSBleGVjdXRpb24gaW5wdXQgd2lsbCBpbmNsdWRlIGEgbmV3IGtleSBgcmVxdWVzdENvbnRleHRgOlxuICAgKlxuICAgKiB7XG4gICAqICAgXCJib2R5XCI6IHt9LFxuICAgKiAgIFwicmVxdWVzdENvbnRleHRcIjoge1xuICAgKiAgICAgICBcImtleVwiOiBcInZhbHVlXCJcbiAgICogICB9XG4gICAqIH1cbiAgICpcbiAgICogQGRlZmF1bHQgLSBhbGwgcGFyYW1ldGVycyB3aXRoaW4gcmVxdWVzdCBjb250ZXh0IHdpbGwgYmUgc2V0IGFzIGZhbHNlXG4gICAqL1xuICByZWFkb25seSByZXF1ZXN0Q29udGV4dD86IFJlcXVlc3RDb250ZXh0O1xuXG4gIC8qKlxuICAgKiBDaGVjayBpZiBxdWVyeXN0cmluZyBpcyB0byBiZSBpbmNsdWRlZCBpbnNpZGUgdGhlIGV4ZWN1dGlvbiBpbnB1dC4gVGhlIGV4ZWN1dGlvbiBpbnB1dCB3aWxsIGluY2x1ZGUgYSBuZXcga2V5IGBxdWVyeVN0cmluZ2A6XG4gICAqXG4gICAqIHtcbiAgICogICBcImJvZHlcIjoge30sXG4gICAqICAgXCJxdWVyeXN0cmluZ1wiOiB7XG4gICAqICAgICBcImtleVwiOiBcInZhbHVlXCJcbiAgICogICB9XG4gICAqIH1cbiAgICpcbiAgICogQGRlZmF1bHQgdHJ1ZVxuICAgKi9cbiAgcmVhZG9ubHkgcXVlcnlzdHJpbmc/OiBib29sZWFuO1xuXG4gIC8qKlxuICAgKiBDaGVjayBpZiBwYXRoIGlzIHRvIGJlIGluY2x1ZGVkIGluc2lkZSB0aGUgZXhlY3V0aW9uIGlucHV0LiBUaGUgZXhlY3V0aW9uIGlucHV0IHdpbGwgaW5jbHVkZSBhIG5ldyBrZXkgYHBhdGhgOlxuICAgKlxuICAgKiB7XG4gICAqICAgXCJib2R5XCI6IHt9LFxuICAgKiAgIFwicGF0aFwiOiB7XG4gICAqICAgICBcInJlc291cmNlTmFtZVwiOiBcInJlc291cmNlVmFsdWVcIlxuICAgKiAgIH1cbiAgICogfVxuICAgKlxuICAgKiBAZGVmYXVsdCB0cnVlXG4gICAqL1xuICByZWFkb25seSBwYXRoPzogYm9vbGVhbjtcblxuICAvKipcbiAgICogQ2hlY2sgaWYgaGVhZGVyIGlzIHRvIGJlIGluY2x1ZGVkIGluc2lkZSB0aGUgZXhlY3V0aW9uIGlucHV0LiBUaGUgZXhlY3V0aW9uIGlucHV0IHdpbGwgaW5jbHVkZSBhIG5ldyBrZXkgYGhlYWRlcnNgOlxuICAgKlxuICAgKiB7XG4gICAqICAgXCJib2R5XCI6IHt9LFxuICAgKiAgIFwiaGVhZGVyc1wiOiB7XG4gICAqICAgICAgXCJoZWFkZXIxXCI6IFwidmFsdWVcIixcbiAgICogICAgICBcImhlYWRlcjJcIjogXCJ2YWx1ZVwiXG4gICAqICAgfVxuICAgKiB9XG4gICAqIEBkZWZhdWx0IGZhbHNlXG4gICAqL1xuICByZWFkb25seSBoZWFkZXJzPzogYm9vbGVhbjtcblxuICAvKipcbiAgICogSWYgdGhlIHdob2xlIGF1dGhvcml6ZXIgb2JqZWN0LCBpbmNsdWRpbmcgY3VzdG9tIGNvbnRleHQgdmFsdWVzIHNob3VsZCBiZSBpbiB0aGUgZXhlY3V0aW9uIGlucHV0LiBUaGUgZXhlY3V0aW9uIGlucHV0IHdpbGwgaW5jbHVkZSBhIG5ldyBrZXkgYGF1dGhvcml6ZXJgOlxuICAgKlxuICAgKiB7XG4gICAqICAgXCJib2R5XCI6IHt9LFxuICAgKiAgIFwiYXV0aG9yaXplclwiOiB7XG4gICAqICAgICBcImtleVwiOiBcInZhbHVlXCJcbiAgICogICB9XG4gICAqIH1cbiAgICpcbiAgICogQGRlZmF1bHQgZmFsc2VcbiAgICovXG4gIHJlYWRvbmx5IGF1dGhvcml6ZXI/OiBib29sZWFuO1xufVxuXG4vKipcbiAqIE9wdGlvbnMgdG8gaW50ZWdyYXRlIHdpdGggdmFyaW91cyBTdGVwRnVuY3Rpb24gQVBJXG4gKi9cbmV4cG9ydCBjbGFzcyBTdGVwRnVuY3Rpb25zSW50ZWdyYXRpb24ge1xuICAvKipcbiAgICogSW50ZWdyYXRlcyBhIFN5bmNocm9ub3VzIEV4cHJlc3MgU3RhdGUgTWFjaGluZSBmcm9tIEFXUyBTdGVwIEZ1bmN0aW9ucyB0byBhbiBBUEkgR2F0ZXdheSBtZXRob2QuXG4gICAqXG4gICAqIEBleGFtcGxlXG4gICAqXG4gICAqICAgIGNvbnN0IHN0YXRlTWFjaGluZSA9IG5ldyBzdGVwZnVuY3Rpb25zLlN0YXRlTWFjaGluZSh0aGlzLCAnTXlTdGF0ZU1hY2hpbmUnLCB7XG4gICAqICAgICAgIHN0YXRlTWFjaGluZVR5cGU6IHN0ZXBmdW5jdGlvbnMuU3RhdGVNYWNoaW5lVHlwZS5FWFBSRVNTLFxuICAgKiAgICAgICBkZWZpbml0aW9uOiBzdGVwZnVuY3Rpb25zLkNoYWluLnN0YXJ0KG5ldyBzdGVwZnVuY3Rpb25zLlBhc3ModGhpcywgJ1Bhc3MnKSksXG4gICAqICAgIH0pO1xuICAgKlxuICAgKiAgICBjb25zdCBhcGkgPSBuZXcgYXBpZ2F0ZXdheS5SZXN0QXBpKHRoaXMsICdBcGknLCB7XG4gICAqICAgICAgIHJlc3RBcGlOYW1lOiAnTXlBcGknLFxuICAgKiAgICB9KTtcbiAgICogICAgYXBpLnJvb3QuYWRkTWV0aG9kKCdHRVQnLCBhcGlnYXRld2F5LlN0ZXBGdW5jdGlvbnNJbnRlZ3JhdGlvbi5zdGFydEV4ZWN1dGlvbihzdGF0ZU1hY2hpbmUpKTtcbiAgICovXG4gIHB1YmxpYyBzdGF0aWMgc3RhcnRFeGVjdXRpb24oc3RhdGVNYWNoaW5lOiBzZm4uSVN0YXRlTWFjaGluZSwgb3B0aW9ucz86IFN0ZXBGdW5jdGlvbnNFeGVjdXRpb25JbnRlZ3JhdGlvbk9wdGlvbnMpOiBBd3NJbnRlZ3JhdGlvbiB7XG4gICAgcmV0dXJuIG5ldyBTdGVwRnVuY3Rpb25zRXhlY3V0aW9uSW50ZWdyYXRpb24oc3RhdGVNYWNoaW5lLCBvcHRpb25zKTtcbiAgfVxufVxuXG5jbGFzcyBTdGVwRnVuY3Rpb25zRXhlY3V0aW9uSW50ZWdyYXRpb24gZXh0ZW5kcyBBd3NJbnRlZ3JhdGlvbiB7XG4gIHByaXZhdGUgcmVhZG9ubHkgc3RhdGVNYWNoaW5lOiBzZm4uSVN0YXRlTWFjaGluZTtcbiAgY29uc3RydWN0b3Ioc3RhdGVNYWNoaW5lOiBzZm4uSVN0YXRlTWFjaGluZSwgb3B0aW9uczogU3RlcEZ1bmN0aW9uc0V4ZWN1dGlvbkludGVncmF0aW9uT3B0aW9ucyA9IHt9KSB7XG4gICAgc3VwZXIoe1xuICAgICAgc2VydmljZTogJ3N0YXRlcycsXG4gICAgICBhY3Rpb246ICdTdGFydFN5bmNFeGVjdXRpb24nLFxuICAgICAgb3B0aW9uczoge1xuICAgICAgICBjcmVkZW50aWFsc1JvbGU6IG9wdGlvbnMuY3JlZGVudGlhbHNSb2xlLFxuICAgICAgICBpbnRlZ3JhdGlvblJlc3BvbnNlczogaW50ZWdyYXRpb25SZXNwb25zZSgpLFxuICAgICAgICBwYXNzdGhyb3VnaEJlaGF2aW9yOiBQYXNzdGhyb3VnaEJlaGF2aW9yLk5FVkVSLFxuICAgICAgICByZXF1ZXN0VGVtcGxhdGVzOiByZXF1ZXN0VGVtcGxhdGVzKHN0YXRlTWFjaGluZSwgb3B0aW9ucyksXG4gICAgICAgIC4uLm9wdGlvbnMsXG4gICAgICB9LFxuICAgIH0pO1xuXG4gICAgdGhpcy5zdGF0ZU1hY2hpbmUgPSBzdGF0ZU1hY2hpbmU7XG4gIH1cblxuICBwdWJsaWMgYmluZChtZXRob2Q6IE1ldGhvZCk6IEludGVncmF0aW9uQ29uZmlnIHtcbiAgICBjb25zdCBiaW5kUmVzdWx0ID0gc3VwZXIuYmluZChtZXRob2QpO1xuXG4gICAgY29uc3QgY3JlZGVudGlhbHNSb2xlID0gYmluZFJlc3VsdC5vcHRpb25zPy5jcmVkZW50aWFsc1JvbGUgPz8gbmV3IGlhbS5Sb2xlKG1ldGhvZCwgJ1N0YXJ0U3luY0V4ZWN1dGlvblJvbGUnLCB7XG4gICAgICBhc3N1bWVkQnk6IG5ldyBpYW0uU2VydmljZVByaW5jaXBhbCgnYXBpZ2F0ZXdheS5hbWF6b25hd3MuY29tJyksXG4gICAgfSk7XG4gICAgdGhpcy5zdGF0ZU1hY2hpbmUuZ3JhbnRTdGFydFN5bmNFeGVjdXRpb24oY3JlZGVudGlhbHNSb2xlKTtcblxuICAgIGxldCBzdGF0ZU1hY2hpbmVOYW1lO1xuXG4gICAgaWYgKHRoaXMuc3RhdGVNYWNoaW5lIGluc3RhbmNlb2Ygc2ZuLlN0YXRlTWFjaGluZSkge1xuICAgICAgY29uc3Qgc3RhdGVNYWNoaW5lVHlwZSA9ICh0aGlzLnN0YXRlTWFjaGluZSBhcyBzZm4uU3RhdGVNYWNoaW5lKS5zdGF0ZU1hY2hpbmVUeXBlO1xuICAgICAgaWYgKHN0YXRlTWFjaGluZVR5cGUgIT09IHNmbi5TdGF0ZU1hY2hpbmVUeXBlLkVYUFJFU1MpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdTdGF0ZSBNYWNoaW5lIG11c3QgYmUgb2YgdHlwZSBcIkVYUFJFU1NcIi4gUGxlYXNlIHVzZSBTdGF0ZU1hY2hpbmVUeXBlLkVYUFJFU1MgYXMgdGhlIHN0YXRlTWFjaGluZVR5cGUnKTtcbiAgICAgIH1cblxuICAgICAgLy9pZiBub3QgaW1wb3J0ZWQsIGV4dHJhY3QgdGhlIG5hbWUgZnJvbSB0aGUgQ0ZOIGxheWVyIHRvIHJlYWNoIHRoZVxuICAgICAgLy9saXRlcmFsIHZhbHVlIGlmIGl0IGlzIGdpdmVuIChyYXRoZXIgdGhhbiBhIHRva2VuKVxuICAgICAgc3RhdGVNYWNoaW5lTmFtZSA9ICh0aGlzLnN0YXRlTWFjaGluZS5ub2RlLmRlZmF1bHRDaGlsZCBhcyBzZm4uQ2ZuU3RhdGVNYWNoaW5lKS5zdGF0ZU1hY2hpbmVOYW1lO1xuICAgIH0gZWxzZSB7XG4gICAgICAvL2ltcG9ydGVkIHN0YXRlIG1hY2hpbmVcbiAgICAgIHN0YXRlTWFjaGluZU5hbWUgPSBgU3RhdGVNYWNoaW5lLSR7dGhpcy5zdGF0ZU1hY2hpbmUuc3RhY2subm9kZS5hZGRyfWA7XG4gICAgfVxuXG4gICAgbGV0IGRlcGxveW1lbnRUb2tlbjtcblxuICAgIGlmIChzdGF0ZU1hY2hpbmVOYW1lICE9PSB1bmRlZmluZWQgJiYgIVRva2VuLmlzVW5yZXNvbHZlZChzdGF0ZU1hY2hpbmVOYW1lKSkge1xuICAgICAgZGVwbG95bWVudFRva2VuID0gSlNPTi5zdHJpbmdpZnkoeyBzdGF0ZU1hY2hpbmVOYW1lIH0pO1xuICAgIH1cblxuICAgIGZvciAoY29uc3QgbWV0aG9kUmVzcG9uc2Ugb2YgTUVUSE9EX1JFU1BPTlNFUykge1xuICAgICAgbWV0aG9kLmFkZE1ldGhvZFJlc3BvbnNlKG1ldGhvZFJlc3BvbnNlKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgLi4uYmluZFJlc3VsdCxcbiAgICAgIG9wdGlvbnM6IHtcbiAgICAgICAgLi4uYmluZFJlc3VsdC5vcHRpb25zLFxuICAgICAgICBjcmVkZW50aWFsc1JvbGUsXG4gICAgICB9LFxuICAgICAgZGVwbG95bWVudFRva2VuLFxuICAgIH07XG4gIH1cbn1cblxuLyoqXG4gKiBEZWZpbmVzIHRoZSBpbnRlZ3JhdGlvbiByZXNwb25zZSB0aGF0IHBhc3NlcyB0aGUgcmVzdWx0IG9uIHN1Y2Nlc3MsXG4gKiBvciB0aGUgZXJyb3Igb24gZmFpbHVyZSwgZnJvbSB0aGUgc3luY2hyb25vdXMgZXhlY3V0aW9uIHRvIHRoZSBjYWxsZXIuXG4gKlxuICogQHJldHVybnMgaW50ZWdyYXRpb25SZXNwb25zZSBtYXBwaW5nXG4gKi9cbmZ1bmN0aW9uIGludGVncmF0aW9uUmVzcG9uc2UoKSB7XG4gIGNvbnN0IGVycm9yUmVzcG9uc2UgPSBbXG4gICAge1xuICAgICAgLyoqXG4gICAgICAgKiBTcGVjaWZpZXMgdGhlIHJlZ3VsYXIgZXhwcmVzc2lvbiAocmVnZXgpIHBhdHRlcm4gdXNlZCB0byBjaG9vc2VcbiAgICAgICAqIGFuIGludGVncmF0aW9uIHJlc3BvbnNlIGJhc2VkIG9uIHRoZSByZXNwb25zZSBmcm9tIHRoZSBiYWNrIGVuZC5cbiAgICAgICAqIEluIHRoaXMgY2FzZSBpdCB3aWxsIG1hdGNoIGFsbCAnNFhYJyBIVFRQIEVycm9yc1xuICAgICAgICovXG4gICAgICBzZWxlY3Rpb25QYXR0ZXJuOiAnNFxcXFxkezJ9JyxcbiAgICAgIHN0YXR1c0NvZGU6ICc0MDAnLFxuICAgICAgcmVzcG9uc2VUZW1wbGF0ZXM6IHtcbiAgICAgICAgJ2FwcGxpY2F0aW9uL2pzb24nOiBge1xuICAgICAgICAgICAgXCJlcnJvclwiOiBcIkJhZCByZXF1ZXN0IVwiXG4gICAgICAgICAgfWAsXG4gICAgICB9LFxuICAgIH0sXG4gICAge1xuICAgICAgLyoqXG4gICAgICAgKiBNYXRjaCBhbGwgJzVYWCcgSFRUUCBFcnJvcnNcbiAgICAgICAqL1xuICAgICAgc2VsZWN0aW9uUGF0dGVybjogJzVcXFxcZHsyfScsXG4gICAgICBzdGF0dXNDb2RlOiAnNTAwJyxcbiAgICAgIHJlc3BvbnNlVGVtcGxhdGVzOiB7XG4gICAgICAgICdhcHBsaWNhdGlvbi9qc29uJzogJ1wiZXJyb3JcIjogJGlucHV0LnBhdGgoXFwnJC5lcnJvclxcJyknLFxuICAgICAgfSxcbiAgICB9LFxuICBdO1xuXG4gIGNvbnN0IGludGVnUmVzcG9uc2UgPSBbXG4gICAge1xuICAgICAgc3RhdHVzQ29kZTogJzIwMCcsXG4gICAgICByZXNwb25zZVRlbXBsYXRlczoge1xuICAgICAgICAvKiBlc2xpbnQtZGlzYWJsZSAqL1xuICAgICAgICAnYXBwbGljYXRpb24vanNvbic6IFtcbiAgICAgICAgICAnI3NldCgkaW5wdXRSb290ID0gJGlucHV0LnBhdGgoXFwnJFxcJykpJyxcbiAgICAgICAgICAnI2lmKCRpbnB1dC5wYXRoKFxcJyQuc3RhdHVzXFwnKS50b1N0cmluZygpLmVxdWFscyhcIkZBSUxFRFwiKSknLFxuICAgICAgICAgICAgJyNzZXQoJGNvbnRleHQucmVzcG9uc2VPdmVycmlkZS5zdGF0dXMgPSA1MDApJyxcbiAgICAgICAgICAgICd7JyxcbiAgICAgICAgICAgICAgJ1wiZXJyb3JcIjogXCIkaW5wdXQucGF0aChcXCckLmVycm9yXFwnKVwiLCcsXG4gICAgICAgICAgICAgICdcImNhdXNlXCI6IFwiJGlucHV0LnBhdGgoXFwnJC5jYXVzZVxcJylcIicsXG4gICAgICAgICAgICAnfScsXG4gICAgICAgICAgJyNlbHNlJyxcbiAgICAgICAgICAgICckaW5wdXQucGF0aChcXCckLm91dHB1dFxcJyknLFxuICAgICAgICAgICcjZW5kJyxcbiAgICAgICAgLyogZXNsaW50LWVuYWJsZSAqL1xuICAgICAgICBdLmpvaW4oJ1xcbicpLFxuICAgICAgfSxcbiAgICB9LFxuICAgIC4uLmVycm9yUmVzcG9uc2UsXG4gIF07XG5cbiAgcmV0dXJuIGludGVnUmVzcG9uc2U7XG59XG5cbi8qKlxuICogRGVmaW5lcyB0aGUgcmVxdWVzdCB0ZW1wbGF0ZSB0aGF0IHdpbGwgYmUgdXNlZCBmb3IgdGhlIGludGVncmF0aW9uXG4gKiBAcGFyYW0gc3RhdGVNYWNoaW5lXG4gKiBAcGFyYW0gb3B0aW9uc1xuICogQHJldHVybnMgcmVxdWVzdFRlbXBsYXRlXG4gKi9cbmZ1bmN0aW9uIHJlcXVlc3RUZW1wbGF0ZXMoc3RhdGVNYWNoaW5lOiBzZm4uSVN0YXRlTWFjaGluZSwgb3B0aW9uczogU3RlcEZ1bmN0aW9uc0V4ZWN1dGlvbkludGVncmF0aW9uT3B0aW9ucykge1xuICBjb25zdCB0ZW1wbGF0ZVN0ciA9IHRlbXBsYXRlU3RyaW5nKHN0YXRlTWFjaGluZSwgb3B0aW9ucyk7XG5cbiAgY29uc3QgcmVxdWVzdFRlbXBsYXRlOiB7IFtjb250ZW50VHlwZTpzdHJpbmddIDogc3RyaW5nIH0gPVxuICAgIHtcbiAgICAgICdhcHBsaWNhdGlvbi9qc29uJzogdGVtcGxhdGVTdHIsXG4gICAgfTtcblxuICByZXR1cm4gcmVxdWVzdFRlbXBsYXRlO1xufVxuXG4vKipcbiAqIFJlYWRzIHRoZSBWVEwgdGVtcGxhdGUgYW5kIHJldHVybnMgdGhlIHRlbXBsYXRlIHN0cmluZyB0byBiZSB1c2VkXG4gKiBmb3IgdGhlIHJlcXVlc3QgdGVtcGxhdGUuXG4gKlxuICogQHBhcmFtIHN0YXRlTWFjaGluZVxuICogQHBhcmFtIGluY2x1ZGVSZXF1ZXN0Q29udGV4dFxuICogQHBhcmFtIG9wdGlvbnNcbiAqIEByZXV0cm5zIHRlbXBsYXRlU3RyaW5nXG4gKi9cbmZ1bmN0aW9uIHRlbXBsYXRlU3RyaW5nKFxuICBzdGF0ZU1hY2hpbmU6IHNmbi5JU3RhdGVNYWNoaW5lLFxuICBvcHRpb25zOiBTdGVwRnVuY3Rpb25zRXhlY3V0aW9uSW50ZWdyYXRpb25PcHRpb25zKTogc3RyaW5nIHtcbiAgbGV0IHRlbXBsYXRlU3RyOiBzdHJpbmc7XG5cbiAgbGV0IHJlcXVlc3RDb250ZXh0U3RyID0gJyc7XG5cbiAgY29uc3QgaW5jbHVkZUhlYWRlciA9IG9wdGlvbnMuaGVhZGVycz8/IGZhbHNlO1xuICBjb25zdCBpbmNsdWRlUXVlcnlTdHJpbmcgPSBvcHRpb25zLnF1ZXJ5c3RyaW5nPz8gdHJ1ZTtcbiAgY29uc3QgaW5jbHVkZVBhdGggPSBvcHRpb25zLnBhdGg/PyB0cnVlO1xuICBjb25zdCBpbmNsdWRlQXV0aG9yaXplciA9IG9wdGlvbnMuYXV0aG9yaXplciA/PyBmYWxzZTtcblxuICBpZiAob3B0aW9ucy5yZXF1ZXN0Q29udGV4dCAmJiBPYmplY3Qua2V5cyhvcHRpb25zLnJlcXVlc3RDb250ZXh0KS5sZW5ndGggPiAwKSB7XG4gICAgcmVxdWVzdENvbnRleHRTdHIgPSByZXF1ZXN0Q29udGV4dChvcHRpb25zLnJlcXVlc3RDb250ZXh0KTtcbiAgfVxuXG4gIHRlbXBsYXRlU3RyID0gZnMucmVhZEZpbGVTeW5jKHBhdGguam9pbihfX2Rpcm5hbWUsICdzdGVwZnVuY3Rpb25zLnZ0bCcpLCB7IGVuY29kaW5nOiAndXRmLTgnIH0pO1xuICB0ZW1wbGF0ZVN0ciA9IHRlbXBsYXRlU3RyLnJlcGxhY2UoJyVTVEFURU1BQ0hJTkUlJywgc3RhdGVNYWNoaW5lLnN0YXRlTWFjaGluZUFybik7XG4gIHRlbXBsYXRlU3RyID0gdGVtcGxhdGVTdHIucmVwbGFjZSgnJUlOQ0xVREVfSEVBREVSUyUnLCBTdHJpbmcoaW5jbHVkZUhlYWRlcikpO1xuICB0ZW1wbGF0ZVN0ciA9IHRlbXBsYXRlU3RyLnJlcGxhY2UoJyVJTkNMVURFX1FVRVJZU1RSSU5HJScsIFN0cmluZyhpbmNsdWRlUXVlcnlTdHJpbmcpKTtcbiAgdGVtcGxhdGVTdHIgPSB0ZW1wbGF0ZVN0ci5yZXBsYWNlKCclSU5DTFVERV9QQVRIJScsIFN0cmluZyhpbmNsdWRlUGF0aCkpO1xuICB0ZW1wbGF0ZVN0ciA9IHRlbXBsYXRlU3RyLnJlcGxhY2UoJyVJTkNMVURFX0FVVEhPUklaRVIlJywgU3RyaW5nKGluY2x1ZGVBdXRob3JpemVyKSk7XG4gIHRlbXBsYXRlU3RyID0gdGVtcGxhdGVTdHIucmVwbGFjZSgnJVJFUVVFU1RDT05URVhUJScsIHJlcXVlc3RDb250ZXh0U3RyKTtcblxuICByZXR1cm4gdGVtcGxhdGVTdHI7XG59XG5cbmZ1bmN0aW9uIHJlcXVlc3RDb250ZXh0KHJlcXVlc3RDb250ZXh0T2JqOiBSZXF1ZXN0Q29udGV4dCB8IHVuZGVmaW5lZCk6IHN0cmluZyB7XG4gIGNvbnN0IGNvbnRleHQgPSB7XG4gICAgYWNjb3VudElkOiByZXF1ZXN0Q29udGV4dE9iaj8uYWNjb3VudElkPyAnJGNvbnRleHQuaWRlbnRpdHkuYWNjb3VudElkJzogdW5kZWZpbmVkLFxuICAgIGFwaUlkOiByZXF1ZXN0Q29udGV4dE9iaj8uYXBpSWQ/ICckY29udGV4dC5hcGlJZCc6IHVuZGVmaW5lZCxcbiAgICBhcGlLZXk6IHJlcXVlc3RDb250ZXh0T2JqPy5hcGlLZXk/ICckY29udGV4dC5pZGVudGl0eS5hcGlLZXknOiB1bmRlZmluZWQsXG4gICAgYXV0aG9yaXplclByaW5jaXBhbElkOiByZXF1ZXN0Q29udGV4dE9iaj8uYXV0aG9yaXplclByaW5jaXBhbElkPyAnJGNvbnRleHQuYXV0aG9yaXplci5wcmluY2lwYWxJZCc6IHVuZGVmaW5lZCxcbiAgICBjYWxsZXI6IHJlcXVlc3RDb250ZXh0T2JqPy5jYWxsZXI/ICckY29udGV4dC5pZGVudGl0eS5jYWxsZXInOiB1bmRlZmluZWQsXG4gICAgY29nbml0b0F1dGhlbnRpY2F0aW9uUHJvdmlkZXI6IHJlcXVlc3RDb250ZXh0T2JqPy5jb2duaXRvQXV0aGVudGljYXRpb25Qcm92aWRlcj8gJyRjb250ZXh0LmlkZW50aXR5LmNvZ25pdG9BdXRoZW50aWNhdGlvblByb3ZpZGVyJzogdW5kZWZpbmVkLFxuICAgIGNvZ25pdG9BdXRoZW50aWNhdGlvblR5cGU6IHJlcXVlc3RDb250ZXh0T2JqPy5jb2duaXRvQXV0aGVudGljYXRpb25UeXBlPyAnJGNvbnRleHQuaWRlbnRpdHkuY29nbml0b0F1dGhlbnRpY2F0aW9uVHlwZSc6IHVuZGVmaW5lZCxcbiAgICBjb2duaXRvSWRlbnRpdHlJZDogcmVxdWVzdENvbnRleHRPYmo/LmNvZ25pdG9JZGVudGl0eUlkPyAnJGNvbnRleHQuaWRlbnRpdHkuY29nbml0b0lkZW50aXR5SWQnOiB1bmRlZmluZWQsXG4gICAgY29nbml0b0lkZW50aXR5UG9vbElkOiByZXF1ZXN0Q29udGV4dE9iaj8uY29nbml0b0lkZW50aXR5UG9vbElkPyAnJGNvbnRleHQuaWRlbnRpdHkuY29nbml0b0lkZW50aXR5UG9vbElkJzogdW5kZWZpbmVkLFxuICAgIGh0dHBNZXRob2Q6IHJlcXVlc3RDb250ZXh0T2JqPy5odHRwTWV0aG9kPyAnJGNvbnRleHQuaHR0cE1ldGhvZCc6IHVuZGVmaW5lZCxcbiAgICBzdGFnZTogcmVxdWVzdENvbnRleHRPYmo/LnN0YWdlPyAnJGNvbnRleHQuc3RhZ2UnOiB1bmRlZmluZWQsXG4gICAgc291cmNlSXA6IHJlcXVlc3RDb250ZXh0T2JqPy5zb3VyY2VJcD8gJyRjb250ZXh0LmlkZW50aXR5LnNvdXJjZUlwJzogdW5kZWZpbmVkLFxuICAgIHVzZXI6IHJlcXVlc3RDb250ZXh0T2JqPy51c2VyPyAnJGNvbnRleHQuaWRlbnRpdHkudXNlcic6IHVuZGVmaW5lZCxcbiAgICB1c2VyQWdlbnQ6IHJlcXVlc3RDb250ZXh0T2JqPy51c2VyQWdlbnQ/ICckY29udGV4dC5pZGVudGl0eS51c2VyQWdlbnQnOiB1bmRlZmluZWQsXG4gICAgdXNlckFybjogcmVxdWVzdENvbnRleHRPYmo/LnVzZXJBcm4/ICckY29udGV4dC5pZGVudGl0eS51c2VyQXJuJzogdW5kZWZpbmVkLFxuICAgIHJlcXVlc3RJZDogcmVxdWVzdENvbnRleHRPYmo/LnJlcXVlc3RJZD8gJyRjb250ZXh0LnJlcXVlc3RJZCc6IHVuZGVmaW5lZCxcbiAgICByZXNvdXJjZUlkOiByZXF1ZXN0Q29udGV4dE9iaj8ucmVzb3VyY2VJZD8gJyRjb250ZXh0LnJlc291cmNlSWQnOiB1bmRlZmluZWQsXG4gICAgcmVzb3VyY2VQYXRoOiByZXF1ZXN0Q29udGV4dE9iaj8ucmVzb3VyY2VQYXRoPyAnJGNvbnRleHQucmVzb3VyY2VQYXRoJzogdW5kZWZpbmVkLFxuICB9O1xuXG4gIGNvbnN0IGNvbnRleHRBc1N0cmluZyA9IEpTT04uc3RyaW5naWZ5KGNvbnRleHQpO1xuXG4gIC8vIFRoZSBWVEwgVGVtcGxhdGUgY29uZmxpY3RzIHdpdGggZG91YmxlLXF1b3RlcyAoXCIpIGZvciBzdHJpbmdzLlxuICAvLyBCZWZvcmUgc2VuZGluZyB0byB0aGUgdGVtcGxhdGUsIHdlIHJlcGxhY2UgZG91YmxlLXF1b3RlcyAoXCIpIHdpdGggQEAgYW5kIHJlcGxhY2UgaXQgYmFjayBpbnNpZGUgdGhlIC52dGwgZmlsZVxuICBjb25zdCBkb3VibGVxdW90ZXMgPSAnXCInO1xuICBjb25zdCByZXBsYWNlV2l0aCA9ICdAQCc7XG4gIHJldHVybiBjb250ZXh0QXNTdHJpbmcuc3BsaXQoZG91YmxlcXVvdGVzKS5qb2luKHJlcGxhY2VXaXRoKTtcbn1cblxuLyoqXG4gKiBNZXRob2QgcmVzcG9uc2UgbW9kZWwgZm9yIGVhY2ggSFRUUCBjb2RlIHJlc3BvbnNlXG4gKi9cbmNvbnN0IE1FVEhPRF9SRVNQT05TRVMgPSBbXG4gIHtcbiAgICBzdGF0dXNDb2RlOiAnMjAwJyxcbiAgICByZXNwb25zZU1vZGVsczoge1xuICAgICAgJ2FwcGxpY2F0aW9uL2pzb24nOiBNb2RlbC5FTVBUWV9NT0RFTCxcbiAgICB9LFxuICB9LFxuICB7XG4gICAgc3RhdHVzQ29kZTogJzQwMCcsXG4gICAgcmVzcG9uc2VNb2RlbHM6IHtcbiAgICAgICdhcHBsaWNhdGlvbi9qc29uJzogTW9kZWwuRVJST1JfTU9ERUwsXG4gICAgfSxcbiAgfSxcbiAge1xuICAgIHN0YXR1c0NvZGU6ICc1MDAnLFxuICAgIHJlc3BvbnNlTW9kZWxzOiB7XG4gICAgICAnYXBwbGljYXRpb24vanNvbic6IE1vZGVsLkVSUk9SX01PREVMLFxuICAgIH0sXG4gIH0sXG5dO1xuIl19 |
\ | No newline at end of file |