@aws-cdk/core
Version:
AWS Cloud Development Kit Core Library
215 lines • 31.7 kB
JavaScript
"use strict";
const lib_1 = require("../lib");
const intrinsic_1 = require("../lib/private/intrinsic");
const util_1 = require("./util");
module.exports = {
'create from components with defaults'(test) {
const stack = new lib_1.Stack();
const arn = stack.formatArn({
service: 'sqs',
resource: 'myqueuename',
});
const pseudo = new lib_1.ScopedAws(stack);
test.deepEqual(stack.resolve(arn), stack.resolve(`arn:${pseudo.partition}:sqs:${pseudo.region}:${pseudo.accountId}:myqueuename`));
test.done();
},
'create from components with specific values for the various components'(test) {
const stack = new lib_1.Stack();
const arn = stack.formatArn({
service: 'dynamodb',
resource: 'table',
account: '123456789012',
region: 'us-east-1',
partition: 'aws-cn',
resourceName: 'mytable/stream/label',
});
test.deepEqual(stack.resolve(arn), 'arn:aws-cn:dynamodb:us-east-1:123456789012:table/mytable/stream/label');
test.done();
},
'allow empty string in components'(test) {
const stack = new lib_1.Stack();
const arn = stack.formatArn({
service: 's3',
resource: 'my-bucket',
account: '',
region: '',
partition: 'aws-cn',
});
test.deepEqual(stack.resolve(arn), 'arn:aws-cn:s3:::my-bucket');
test.done();
},
'resourcePathSep can be set to ":" instead of the default "/"'(test) {
const stack = new lib_1.Stack();
const arn = stack.formatArn({
service: 'codedeploy',
resource: 'application',
sep: ':',
resourceName: 'WordPress_App',
});
const pseudo = new lib_1.ScopedAws(stack);
test.deepEqual(stack.resolve(arn), stack.resolve(`arn:${pseudo.partition}:codedeploy:${pseudo.region}:${pseudo.accountId}:application:WordPress_App`));
test.done();
},
'resourcePathSep can be set to "" instead of the default "/"'(test) {
const stack = new lib_1.Stack();
const arn = stack.formatArn({
service: 'ssm',
resource: 'parameter',
sep: '',
resourceName: '/parameter-name',
});
const pseudo = new lib_1.ScopedAws(stack);
test.deepEqual(stack.resolve(arn), stack.resolve(`arn:${pseudo.partition}:ssm:${pseudo.region}:${pseudo.accountId}:parameter/parameter-name`));
test.done();
},
'fails if resourcePathSep is neither ":" nor "/"'(test) {
const stack = new lib_1.Stack();
test.throws(() => stack.formatArn({
service: 'foo',
resource: 'bar',
sep: 'x'
}));
test.done();
},
'Arn.parse(s)': {
'fails': {
'if doesn\'t start with "arn:"'(test) {
const stack = new lib_1.Stack();
test.throws(() => stack.parseArn('barn:foo:x:a:1:2'), /ARNs must start with "arn:": barn:foo/);
test.done();
},
'if the ARN doesnt have enough components'(test) {
const stack = new lib_1.Stack();
test.throws(() => stack.parseArn('arn:is:too:short'), /ARNs must have at least 6 components: arn:is:too:short/);
test.done();
},
'if "service" is not specified'(test) {
const stack = new lib_1.Stack();
test.throws(() => stack.parseArn('arn:aws::4:5:6'), /The `service` component \(3rd component\) is required/);
test.done();
},
'if "resource" is not specified'(test) {
const stack = new lib_1.Stack();
test.throws(() => stack.parseArn('arn:aws:service:::'), /The `resource` component \(6th component\) is required/);
test.done();
},
},
'various successful parses'(test) {
const stack = new lib_1.Stack();
const tests = {
'arn:aws:a4b:region:accountid:resourcetype/resource': {
partition: 'aws',
service: 'a4b',
region: 'region',
account: 'accountid',
resource: 'resourcetype',
resourceName: 'resource',
sep: '/',
},
'arn:aws:apigateway:us-east-1::a123456789012bc3de45678901f23a45:/test/mydemoresource/*': {
partition: 'aws',
service: 'apigateway',
region: 'us-east-1',
account: '',
resource: 'a123456789012bc3de45678901f23a45',
sep: ':',
resourceName: '/test/mydemoresource/*',
},
'arn:aws-cn:cloud9::123456789012:environment:81e900317347585a0601e04c8d52eaEX': {
partition: 'aws-cn',
service: 'cloud9',
region: '',
account: '123456789012',
resource: 'environment',
resourceName: '81e900317347585a0601e04c8d52eaEX',
sep: ':',
},
'arn::cognito-sync:::identitypool/us-east-1:1a1a1a1a-ffff-1111-9999-12345678:bla': {
service: 'cognito-sync',
region: '',
account: '',
resource: 'identitypool',
resourceName: 'us-east-1:1a1a1a1a-ffff-1111-9999-12345678:bla',
sep: '/',
},
'arn:aws:s3:::my_corporate_bucket': {
partition: 'aws',
service: 's3',
region: '',
account: '',
resource: 'my_corporate_bucket',
},
};
Object.keys(tests).forEach(arn => {
const expected = tests[arn];
test.deepEqual(stack.parseArn(arn), expected, arn);
});
test.done();
},
'a Token with : separator'(test) {
const stack = new lib_1.Stack();
const theToken = { Ref: 'SomeParameter' };
const parsed = stack.parseArn(new intrinsic_1.Intrinsic(theToken).toString(), ':');
test.deepEqual(stack.resolve(parsed.partition), { 'Fn::Select': [1, { 'Fn::Split': [':', theToken] }] });
test.deepEqual(stack.resolve(parsed.service), { 'Fn::Select': [2, { 'Fn::Split': [':', theToken] }] });
test.deepEqual(stack.resolve(parsed.region), { 'Fn::Select': [3, { 'Fn::Split': [':', theToken] }] });
test.deepEqual(stack.resolve(parsed.account), { 'Fn::Select': [4, { 'Fn::Split': [':', theToken] }] });
test.deepEqual(stack.resolve(parsed.resource), { 'Fn::Select': [5, { 'Fn::Split': [':', theToken] }] });
test.deepEqual(stack.resolve(parsed.resourceName), { 'Fn::Select': [6, { 'Fn::Split': [':', theToken] }] });
test.equal(parsed.sep, ':');
test.done();
},
'a Token with / separator'(test) {
const stack = new lib_1.Stack();
const theToken = { Ref: 'SomeParameter' };
const parsed = stack.parseArn(new intrinsic_1.Intrinsic(theToken).toString());
test.equal(parsed.sep, '/');
// tslint:disable-next-line:max-line-length
test.deepEqual(stack.resolve(parsed.resource), { 'Fn::Select': [0, { 'Fn::Split': ['/', { 'Fn::Select': [5, { 'Fn::Split': [':', theToken] }] }] }] });
// tslint:disable-next-line:max-line-length
test.deepEqual(stack.resolve(parsed.resourceName), { 'Fn::Select': [1, { 'Fn::Split': ['/', { 'Fn::Select': [5, { 'Fn::Split': [':', theToken] }] }] }] });
test.done();
},
'returns empty string ARN components'(test) {
const stack = new lib_1.Stack();
const arn = 'arn:aws:iam::123456789012:role/abc123';
const expected = {
partition: 'aws',
service: 'iam',
region: '',
account: '123456789012',
resource: 'role',
resourceName: 'abc123',
sep: '/',
};
test.deepEqual(stack.parseArn(arn), expected, arn);
test.done();
},
},
'can use a fully specified ARN from a different stack without incurring an import'(test) {
// GIVEN
const stack1 = new lib_1.Stack(undefined, 'Stack1', { env: { account: '12345678', region: 'us-turbo-5' } });
const stack2 = new lib_1.Stack(undefined, 'Stack2', { env: { account: '87654321', region: 'us-turbo-1' } });
// WHEN
const arn = stack1.formatArn({
// No partition specified here
service: 'bla',
resource: 'thing',
resourceName: 'thong',
});
new lib_1.CfnOutput(stack2, 'SomeValue', { value: arn });
// THEN
test.deepEqual(util_1.toCloudFormation(stack2), {
Outputs: {
SomeValue: {
Value: {
// Look ma, no Fn::ImportValue!
'Fn::Join': ['', ['arn:', { Ref: 'AWS::Partition' }, ':bla:us-turbo-5:12345678:thing/thong']]
},
},
},
});
test.done();
},
};
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidGVzdC5hcm4uanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyJ0ZXN0LmFybi50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQ0EsZ0NBQW9FO0FBQ3BFLHdEQUFxRDtBQUNyRCxpQ0FBMEM7QUFFMUMsaUJBQVM7SUFDUCxzQ0FBc0MsQ0FBQyxJQUFVO1FBQy9DLE1BQU0sS0FBSyxHQUFHLElBQUksV0FBSyxFQUFFLENBQUM7UUFFMUIsTUFBTSxHQUFHLEdBQUcsS0FBSyxDQUFDLFNBQVMsQ0FBQztZQUMxQixPQUFPLEVBQUUsS0FBSztZQUNkLFFBQVEsRUFBRSxhQUFhO1NBQ3hCLENBQUMsQ0FBQztRQUVILE1BQU0sTUFBTSxHQUFHLElBQUksZUFBUyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBRXBDLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsRUFDL0IsS0FBSyxDQUFDLE9BQU8sQ0FBQyxPQUFPLE1BQU0sQ0FBQyxTQUFTLFFBQVEsTUFBTSxDQUFDLE1BQU0sSUFBSSxNQUFNLENBQUMsU0FBUyxjQUFjLENBQUMsQ0FBQyxDQUFDO1FBQ2pHLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNkLENBQUM7SUFFRCx3RUFBd0UsQ0FBQyxJQUFVO1FBQ2pGLE1BQU0sS0FBSyxHQUFHLElBQUksV0FBSyxFQUFFLENBQUM7UUFFMUIsTUFBTSxHQUFHLEdBQUcsS0FBSyxDQUFDLFNBQVMsQ0FBQztZQUMxQixPQUFPLEVBQUUsVUFBVTtZQUNuQixRQUFRLEVBQUUsT0FBTztZQUNqQixPQUFPLEVBQUUsY0FBYztZQUN2QixNQUFNLEVBQUUsV0FBVztZQUNuQixTQUFTLEVBQUUsUUFBUTtZQUNuQixZQUFZLEVBQUUsc0JBQXNCO1NBQ3JDLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsRUFDL0IsdUVBQXVFLENBQUMsQ0FBQztRQUMzRSxJQUFJLENBQUMsSUFBSSxFQUFFLENBQUM7SUFDZCxDQUFDO0lBRUQsa0NBQWtDLENBQUMsSUFBVTtRQUMzQyxNQUFNLEtBQUssR0FBRyxJQUFJLFdBQUssRUFBRSxDQUFDO1FBRTFCLE1BQU0sR0FBRyxHQUFHLEtBQUssQ0FBQyxTQUFTLENBQUM7WUFDMUIsT0FBTyxFQUFFLElBQUk7WUFDYixRQUFRLEVBQUUsV0FBVztZQUNyQixPQUFPLEVBQUUsRUFBRTtZQUNYLE1BQU0sRUFBRSxFQUFFO1lBQ1YsU0FBUyxFQUFFLFFBQVE7U0FDcEIsQ0FBQyxDQUFDO1FBRUgsSUFBSSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLEdBQUcsQ0FBQyxFQUMvQiwyQkFBMkIsQ0FBQyxDQUFDO1FBRS9CLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNkLENBQUM7SUFFRCw4REFBOEQsQ0FBQyxJQUFVO1FBQ3ZFLE1BQU0sS0FBSyxHQUFHLElBQUksV0FBSyxFQUFFLENBQUM7UUFFMUIsTUFBTSxHQUFHLEdBQUcsS0FBSyxDQUFDLFNBQVMsQ0FBQztZQUMxQixPQUFPLEVBQUUsWUFBWTtZQUNyQixRQUFRLEVBQUUsYUFBYTtZQUN2QixHQUFHLEVBQUUsR0FBRztZQUNSLFlBQVksRUFBRSxlQUFlO1NBQzlCLENBQUMsQ0FBQztRQUVILE1BQU0sTUFBTSxHQUFHLElBQUksZUFBUyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBRXBDLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsRUFDL0IsS0FBSyxDQUFDLE9BQU8sQ0FBQyxPQUFPLE1BQU0sQ0FBQyxTQUFTLGVBQWUsTUFBTSxDQUFDLE1BQU0sSUFBSSxNQUFNLENBQUMsU0FBUyw0QkFBNEIsQ0FBQyxDQUFDLENBQUM7UUFDdEgsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO0lBQ2QsQ0FBQztJQUVELDZEQUE2RCxDQUFDLElBQVU7UUFDdEUsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztRQUUxQixNQUFNLEdBQUcsR0FBRyxLQUFLLENBQUMsU0FBUyxDQUFDO1lBQzFCLE9BQU8sRUFBRSxLQUFLO1lBQ2QsUUFBUSxFQUFFLFdBQVc7WUFDckIsR0FBRyxFQUFFLEVBQUU7WUFDUCxZQUFZLEVBQUUsaUJBQWlCO1NBQ2hDLENBQUMsQ0FBQztRQUVILE1BQU0sTUFBTSxHQUFHLElBQUksZUFBUyxDQUFDLEtBQUssQ0FBQyxDQUFDO1FBRXBDLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsRUFDL0IsS0FBSyxDQUFDLE9BQU8sQ0FBQyxPQUFPLE1BQU0sQ0FBQyxTQUFTLFFBQVEsTUFBTSxDQUFDLE1BQU0sSUFBSSxNQUFNLENBQUMsU0FBUywyQkFBMkIsQ0FBQyxDQUFDLENBQUM7UUFDOUcsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO0lBQ2QsQ0FBQztJQUVELGlEQUFpRCxDQUFDLElBQVU7UUFDMUQsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztRQUUxQixJQUFJLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLEtBQUssQ0FBQyxTQUFTLENBQUM7WUFDaEMsT0FBTyxFQUFFLEtBQUs7WUFDZCxRQUFRLEVBQUUsS0FBSztZQUNmLEdBQUcsRUFBRSxHQUFHO1NBQUUsQ0FBQyxDQUFDLENBQUM7UUFDZixJQUFJLENBQUMsSUFBSSxFQUFFLENBQUM7SUFDZCxDQUFDO0lBRUQsY0FBYyxFQUFFO1FBRWQsT0FBTyxFQUFFO1lBQ1AsK0JBQStCLENBQUMsSUFBVTtnQkFDeEMsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztnQkFDMUIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLGtCQUFrQixDQUFDLEVBQUUsdUNBQXVDLENBQUMsQ0FBQztnQkFDL0YsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO1lBQ2QsQ0FBQztZQUVELDBDQUEwQyxDQUFDLElBQVU7Z0JBQ25ELE1BQU0sS0FBSyxHQUFHLElBQUksV0FBSyxFQUFFLENBQUM7Z0JBQzFCLElBQUksQ0FBQyxNQUFNLENBQUMsR0FBRyxFQUFFLENBQUMsS0FBSyxDQUFDLFFBQVEsQ0FBQyxrQkFBa0IsQ0FBQyxFQUFFLHdEQUF3RCxDQUFDLENBQUM7Z0JBQ2hILElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztZQUNkLENBQUM7WUFFRCwrQkFBK0IsQ0FBQyxJQUFVO2dCQUN4QyxNQUFNLEtBQUssR0FBRyxJQUFJLFdBQUssRUFBRSxDQUFDO2dCQUMxQixJQUFJLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsZ0JBQWdCLENBQUMsRUFBRSx1REFBdUQsQ0FBQyxDQUFDO2dCQUM3RyxJQUFJLENBQUMsSUFBSSxFQUFFLENBQUM7WUFDZCxDQUFDO1lBRUQsZ0NBQWdDLENBQUMsSUFBVTtnQkFDekMsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztnQkFDMUIsSUFBSSxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLG9CQUFvQixDQUFDLEVBQUUsd0RBQXdELENBQUMsQ0FBQztnQkFDbEgsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO1lBQ2QsQ0FBQztTQUNGO1FBRUQsMkJBQTJCLENBQUMsSUFBVTtZQUNwQyxNQUFNLEtBQUssR0FBRyxJQUFJLFdBQUssRUFBRSxDQUFDO1lBQzFCLE1BQU0sS0FBSyxHQUFxQztnQkFDOUMsb0RBQW9ELEVBQUU7b0JBQ3BELFNBQVMsRUFBRSxLQUFLO29CQUNoQixPQUFPLEVBQUUsS0FBSztvQkFDZCxNQUFNLEVBQUUsUUFBUTtvQkFDaEIsT0FBTyxFQUFFLFdBQVc7b0JBQ3BCLFFBQVEsRUFBRSxjQUFjO29CQUN4QixZQUFZLEVBQUUsVUFBVTtvQkFDeEIsR0FBRyxFQUFFLEdBQUc7aUJBQ1Q7Z0JBQ0QsdUZBQXVGLEVBQUU7b0JBQ3ZGLFNBQVMsRUFBRSxLQUFLO29CQUNoQixPQUFPLEVBQUUsWUFBWTtvQkFDckIsTUFBTSxFQUFFLFdBQVc7b0JBQ25CLE9BQU8sRUFBRSxFQUFFO29CQUNYLFFBQVEsRUFBRSxrQ0FBa0M7b0JBQzVDLEdBQUcsRUFBRSxHQUFHO29CQUNSLFlBQVksRUFBRSx3QkFBd0I7aUJBQ3ZDO2dCQUNELDhFQUE4RSxFQUFFO29CQUM5RSxTQUFTLEVBQUUsUUFBUTtvQkFDbkIsT0FBTyxFQUFFLFFBQVE7b0JBQ2pCLE1BQU0sRUFBRSxFQUFFO29CQUNWLE9BQU8sRUFBRSxjQUFjO29CQUN2QixRQUFRLEVBQUUsYUFBYTtvQkFDdkIsWUFBWSxFQUFFLGtDQUFrQztvQkFDaEQsR0FBRyxFQUFFLEdBQUc7aUJBQ1Q7Z0JBQ0QsaUZBQWlGLEVBQUU7b0JBQ2pGLE9BQU8sRUFBRSxjQUFjO29CQUN2QixNQUFNLEVBQUUsRUFBRTtvQkFDVixPQUFPLEVBQUUsRUFBRTtvQkFDWCxRQUFRLEVBQUUsY0FBYztvQkFDeEIsWUFBWSxFQUFFLGdEQUFnRDtvQkFDOUQsR0FBRyxFQUFFLEdBQUc7aUJBQ1Q7Z0JBQ0Qsa0NBQWtDLEVBQUU7b0JBQ2xDLFNBQVMsRUFBRSxLQUFLO29CQUNoQixPQUFPLEVBQUUsSUFBSTtvQkFDYixNQUFNLEVBQUUsRUFBRTtvQkFDVixPQUFPLEVBQUUsRUFBRTtvQkFDWCxRQUFRLEVBQUUscUJBQXFCO2lCQUNoQzthQUNGLENBQUM7WUFFRixNQUFNLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUMsRUFBRTtnQkFDL0IsTUFBTSxRQUFRLEdBQUcsS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDO2dCQUM1QixJQUFJLENBQUMsU0FBUyxDQUFDLEtBQUssQ0FBQyxRQUFRLENBQUMsR0FBRyxDQUFDLEVBQUUsUUFBUSxFQUFFLEdBQUcsQ0FBQyxDQUFDO1lBQ3JELENBQUMsQ0FBQyxDQUFDO1lBRUgsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO1FBQ2QsQ0FBQztRQUVELDBCQUEwQixDQUFDLElBQVU7WUFDbkMsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztZQUMxQixNQUFNLFFBQVEsR0FBRyxFQUFFLEdBQUcsRUFBRSxlQUFlLEVBQUUsQ0FBQztZQUMxQyxNQUFNLE1BQU0sR0FBRyxLQUFLLENBQUMsUUFBUSxDQUFDLElBQUkscUJBQVMsQ0FBQyxRQUFRLENBQUMsQ0FBQyxRQUFRLEVBQUUsRUFBRSxHQUFHLENBQUMsQ0FBQztZQUV2RSxJQUFJLENBQUMsU0FBUyxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsTUFBTSxDQUFDLFNBQVMsQ0FBQyxFQUFFLEVBQUUsWUFBWSxFQUFFLENBQUUsQ0FBQyxFQUFFLEVBQUUsV0FBVyxFQUFFLENBQUUsR0FBRyxFQUFFLFFBQVEsQ0FBRSxFQUFDLENBQUUsRUFBQyxDQUFDLENBQUM7WUFDM0csSUFBSSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQyxPQUFPLENBQUMsRUFBRSxFQUFFLFlBQVksRUFBRSxDQUFFLENBQUMsRUFBRSxFQUFFLFdBQVcsRUFBRSxDQUFFLEdBQUcsRUFBRSxRQUFRLENBQUUsRUFBQyxDQUFFLEVBQUMsQ0FBQyxDQUFDO1lBQ3pHLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLEVBQUUsRUFBRSxZQUFZLEVBQUUsQ0FBRSxDQUFDLEVBQUUsRUFBRSxXQUFXLEVBQUUsQ0FBRSxHQUFHLEVBQUUsUUFBUSxDQUFFLEVBQUMsQ0FBRSxFQUFDLENBQUMsQ0FBQztZQUN4RyxJQUFJLENBQUMsU0FBUyxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsTUFBTSxDQUFDLE9BQU8sQ0FBQyxFQUFFLEVBQUUsWUFBWSxFQUFFLENBQUUsQ0FBQyxFQUFFLEVBQUUsV0FBVyxFQUFFLENBQUUsR0FBRyxFQUFFLFFBQVEsQ0FBRSxFQUFDLENBQUUsRUFBQyxDQUFDLENBQUM7WUFDekcsSUFBSSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQyxRQUFRLENBQUMsRUFBRSxFQUFFLFlBQVksRUFBRSxDQUFFLENBQUMsRUFBRSxFQUFFLFdBQVcsRUFBRSxDQUFFLEdBQUcsRUFBRSxRQUFRLENBQUUsRUFBQyxDQUFFLEVBQUMsQ0FBQyxDQUFDO1lBQzFHLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUMsWUFBWSxDQUFDLEVBQUUsRUFBRSxZQUFZLEVBQUUsQ0FBRSxDQUFDLEVBQUUsRUFBRSxXQUFXLEVBQUUsQ0FBRSxHQUFHLEVBQUUsUUFBUSxDQUFFLEVBQUMsQ0FBRSxFQUFDLENBQUMsQ0FBQztZQUM5RyxJQUFJLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxHQUFHLEVBQUUsR0FBRyxDQUFDLENBQUM7WUFFNUIsSUFBSSxDQUFDLElBQUksRUFBRSxDQUFDO1FBQ2QsQ0FBQztRQUVELDBCQUEwQixDQUFDLElBQVU7WUFDbkMsTUFBTSxLQUFLLEdBQUcsSUFBSSxXQUFLLEVBQUUsQ0FBQztZQUMxQixNQUFNLFFBQVEsR0FBRyxFQUFFLEdBQUcsRUFBRSxlQUFlLEVBQUUsQ0FBQztZQUMxQyxNQUFNLE1BQU0sR0FBRyxLQUFLLENBQUMsUUFBUSxDQUFDLElBQUkscUJBQVMsQ0FBQyxRQUFRLENBQUMsQ0FBQyxRQUFRLEVBQUUsQ0FBQyxDQUFDO1lBRWxFLElBQUksQ0FBQyxLQUFLLENBQUMsTUFBTSxDQUFDLEdBQUcsRUFBRSxHQUFHLENBQUMsQ0FBQztZQUU1QiwyQ0FBMkM7WUFDM0MsSUFBSSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQyxRQUFRLENBQUMsRUFBRSxFQUFFLFlBQVksRUFBRSxDQUFFLENBQUMsRUFBRSxFQUFFLFdBQVcsRUFBRSxDQUFFLEdBQUcsRUFBRSxFQUFFLFlBQVksRUFBRSxDQUFFLENBQUMsRUFBRSxFQUFFLFdBQVcsRUFBRSxDQUFFLEdBQUcsRUFBRSxRQUFRLENBQUUsRUFBQyxDQUFFLEVBQUMsQ0FBRSxFQUFDLENBQUUsRUFBQyxDQUFDLENBQUM7WUFDM0osMkNBQTJDO1lBQzNDLElBQUksQ0FBQyxTQUFTLENBQUMsS0FBSyxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUMsWUFBWSxDQUFDLEVBQUUsRUFBRSxZQUFZLEVBQUUsQ0FBRSxDQUFDLEVBQUUsRUFBRSxXQUFXLEVBQUUsQ0FBRSxHQUFHLEVBQUUsRUFBRSxZQUFZLEVBQUUsQ0FBRSxDQUFDLEVBQUUsRUFBRSxXQUFXLEVBQUUsQ0FBRSxHQUFHLEVBQUUsUUFBUSxDQUFFLEVBQUMsQ0FBRSxFQUFDLENBQUUsRUFBQyxDQUFFLEVBQUMsQ0FBQyxDQUFDO1lBRS9KLElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztRQUNkLENBQUM7UUFFRCxxQ0FBcUMsQ0FBQyxJQUFVO1lBQzlDLE1BQU0sS0FBSyxHQUFHLElBQUksV0FBSyxFQUFFLENBQUM7WUFDMUIsTUFBTSxHQUFHLEdBQUcsdUNBQXVDLENBQUM7WUFDcEQsTUFBTSxRQUFRLEdBQWtCO2dCQUM5QixTQUFTLEVBQUUsS0FBSztnQkFDaEIsT0FBTyxFQUFFLEtBQUs7Z0JBQ2QsTUFBTSxFQUFFLEVBQUU7Z0JBQ1YsT0FBTyxFQUFFLGNBQWM7Z0JBQ3ZCLFFBQVEsRUFBRSxNQUFNO2dCQUNoQixZQUFZLEVBQUUsUUFBUTtnQkFDdEIsR0FBRyxFQUFFLEdBQUc7YUFDVCxDQUFDO1lBRUYsSUFBSSxDQUFDLFNBQVMsQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxFQUFFLFFBQVEsRUFBRSxHQUFHLENBQUMsQ0FBQztZQUNuRCxJQUFJLENBQUMsSUFBSSxFQUFFLENBQUM7UUFDZCxDQUFDO0tBQ0Y7SUFFRCxrRkFBa0YsQ0FBQyxJQUFVO1FBQzNGLFFBQVE7UUFDUixNQUFNLE1BQU0sR0FBRyxJQUFJLFdBQUssQ0FBQyxTQUFTLEVBQUUsUUFBUSxFQUFFLEVBQUUsR0FBRyxFQUFFLEVBQUUsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLEVBQUUsWUFBWSxFQUFFLEVBQUMsQ0FBQyxDQUFDO1FBQ3JHLE1BQU0sTUFBTSxHQUFHLElBQUksV0FBSyxDQUFDLFNBQVMsRUFBRSxRQUFRLEVBQUUsRUFBRSxHQUFHLEVBQUUsRUFBRSxPQUFPLEVBQUUsVUFBVSxFQUFFLE1BQU0sRUFBRSxZQUFZLEVBQUUsRUFBQyxDQUFDLENBQUM7UUFFckcsT0FBTztRQUNQLE1BQU0sR0FBRyxHQUFHLE1BQU0sQ0FBQyxTQUFTLENBQUM7WUFDM0IsOEJBQThCO1lBQzlCLE9BQU8sRUFBRSxLQUFLO1lBQ2QsUUFBUSxFQUFFLE9BQU87WUFDakIsWUFBWSxFQUFFLE9BQU87U0FDdEIsQ0FBQyxDQUFDO1FBQ0gsSUFBSSxlQUFTLENBQUMsTUFBTSxFQUFFLFdBQVcsRUFBRSxFQUFFLEtBQUssRUFBRSxHQUFHLEVBQUUsQ0FBQyxDQUFDO1FBRW5ELE9BQU87UUFDUCxJQUFJLENBQUMsU0FBUyxDQUFDLHVCQUFnQixDQUFDLE1BQU0sQ0FBQyxFQUFFO1lBQ3ZDLE9BQU8sRUFBRTtnQkFDUCxTQUFTLEVBQUU7b0JBQ1QsS0FBSyxFQUFFO3dCQUNMLCtCQUErQjt3QkFDL0IsVUFBVSxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUMsTUFBTSxFQUFFLEVBQUUsR0FBRyxFQUFFLGdCQUFnQixFQUFFLEVBQUUsc0NBQXNDLENBQUMsQ0FBQztxQkFBRTtpQkFDbEc7YUFDRjtTQUNGLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxJQUFJLEVBQUUsQ0FBQztJQUNkLENBQUM7Q0FDRixDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgVGVzdCB9IGZyb20gJ25vZGV1bml0JztcbmltcG9ydCB7IEFybkNvbXBvbmVudHMsIENmbk91dHB1dCwgU2NvcGVkQXdzLCBTdGFjayB9IGZyb20gJy4uL2xpYic7XG5pbXBvcnQgeyBJbnRyaW5zaWMgfSBmcm9tICcuLi9saWIvcHJpdmF0ZS9pbnRyaW5zaWMnO1xuaW1wb3J0IHsgdG9DbG91ZEZvcm1hdGlvbiB9IGZyb20gJy4vdXRpbCc7XG5cbmV4cG9ydCA9IHtcbiAgJ2NyZWF0ZSBmcm9tIGNvbXBvbmVudHMgd2l0aCBkZWZhdWx0cycodGVzdDogVGVzdCkge1xuICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG5cbiAgICBjb25zdCBhcm4gPSBzdGFjay5mb3JtYXRBcm4oe1xuICAgICAgc2VydmljZTogJ3NxcycsXG4gICAgICByZXNvdXJjZTogJ215cXVldWVuYW1lJyxcbiAgICB9KTtcblxuICAgIGNvbnN0IHBzZXVkbyA9IG5ldyBTY29wZWRBd3Moc3RhY2spO1xuXG4gICAgdGVzdC5kZWVwRXF1YWwoc3RhY2sucmVzb2x2ZShhcm4pLFxuICAgICAgc3RhY2sucmVzb2x2ZShgYXJuOiR7cHNldWRvLnBhcnRpdGlvbn06c3FzOiR7cHNldWRvLnJlZ2lvbn06JHtwc2V1ZG8uYWNjb3VudElkfTpteXF1ZXVlbmFtZWApKTtcbiAgICB0ZXN0LmRvbmUoKTtcbiAgfSxcblxuICAnY3JlYXRlIGZyb20gY29tcG9uZW50cyB3aXRoIHNwZWNpZmljIHZhbHVlcyBmb3IgdGhlIHZhcmlvdXMgY29tcG9uZW50cycodGVzdDogVGVzdCkge1xuICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG5cbiAgICBjb25zdCBhcm4gPSBzdGFjay5mb3JtYXRBcm4oe1xuICAgICAgc2VydmljZTogJ2R5bmFtb2RiJyxcbiAgICAgIHJlc291cmNlOiAndGFibGUnLFxuICAgICAgYWNjb3VudDogJzEyMzQ1Njc4OTAxMicsXG4gICAgICByZWdpb246ICd1cy1lYXN0LTEnLFxuICAgICAgcGFydGl0aW9uOiAnYXdzLWNuJyxcbiAgICAgIHJlc291cmNlTmFtZTogJ215dGFibGUvc3RyZWFtL2xhYmVsJyxcbiAgICB9KTtcblxuICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUoYXJuKSxcbiAgICAgICdhcm46YXdzLWNuOmR5bmFtb2RiOnVzLWVhc3QtMToxMjM0NTY3ODkwMTI6dGFibGUvbXl0YWJsZS9zdHJlYW0vbGFiZWwnKTtcbiAgICB0ZXN0LmRvbmUoKTtcbiAgfSxcblxuICAnYWxsb3cgZW1wdHkgc3RyaW5nIGluIGNvbXBvbmVudHMnKHRlc3Q6IFRlc3QpIHtcbiAgICBjb25zdCBzdGFjayA9IG5ldyBTdGFjaygpO1xuXG4gICAgY29uc3QgYXJuID0gc3RhY2suZm9ybWF0QXJuKHtcbiAgICAgIHNlcnZpY2U6ICdzMycsXG4gICAgICByZXNvdXJjZTogJ215LWJ1Y2tldCcsXG4gICAgICBhY2NvdW50OiAnJyxcbiAgICAgIHJlZ2lvbjogJycsXG4gICAgICBwYXJ0aXRpb246ICdhd3MtY24nLFxuICAgIH0pO1xuXG4gICAgdGVzdC5kZWVwRXF1YWwoc3RhY2sucmVzb2x2ZShhcm4pLFxuICAgICAgJ2Fybjphd3MtY246czM6OjpteS1idWNrZXQnKTtcblxuICAgIHRlc3QuZG9uZSgpO1xuICB9LFxuXG4gICdyZXNvdXJjZVBhdGhTZXAgY2FuIGJlIHNldCB0byBcIjpcIiBpbnN0ZWFkIG9mIHRoZSBkZWZhdWx0IFwiL1wiJyh0ZXN0OiBUZXN0KSB7XG4gICAgY29uc3Qgc3RhY2sgPSBuZXcgU3RhY2soKTtcblxuICAgIGNvbnN0IGFybiA9IHN0YWNrLmZvcm1hdEFybih7XG4gICAgICBzZXJ2aWNlOiAnY29kZWRlcGxveScsXG4gICAgICByZXNvdXJjZTogJ2FwcGxpY2F0aW9uJyxcbiAgICAgIHNlcDogJzonLFxuICAgICAgcmVzb3VyY2VOYW1lOiAnV29yZFByZXNzX0FwcCcsXG4gICAgfSk7XG5cbiAgICBjb25zdCBwc2V1ZG8gPSBuZXcgU2NvcGVkQXdzKHN0YWNrKTtcblxuICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUoYXJuKSxcbiAgICAgIHN0YWNrLnJlc29sdmUoYGFybjoke3BzZXVkby5wYXJ0aXRpb259OmNvZGVkZXBsb3k6JHtwc2V1ZG8ucmVnaW9ufToke3BzZXVkby5hY2NvdW50SWR9OmFwcGxpY2F0aW9uOldvcmRQcmVzc19BcHBgKSk7XG4gICAgdGVzdC5kb25lKCk7XG4gIH0sXG5cbiAgJ3Jlc291cmNlUGF0aFNlcCBjYW4gYmUgc2V0IHRvIFwiXCIgaW5zdGVhZCBvZiB0aGUgZGVmYXVsdCBcIi9cIicodGVzdDogVGVzdCkge1xuICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG5cbiAgICBjb25zdCBhcm4gPSBzdGFjay5mb3JtYXRBcm4oe1xuICAgICAgc2VydmljZTogJ3NzbScsXG4gICAgICByZXNvdXJjZTogJ3BhcmFtZXRlcicsXG4gICAgICBzZXA6ICcnLFxuICAgICAgcmVzb3VyY2VOYW1lOiAnL3BhcmFtZXRlci1uYW1lJyxcbiAgICB9KTtcblxuICAgIGNvbnN0IHBzZXVkbyA9IG5ldyBTY29wZWRBd3Moc3RhY2spO1xuXG4gICAgdGVzdC5kZWVwRXF1YWwoc3RhY2sucmVzb2x2ZShhcm4pLFxuICAgICAgc3RhY2sucmVzb2x2ZShgYXJuOiR7cHNldWRvLnBhcnRpdGlvbn06c3NtOiR7cHNldWRvLnJlZ2lvbn06JHtwc2V1ZG8uYWNjb3VudElkfTpwYXJhbWV0ZXIvcGFyYW1ldGVyLW5hbWVgKSk7XG4gICAgdGVzdC5kb25lKCk7XG4gIH0sXG5cbiAgJ2ZhaWxzIGlmIHJlc291cmNlUGF0aFNlcCBpcyBuZWl0aGVyIFwiOlwiIG5vciBcIi9cIicodGVzdDogVGVzdCkge1xuICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG5cbiAgICB0ZXN0LnRocm93cygoKSA9PiBzdGFjay5mb3JtYXRBcm4oe1xuICAgICAgc2VydmljZTogJ2ZvbycsXG4gICAgICByZXNvdXJjZTogJ2JhcicsXG4gICAgICBzZXA6ICd4JyB9KSk7XG4gICAgdGVzdC5kb25lKCk7XG4gIH0sXG5cbiAgJ0Fybi5wYXJzZShzKSc6IHtcblxuICAgICdmYWlscyc6IHtcbiAgICAgICdpZiBkb2VzblxcJ3Qgc3RhcnQgd2l0aCBcImFybjpcIicodGVzdDogVGVzdCkge1xuICAgICAgICBjb25zdCBzdGFjayA9IG5ldyBTdGFjaygpO1xuICAgICAgICB0ZXN0LnRocm93cygoKSA9PiBzdGFjay5wYXJzZUFybignYmFybjpmb286eDphOjE6MicpLCAvQVJOcyBtdXN0IHN0YXJ0IHdpdGggXCJhcm46XCI6IGJhcm46Zm9vLyk7XG4gICAgICAgIHRlc3QuZG9uZSgpO1xuICAgICAgfSxcblxuICAgICAgJ2lmIHRoZSBBUk4gZG9lc250IGhhdmUgZW5vdWdoIGNvbXBvbmVudHMnKHRlc3Q6IFRlc3QpIHtcbiAgICAgICAgY29uc3Qgc3RhY2sgPSBuZXcgU3RhY2soKTtcbiAgICAgICAgdGVzdC50aHJvd3MoKCkgPT4gc3RhY2sucGFyc2VBcm4oJ2Fybjppczp0b286c2hvcnQnKSwgL0FSTnMgbXVzdCBoYXZlIGF0IGxlYXN0IDYgY29tcG9uZW50czogYXJuOmlzOnRvbzpzaG9ydC8pO1xuICAgICAgICB0ZXN0LmRvbmUoKTtcbiAgICAgIH0sXG5cbiAgICAgICdpZiBcInNlcnZpY2VcIiBpcyBub3Qgc3BlY2lmaWVkJyh0ZXN0OiBUZXN0KSB7XG4gICAgICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG4gICAgICAgIHRlc3QudGhyb3dzKCgpID0+IHN0YWNrLnBhcnNlQXJuKCdhcm46YXdzOjo0OjU6NicpLCAvVGhlIGBzZXJ2aWNlYCBjb21wb25lbnQgXFwoM3JkIGNvbXBvbmVudFxcKSBpcyByZXF1aXJlZC8pO1xuICAgICAgICB0ZXN0LmRvbmUoKTtcbiAgICAgIH0sXG5cbiAgICAgICdpZiBcInJlc291cmNlXCIgaXMgbm90IHNwZWNpZmllZCcodGVzdDogVGVzdCkge1xuICAgICAgICBjb25zdCBzdGFjayA9IG5ldyBTdGFjaygpO1xuICAgICAgICB0ZXN0LnRocm93cygoKSA9PiBzdGFjay5wYXJzZUFybignYXJuOmF3czpzZXJ2aWNlOjo6JyksIC9UaGUgYHJlc291cmNlYCBjb21wb25lbnQgXFwoNnRoIGNvbXBvbmVudFxcKSBpcyByZXF1aXJlZC8pO1xuICAgICAgICB0ZXN0LmRvbmUoKTtcbiAgICAgIH0sXG4gICAgfSxcblxuICAgICd2YXJpb3VzIHN1Y2Nlc3NmdWwgcGFyc2VzJyh0ZXN0OiBUZXN0KSB7XG4gICAgICBjb25zdCBzdGFjayA9IG5ldyBTdGFjaygpO1xuICAgICAgY29uc3QgdGVzdHM6IHsgW2Fybjogc3RyaW5nXTogQXJuQ29tcG9uZW50cyB9ID0ge1xuICAgICAgICAnYXJuOmF3czphNGI6cmVnaW9uOmFjY291bnRpZDpyZXNvdXJjZXR5cGUvcmVzb3VyY2UnOiB7XG4gICAgICAgICAgcGFydGl0aW9uOiAnYXdzJyxcbiAgICAgICAgICBzZXJ2aWNlOiAnYTRiJyxcbiAgICAgICAgICByZWdpb246ICdyZWdpb24nLFxuICAgICAgICAgIGFjY291bnQ6ICdhY2NvdW50aWQnLFxuICAgICAgICAgIHJlc291cmNlOiAncmVzb3VyY2V0eXBlJyxcbiAgICAgICAgICByZXNvdXJjZU5hbWU6ICdyZXNvdXJjZScsXG4gICAgICAgICAgc2VwOiAnLycsXG4gICAgICAgIH0sXG4gICAgICAgICdhcm46YXdzOmFwaWdhdGV3YXk6dXMtZWFzdC0xOjphMTIzNDU2Nzg5MDEyYmMzZGU0NTY3ODkwMWYyM2E0NTovdGVzdC9teWRlbW9yZXNvdXJjZS8qJzoge1xuICAgICAgICAgIHBhcnRpdGlvbjogJ2F3cycsXG4gICAgICAgICAgc2VydmljZTogJ2FwaWdhdGV3YXknLFxuICAgICAgICAgIHJlZ2lvbjogJ3VzLWVhc3QtMScsXG4gICAgICAgICAgYWNjb3VudDogJycsXG4gICAgICAgICAgcmVzb3VyY2U6ICdhMTIzNDU2Nzg5MDEyYmMzZGU0NTY3ODkwMWYyM2E0NScsXG4gICAgICAgICAgc2VwOiAnOicsXG4gICAgICAgICAgcmVzb3VyY2VOYW1lOiAnL3Rlc3QvbXlkZW1vcmVzb3VyY2UvKicsXG4gICAgICAgIH0sXG4gICAgICAgICdhcm46YXdzLWNuOmNsb3VkOTo6MTIzNDU2Nzg5MDEyOmVudmlyb25tZW50OjgxZTkwMDMxNzM0NzU4NWEwNjAxZTA0YzhkNTJlYUVYJzoge1xuICAgICAgICAgIHBhcnRpdGlvbjogJ2F3cy1jbicsXG4gICAgICAgICAgc2VydmljZTogJ2Nsb3VkOScsXG4gICAgICAgICAgcmVnaW9uOiAnJyxcbiAgICAgICAgICBhY2NvdW50OiAnMTIzNDU2Nzg5MDEyJyxcbiAgICAgICAgICByZXNvdXJjZTogJ2Vudmlyb25tZW50JyxcbiAgICAgICAgICByZXNvdXJjZU5hbWU6ICc4MWU5MDAzMTczNDc1ODVhMDYwMWUwNGM4ZDUyZWFFWCcsXG4gICAgICAgICAgc2VwOiAnOicsXG4gICAgICAgIH0sXG4gICAgICAgICdhcm46OmNvZ25pdG8tc3luYzo6OmlkZW50aXR5cG9vbC91cy1lYXN0LTE6MWExYTFhMWEtZmZmZi0xMTExLTk5OTktMTIzNDU2Nzg6YmxhJzoge1xuICAgICAgICAgIHNlcnZpY2U6ICdjb2duaXRvLXN5bmMnLFxuICAgICAgICAgIHJlZ2lvbjogJycsXG4gICAgICAgICAgYWNjb3VudDogJycsXG4gICAgICAgICAgcmVzb3VyY2U6ICdpZGVudGl0eXBvb2wnLFxuICAgICAgICAgIHJlc291cmNlTmFtZTogJ3VzLWVhc3QtMToxYTFhMWExYS1mZmZmLTExMTEtOTk5OS0xMjM0NTY3ODpibGEnLFxuICAgICAgICAgIHNlcDogJy8nLFxuICAgICAgICB9LFxuICAgICAgICAnYXJuOmF3czpzMzo6Om15X2NvcnBvcmF0ZV9idWNrZXQnOiB7XG4gICAgICAgICAgcGFydGl0aW9uOiAnYXdzJyxcbiAgICAgICAgICBzZXJ2aWNlOiAnczMnLFxuICAgICAgICAgIHJlZ2lvbjogJycsXG4gICAgICAgICAgYWNjb3VudDogJycsXG4gICAgICAgICAgcmVzb3VyY2U6ICdteV9jb3Jwb3JhdGVfYnVja2V0JyxcbiAgICAgICAgfSxcbiAgICAgIH07XG5cbiAgICAgIE9iamVjdC5rZXlzKHRlc3RzKS5mb3JFYWNoKGFybiA9PiB7XG4gICAgICAgIGNvbnN0IGV4cGVjdGVkID0gdGVzdHNbYXJuXTtcbiAgICAgICAgdGVzdC5kZWVwRXF1YWwoc3RhY2sucGFyc2VBcm4oYXJuKSwgZXhwZWN0ZWQsIGFybik7XG4gICAgICB9KTtcblxuICAgICAgdGVzdC5kb25lKCk7XG4gICAgfSxcblxuICAgICdhIFRva2VuIHdpdGggOiBzZXBhcmF0b3InKHRlc3Q6IFRlc3QpIHtcbiAgICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG4gICAgICBjb25zdCB0aGVUb2tlbiA9IHsgUmVmOiAnU29tZVBhcmFtZXRlcicgfTtcbiAgICAgIGNvbnN0IHBhcnNlZCA9IHN0YWNrLnBhcnNlQXJuKG5ldyBJbnRyaW5zaWModGhlVG9rZW4pLnRvU3RyaW5nKCksICc6Jyk7XG5cbiAgICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUocGFyc2VkLnBhcnRpdGlvbiksIHsgJ0ZuOjpTZWxlY3QnOiBbIDEsIHsgJ0ZuOjpTcGxpdCc6IFsgJzonLCB0aGVUb2tlbiBdfSBdfSk7XG4gICAgICB0ZXN0LmRlZXBFcXVhbChzdGFjay5yZXNvbHZlKHBhcnNlZC5zZXJ2aWNlKSwgeyAnRm46OlNlbGVjdCc6IFsgMiwgeyAnRm46OlNwbGl0JzogWyAnOicsIHRoZVRva2VuIF19IF19KTtcbiAgICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUocGFyc2VkLnJlZ2lvbiksIHsgJ0ZuOjpTZWxlY3QnOiBbIDMsIHsgJ0ZuOjpTcGxpdCc6IFsgJzonLCB0aGVUb2tlbiBdfSBdfSk7XG4gICAgICB0ZXN0LmRlZXBFcXVhbChzdGFjay5yZXNvbHZlKHBhcnNlZC5hY2NvdW50KSwgeyAnRm46OlNlbGVjdCc6IFsgNCwgeyAnRm46OlNwbGl0JzogWyAnOicsIHRoZVRva2VuIF19IF19KTtcbiAgICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUocGFyc2VkLnJlc291cmNlKSwgeyAnRm46OlNlbGVjdCc6IFsgNSwgeyAnRm46OlNwbGl0JzogWyAnOicsIHRoZVRva2VuIF19IF19KTtcbiAgICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnJlc29sdmUocGFyc2VkLnJlc291cmNlTmFtZSksIHsgJ0ZuOjpTZWxlY3QnOiBbIDYsIHsgJ0ZuOjpTcGxpdCc6IFsgJzonLCB0aGVUb2tlbiBdfSBdfSk7XG4gICAgICB0ZXN0LmVxdWFsKHBhcnNlZC5zZXAsICc6Jyk7XG5cbiAgICAgIHRlc3QuZG9uZSgpO1xuICAgIH0sXG5cbiAgICAnYSBUb2tlbiB3aXRoIC8gc2VwYXJhdG9yJyh0ZXN0OiBUZXN0KSB7XG4gICAgICBjb25zdCBzdGFjayA9IG5ldyBTdGFjaygpO1xuICAgICAgY29uc3QgdGhlVG9rZW4gPSB7IFJlZjogJ1NvbWVQYXJhbWV0ZXInIH07XG4gICAgICBjb25zdCBwYXJzZWQgPSBzdGFjay5wYXJzZUFybihuZXcgSW50cmluc2ljKHRoZVRva2VuKS50b1N0cmluZygpKTtcblxuICAgICAgdGVzdC5lcXVhbChwYXJzZWQuc2VwLCAnLycpO1xuXG4gICAgICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bWF4LWxpbmUtbGVuZ3RoXG4gICAgICB0ZXN0LmRlZXBFcXVhbChzdGFjay5yZXNvbHZlKHBhcnNlZC5yZXNvdXJjZSksIHsgJ0ZuOjpTZWxlY3QnOiBbIDAsIHsgJ0ZuOjpTcGxpdCc6IFsgJy8nLCB7ICdGbjo6U2VsZWN0JzogWyA1LCB7ICdGbjo6U3BsaXQnOiBbICc6JywgdGhlVG9rZW4gXX0gXX0gXX0gXX0pO1xuICAgICAgLy8gdHNsaW50OmRpc2FibGUtbmV4dC1saW5lOm1heC1saW5lLWxlbmd0aFxuICAgICAgdGVzdC5kZWVwRXF1YWwoc3RhY2sucmVzb2x2ZShwYXJzZWQucmVzb3VyY2VOYW1lKSwgeyAnRm46OlNlbGVjdCc6IFsgMSwgeyAnRm46OlNwbGl0JzogWyAnLycsIHsgJ0ZuOjpTZWxlY3QnOiBbIDUsIHsgJ0ZuOjpTcGxpdCc6IFsgJzonLCB0aGVUb2tlbiBdfSBdfSBdfSBdfSk7XG5cbiAgICAgIHRlc3QuZG9uZSgpO1xuICAgIH0sXG5cbiAgICAncmV0dXJucyBlbXB0eSBzdHJpbmcgQVJOIGNvbXBvbmVudHMnKHRlc3Q6IFRlc3QpIHtcbiAgICAgIGNvbnN0IHN0YWNrID0gbmV3IFN0YWNrKCk7XG4gICAgICBjb25zdCBhcm4gPSAnYXJuOmF3czppYW06OjEyMzQ1Njc4OTAxMjpyb2xlL2FiYzEyMyc7XG4gICAgICBjb25zdCBleHBlY3RlZDogQXJuQ29tcG9uZW50cyA9IHtcbiAgICAgICAgcGFydGl0aW9uOiAnYXdzJyxcbiAgICAgICAgc2VydmljZTogJ2lhbScsXG4gICAgICAgIHJlZ2lvbjogJycsXG4gICAgICAgIGFjY291bnQ6ICcxMjM0NTY3ODkwMTInLFxuICAgICAgICByZXNvdXJjZTogJ3JvbGUnLFxuICAgICAgICByZXNvdXJjZU5hbWU6ICdhYmMxMjMnLFxuICAgICAgICBzZXA6ICcvJyxcbiAgICAgIH07XG5cbiAgICAgIHRlc3QuZGVlcEVxdWFsKHN0YWNrLnBhcnNlQXJuKGFybiksIGV4cGVjdGVkLCBhcm4pO1xuICAgICAgdGVzdC5kb25lKCk7XG4gICAgfSxcbiAgfSxcblxuICAnY2FuIHVzZSBhIGZ1bGx5IHNwZWNpZmllZCBBUk4gZnJvbSBhIGRpZmZlcmVudCBzdGFjayB3aXRob3V0IGluY3VycmluZyBhbiBpbXBvcnQnKHRlc3Q6IFRlc3QpIHtcbiAgICAvLyBHSVZFTlxuICAgIGNvbnN0IHN0YWNrMSA9IG5ldyBTdGFjayh1bmRlZmluZWQsICdTdGFjazEnLCB7IGVudjogeyBhY2NvdW50OiAnMTIzNDU2NzgnLCByZWdpb246ICd1cy10dXJiby01JyB9fSk7XG4gICAgY29uc3Qgc3RhY2syID0gbmV3IFN0YWNrKHVuZGVmaW5lZCwgJ1N0YWNrMicsIHsgZW52OiB7IGFjY291bnQ6ICc4NzY1NDMyMScsIHJlZ2lvbjogJ3VzLXR1cmJvLTEnIH19KTtcblxuICAgIC8vIFdIRU5cbiAgICBjb25zdCBhcm4gPSBzdGFjazEuZm9ybWF0QXJuKHtcbiAgICAgIC8vIE5vIHBhcnRpdGlvbiBzcGVjaWZpZWQgaGVyZVxuICAgICAgc2VydmljZTogJ2JsYScsXG4gICAgICByZXNvdXJjZTogJ3RoaW5nJyxcbiAgICAgIHJlc291cmNlTmFtZTogJ3Rob25nJyxcbiAgICB9KTtcbiAgICBuZXcgQ2ZuT3V0cHV0KHN0YWNrMiwgJ1NvbWVWYWx1ZScsIHsgdmFsdWU6IGFybiB9KTtcblxuICAgIC8vIFRIRU5cbiAgICB0ZXN0LmRlZXBFcXVhbCh0b0Nsb3VkRm9ybWF0aW9uKHN0YWNrMiksIHtcbiAgICAgIE91dHB1dHM6IHtcbiAgICAgICAgU29tZVZhbHVlOiB7XG4gICAgICAgICAgVmFsdWU6IHtcbiAgICAgICAgICAgIC8vIExvb2sgbWEsIG5vIEZuOjpJbXBvcnRWYWx1ZSFcbiAgICAgICAgICAgICdGbjo6Sm9pbic6IFsnJywgWydhcm46JywgeyBSZWY6ICdBV1M6OlBhcnRpdGlvbicgfSwgJzpibGE6dXMtdHVyYm8tNToxMjM0NTY3ODp0aGluZy90aG9uZyddXSB9LFxuICAgICAgICB9LFxuICAgICAgfSxcbiAgICB9KTtcblxuICAgIHRlc3QuZG9uZSgpO1xuICB9LFxufTtcbiJdfQ==