UNPKG

@gammarers/aws-rds-database-auto-running-protection-stack

Version:
189 lines 43 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.ProtectionStateMachine = void 0; const aws_cdk_lib_1 = require("aws-cdk-lib"); const sfn = require("aws-cdk-lib/aws-stepfunctions"); const tasks = require("aws-cdk-lib/aws-stepfunctions-tasks"); class ProtectionStateMachine extends sfn.StateMachine { constructor(scope, id, props) { super(scope, id, { ...props, definitionBody: (() => { // 👇 Get AWS account const account = aws_cdk_lib_1.Stack.of(scope).account; //const region = Stack.of(this).region; const stringMappingDefinition = new sfn.Pass(scope, 'StringMappingDefinition', { result: sfn.Result.fromObject({ SourceType: [ { key: 'CLUSTER', value: 'Cluster' }, { key: 'DB_INSTANCE', value: 'Instance' }, ], }), resultPath: '$.definition.mapping', }); const prepareTopicValue = new sfn.Pass(scope, 'PrepareTopicValue', { resultPath: '$.prepare.topic.values', parameters: { account: sfn.JsonPath.arrayGetItem(sfn.JsonPath.stringSplit(sfn.JsonPath.stringAt('$.event.detail.SourceArn'), ':'), 4), // account region: sfn.JsonPath.arrayGetItem(sfn.JsonPath.stringSplit(sfn.JsonPath.stringAt('$.event.detail.SourceArn'), ':'), 3), // region }, }); // 👇 Generate aws web console link const generateConsoleLink = new sfn.Pass(scope, 'GenerateConsoleLink', { resultPath: '$.Generate.Link', parameters: { Value: sfn.JsonPath.format('https://{}.console.aws.amazon.com/rds/home#database', sfn.JsonPath.stringAt('$.prepare.topic.values.region')), }, }); prepareTopicValue.next(generateConsoleLink); // 👇 Generate topic message const generateTopicMessage = new sfn.Pass(scope, 'GenerateTopicMessage', { resultPath: '$.Generate.Topic', parameters: { Subject: sfn.JsonPath.format('😴 [STOPPED] AWS RDS DB {} Auto Running Protected Notification [{}][{}]', sfn.JsonPath.arrayGetItem(sfn.JsonPath.stringAt('$.definition.mapping.SourceType[?(@.key == $.event.detail.SourceType)].value'), 0), sfn.JsonPath.stringAt('$.prepare.topic.values.account'), sfn.JsonPath.stringAt('$.prepare.topic.values.region')), TextMessage: sfn.JsonPath.format('Account : {}\nRegion : {}\nType : {}\nIdentifier : {}', sfn.JsonPath.stringAt('$.prepare.topic.values.account'), sfn.JsonPath.stringAt('$.prepare.topic.values.region'), sfn.JsonPath.stringAt('$.event.detail.SourceType'), sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier')), SlackJsonMessage: { attachments: [ { color: '#36a64f', pretext: sfn.JsonPath.format('😴 Successfully stopped the automatically running RDS {} {}.', sfn.JsonPath.stringAt('$.event.detail.SourceType'), sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier')), fields: [ { title: 'Account', value: sfn.JsonPath.stringAt('$.prepare.topic.values.account'), short: true, }, { title: 'Region', value: sfn.JsonPath.stringAt('$.prepare.topic.values.region'), short: true, }, { title: 'Type', value: sfn.JsonPath.stringAt('$.event.detail.SourceType'), short: true, }, { title: 'Identifier', value: sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier'), short: true, }, ], }, ], }, }, }); generateConsoleLink.next(generateTopicMessage); // 👇 SNS Topic Publish const publishMessage = new tasks.SnsPublish(scope, 'PublishMessage', { topic: props.notificationTopic, subject: sfn.JsonPath.stringAt('$.Generate.Topic.Subject'), message: sfn.TaskInput.fromObject({ default: sfn.JsonPath.stringAt('$.Generate.Topic.TextMessage'), email: sfn.JsonPath.stringAt('$.Generate.Topic.TextMessage'), lambda: sfn.JsonPath.jsonToString(sfn.JsonPath.objectAt('$.Generate.Topic.SlackJsonMessage')), }), messagePerSubscriptionType: true, resultPath: '$.snsResult', }); generateTopicMessage.next(publishMessage); const succeed = new sfn.Succeed(scope, 'Succeed'); publishMessage.next(succeed); const startingWait = new sfn.Wait(scope, 'StartingWait', { time: sfn.WaitTime.duration(aws_cdk_lib_1.Duration.minutes(1)), }); startingWait.next(stringMappingDefinition); const describeDBInstancesTask = new tasks.CallAwsService(scope, 'DescribeDBInstances', { iamResources: [`arn:aws:rds:*:${account}:db:*`], service: 'rds', action: 'describeDBInstances', parameters: { DbInstanceIdentifier: sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier'), }, resultPath: '$.result.describe', resultSelector: { status: sfn.JsonPath.stringAt('$.DbInstances[0].DbInstanceStatus'), identifier: sfn.JsonPath.stringAt('$.DbInstances[0].DbInstanceIdentifier'), tags: sfn.JsonPath.stringAt('$.DbInstances[0].TagList'), }, }); const stopDBInstanceTask = new tasks.CallAwsService(scope, 'StopDBInstance', { iamResources: [`arn:aws:rds:*:${account}:db:*`], service: 'rds', action: 'stopDBInstance', parameters: { DbInstanceIdentifier: sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier'), }, resultPath: '$.result.stop', }); const describeDBClustersTask = new tasks.CallAwsService(scope, 'DescribeDBClusters', { iamResources: [`arn:aws:rds:*:${account}:cluster:*`], service: 'rds', action: 'describeDBClusters', parameters: { DbClusterIdentifier: sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier'), }, resultPath: '$.result.describe', resultSelector: { status: sfn.JsonPath.stringAt('$.DbClusters[0].Status'), identifier: sfn.JsonPath.stringAt('$.DbClusters[0].DbClusterIdentifier'), tags: sfn.JsonPath.stringAt('$.DbClusters[0].TagList'), }, }); const stopDBClusterTask = new tasks.CallAwsService(scope, 'StopDBCluster', { iamResources: [`arn:aws:rds:*:${account}:cluster:*`], service: 'rds', action: 'stopDBCluster', parameters: { DbClusterIdentifier: sfn.JsonPath.stringAt('$.event.detail.SourceIdentifier'), }, resultPath: '$.result.stop', }); const describeTypeChoice = new sfn.Choice(scope, 'DescribeTypeChoice') .when(sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Instance Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'DB_INSTANCE'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0154')), describeDBInstancesTask) .when(sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Cluster Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'CLUSTER'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0153')), describeDBClustersTask) .otherwise(new sfn.Fail(scope, 'UnknownType')); stringMappingDefinition.next(describeTypeChoice); const statusChangeWait = new sfn.Wait(scope, 'StatusChangeWait', { time: sfn.WaitTime.duration(aws_cdk_lib_1.Duration.minutes(5)), }); statusChangeWait.next(describeTypeChoice); stopDBInstanceTask.next(statusChangeWait); stopDBClusterTask.next(statusChangeWait); // 👇 Status Choice const statusChoice = new sfn.Choice(scope, 'StatusChoice') // db instance stop on status.available .when(sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Instance Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'DB_INSTANCE'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0154'), sfn.Condition.stringEquals('$.result.describe.status', 'available')), stopDBInstanceTask) // db cluster stop on status.available .when(sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Cluster Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'CLUSTER'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0153'), sfn.Condition.stringEquals('$.result.describe.status', 'available')), stopDBClusterTask) .when(sfn.Condition.and(sfn.Condition.or(sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Instance Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'DB_INSTANCE'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0154')), sfn.Condition.and(sfn.Condition.stringEquals('$.event.detail-type', 'RDS DB Cluster Event'), sfn.Condition.stringEquals('$.event.detail.SourceType', 'CLUSTER'), sfn.Condition.stringEquals('$.event.detail.EventID', 'RDS-EVENT-0153'))), sfn.Condition.stringEquals('$.result.describe.status', 'stopped')), prepareTopicValue) .when(sfn.Condition.or(sfn.Condition.stringEquals('$.result.describe.status', 'starting'), sfn.Condition.stringEquals('$.result.describe.status', 'configuring-enhanced-monitoring'), sfn.Condition.stringEquals('$.result.describe.status', 'backing-up'), sfn.Condition.stringEquals('$.result.describe.status', 'modifying'), sfn.Condition.stringEquals('$.result.describe.status', 'stopping')), statusChangeWait) .otherwise(new sfn.Fail(scope, 'StatusFail', { cause: 'db instance or cluster status fail.', })); // 👇 Tag Match const tagMatchChoice = new sfn.Choice(scope, 'ExistTagChoide') .when(sfn.Condition.isPresent('$.result.describe.tags'), new sfn.Pass(scope, 'ContainTagVlue', { resultPath: '$.check.tag', parameters: { isContain: sfn.JsonPath.arrayContains(sfn.JsonPath.stringAt('$.params.tagValues'), sfn.JsonPath.arrayGetItem(sfn.JsonPath.stringAt('$.result.describe.tags[?(@.Key == $.params.tagKey)].Value'), 0)), }, }).next(new sfn.Choice(scope, 'FilterTagChoise') .when(sfn.Condition.booleanEquals('$.check.tag.isContain', true), statusChoice) .otherwise(new sfn.Pass(scope, 'NoTagMatch', { comment: 'no tag match', })))) .otherwise(new sfn.Pass(scope, 'NoTagsFound', { comment: 'no tags found', })); // 👇 describe next tag found & match describeDBInstancesTask.next(tagMatchChoice); describeDBClustersTask.next(tagMatchChoice); return sfn.DefinitionBody.fromChainable(startingWait); })(), }); } } exports.ProtectionStateMachine = ProtectionStateMachine; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicHJvdGVjdGlvbi1zdGF0ZS1tYWNoaW5lLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL3Jlc291cmNlcy9wcm90ZWN0aW9uLXN0YXRlLW1hY2hpbmUudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7O0FBQUEsNkNBQThDO0FBRTlDLHFEQUFxRDtBQUNyRCw2REFBNkQ7QUFPN0QsTUFBYSxzQkFBdUIsU0FBUSxHQUFHLENBQUMsWUFBWTtJQUMxRCxZQUFZLEtBQWdCLEVBQUUsRUFBVSxFQUFFLEtBQWtDO1FBQzFFLEtBQUssQ0FBQyxLQUFLLEVBQUUsRUFBRSxFQUFFO1lBQ2YsR0FBRyxLQUFLO1lBQ1IsY0FBYyxFQUFFLENBQUMsR0FBRyxFQUFFO2dCQUVwQixxQkFBcUI7Z0JBQ3JCLE1BQU0sT0FBTyxHQUFHLG1CQUFLLENBQUMsRUFBRSxDQUFDLEtBQUssQ0FBQyxDQUFDLE9BQU8sQ0FBQztnQkFDeEMsdUNBQXVDO2dCQUV2QyxNQUFNLHVCQUF1QixHQUFHLElBQUksR0FBRyxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUseUJBQXlCLEVBQUU7b0JBQzdFLE1BQU0sRUFBRSxHQUFHLENBQUMsTUFBTSxDQUFDLFVBQVUsQ0FBQzt3QkFDNUIsVUFBVSxFQUFFOzRCQUNWLEVBQUUsR0FBRyxFQUFFLFNBQVMsRUFBRSxLQUFLLEVBQUUsU0FBUyxFQUFFOzRCQUNwQyxFQUFFLEdBQUcsRUFBRSxhQUFhLEVBQUUsS0FBSyxFQUFFLFVBQVUsRUFBRTt5QkFDMUM7cUJBQ0YsQ0FBQztvQkFDRixVQUFVLEVBQUUsc0JBQXNCO2lCQUNuQyxDQUFDLENBQUM7Z0JBRUgsTUFBTSxpQkFBaUIsR0FBRyxJQUFJLEdBQUcsQ0FBQyxJQUFJLENBQUMsS0FBSyxFQUFFLG1CQUFtQixFQUFFO29CQUNqRSxVQUFVLEVBQUUsd0JBQXdCO29CQUNwQyxVQUFVLEVBQUU7d0JBQ1YsT0FBTyxFQUFFLEdBQUcsQ0FBQyxRQUFRLENBQUMsWUFBWSxDQUFDLEdB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LEVBQUU7U0FDTCxDQUFDLENBQUM7SUFDTCxDQUFDO0NBQ0Y7QUFqU0Qsd0RBaVNDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgRHVyYXRpb24sIFN0YWNrIH0gZnJvbSAnYXdzLWNkay1saWInO1xuaW1wb3J0ICogYXMgc25zIGZyb20gJ2F3cy1jZGstbGliL2F3cy1zbnMnO1xuaW1wb3J0ICogYXMgc2ZuIGZyb20gJ2F3cy1jZGstbGliL2F3cy1zdGVwZnVuY3Rpb25zJztcbmltcG9ydCAqIGFzIHRhc2tzIGZyb20gJ2F3cy1jZGstbGliL2F3cy1zdGVwZnVuY3Rpb25zLXRhc2tzJztcbmltcG9ydCB7IENvbnN0cnVjdCB9IGZyb20gJ2NvbnN0cnVjdHMnO1xuXG5leHBvcnQgaW50ZXJmYWNlIFByb3RlY3Rpb25TdGF0ZU1hY2hpbmVQcm9wcyBleHRlbmRzIHNmbi5TdGF0ZU1hY2hpbmVQcm9wcyB7XG4gIG5vdGlmaWNhdGlvblRvcGljOiBzbnMuSVRvcGljO1xufVxuXG5leHBvcnQgY2xhc3MgUHJvdGVjdGlvblN0YXRlTWFjaGluZSBleHRlbmRzIHNmbi5TdGF0ZU1hY2hpbmUge1xuICBjb25zdHJ1Y3RvcihzY29wZTogQ29uc3RydWN0LCBpZDogc3RyaW5nLCBwcm9wczogUHJvdGVjdGlvblN0YXRlTWFjaGluZVByb3BzKSB7XG4gICAgc3VwZXIoc2NvcGUsIGlkLCB7XG4gICAgICAuLi5wcm9wcyxcbiAgICAgIGRlZmluaXRpb25Cb2R5OiAoKCkgPT4ge1xuXG4gICAgICAgIC8vIPCfkYcgR2V0IEFXUyBhY2NvdW50XG4gICAgICAgIGNvbnN0IGFjY291bnQgPSBTdGFjay5vZihzY29wZSkuYWNjb3VudDtcbiAgICAgICAgLy9jb25zdCByZWdpb24gPSBTdGFjay5vZih0aGlzKS5yZWdpb247XG5cbiAgICAgICAgY29uc3Qgc3RyaW5nTWFwcGluZ0RlZmluaXRpb24gPSBuZXcgc2ZuLlBhc3Moc2NvcGUsICdTdHJpbmdNYXBwaW5nRGVmaW5pdGlvbicsIHtcbiAgICAgICAgICByZXN1bHQ6IHNmbi5SZXN1bHQuZnJvbU9iamVjdCh7XG4gICAgICAgICAgICBTb3VyY2VUeXBlOiBbXG4gICAgICAgICAgICAgIHsga2V5OiAnQ0xVU1RFUicsIHZhbHVlOiAnQ2x1c3RlcicgfSxcbiAgICAgICAgICAgICAgeyBrZXk6ICdEQl9JTlNUQU5DRScsIHZhbHVlOiAnSW5zdGFuY2UnIH0sXG4gICAgICAgICAgICBdLFxuICAgICAgICAgIH0pLFxuICAgICAgICAgIHJlc3VsdFBhdGg6ICckLmRlZmluaXRpb24ubWFwcGluZycsXG4gICAgICAgIH0pO1xuXG4gICAgICAgIGNvbnN0IHByZXBhcmVUb3BpY1ZhbHVlID0gbmV3IHNmbi5QYXNzKHNjb3BlLCAnUHJlcGFyZVRvcGljVmFsdWUnLCB7XG4gICAgICAgICAgcmVzdWx0UGF0aDogJyQucHJlcGFyZS50b3BpYy52YWx1ZXMnLFxuICAgICAgICAgIHBhcmFtZXRlcnM6IHtcbiAgICAgICAgICAgIGFjY291bnQ6IHNmbi5Kc29uUGF0aC5hcnJheUdldEl0ZW0oc2ZuLkpzb25QYXRoLnN0cmluZ1NwbGl0KHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5ldmVudC5kZXRhaWwuU291cmNlQXJuJyksICc6JyksIDQpLCAvLyBhY2NvdW50XG4gICAgICAgICAgICByZWdpb246IHNmbi5Kc29uUGF0aC5hcnJheUdldEl0ZW0oc2ZuLkpzb25QYXRoLnN0cmluZ1NwbGl0KHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5ldmVudC5kZXRhaWwuU291cmNlQXJuJyksICc6JyksIDMpLCAvLyByZWdpb25cbiAgICAgICAgICB9LFxuICAgICAgICB9KTtcblxuICAgICAgICAvLyDwn5GHIEdlbmVyYXRlIGF3cyB3ZWIgY29uc29sZSBsaW5rXG4gICAgICAgIGNvbnN0IGdlbmVyYXRlQ29uc29sZUxpbmsgPSBuZXcgc2ZuLlBhc3Moc2NvcGUsICdHZW5lcmF0ZUNvbnNvbGVMaW5rJywge1xuICAgICAgICAgIHJlc3VsdFBhdGg6ICckLkdlbmVyYXRlLkxpbmsnLFxuICAgICAgICAgIHBhcmFtZXRlcnM6IHtcbiAgICAgICAgICAgIFZhbHVlOiBzZm4uSnNvblBhdGguZm9ybWF0KCdodHRwczovL3t9LmNvbnNvbGUuYXdzLmFtYXpvbi5jb20vcmRzL2hvbWUjZGF0YWJhc2UnLFxuICAgICAgICAgICAgICBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQucHJlcGFyZS50b3BpYy52YWx1ZXMucmVnaW9uJyksXG4gICAgICAgICAgICApLFxuICAgICAgICAgIH0sXG4gICAgICAgIH0pO1xuICAgICAgICBwcmVwYXJlVG9waWNWYWx1ZS5uZXh0KGdlbmVyYXRlQ29uc29sZUxpbmspO1xuXG4gICAgICAgIC8vIPCfkYcgR2VuZXJhdGUgdG9waWMgbWVzc2FnZVxuICAgICAgICBjb25zdCBnZW5lcmF0ZVRvcGljTWVzc2FnZSA9IG5ldyBzZm4uUGFzcyhzY29wZSwgJ0dlbmVyYXRlVG9waWNNZXNzYWdlJywge1xuICAgICAgICAgIHJlc3VsdFBhdGg6ICckLkdlbmVyYXRlLlRvcGljJyxcbiAgICAgICAgICBwYXJhbWV0ZXJzOiB7XG4gICAgICAgICAgICBTdWJqZWN0OiBzZm4uSnNvblBhdGguZm9ybWF0KCfwn5i0IFtTVE9QUEVEXSBBV1MgUkRTIERCIHt9IEF1dG8gUnVubmluZyBQcm90ZWN0ZWQgTm90aWZpY2F0aW9uIFt7fV1be31dJyxcbiAgICAgICAgICAgICAgc2ZuLkpzb25QYXRoLmFycmF5R2V0SXRlbShzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQuZGVmaW5pdGlvbi5tYXBwaW5nLlNvdXJjZVR5cGVbPyhALmtleSA9PSAkLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlKV0udmFsdWUnKSwgMCksXG4gICAgICAgICAgICAgIHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5wcmVwYXJlLnRvcGljLnZhbHVlcy5hY2NvdW50JyksXG4gICAgICAgICAgICAgIHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5wcmVwYXJlLnRvcGljLnZhbHVlcy5yZWdpb24nKSxcbiAgICAgICAgICAgICksXG4gICAgICAgICAgICBUZXh0TWVzc2FnZTogc2ZuLkpzb25QYXRoLmZvcm1hdCgnQWNjb3VudCA6IHt9XFxuUmVnaW9uIDoge31cXG5UeXBlIDoge31cXG5JZGVudGlmaWVyIDoge30nLFxuICAgICAgICAgICAgICBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQucHJlcGFyZS50b3BpYy52YWx1ZXMuYWNjb3VudCcpLFxuICAgICAgICAgICAgICBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQucHJlcGFyZS50b3BpYy52YWx1ZXMucmVnaW9uJyksXG4gICAgICAgICAgICAgIHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5ldmVudC5kZXRhaWwuU291cmNlVHlwZScpLFxuICAgICAgICAgICAgICBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQuZXZlbnQuZGV0YWlsLlNvdXJjZUlkZW50aWZpZXInKSxcbiAgICAgICAgICAgICksXG4gICAgICAgICAgICBTbGFja0pzb25NZXNzYWdlOiB7XG4gICAgICAgICAgICAgIGF0dGFjaG1lbnRzOiBbXG4gICAgICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgICAgY29sb3I6ICcjMzZhNjRmJyxcbiAgICAgICAgICAgICAgICAgIHByZXRleHQ6IHNmbi5Kc29uUGF0aC5mb3JtYXQoJ/CfmLQgU3VjY2Vzc2Z1bGx5IHN0b3BwZWQgdGhlIGF1dG9tYXRpY2FsbHkgcnVubmluZyBSRFMge30ge30uJyxcbiAgICAgICAgICAgICAgICAgICAgc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlJyksXG4gICAgICAgICAgICAgICAgICAgIHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5ldmVudC5kZXRhaWwuU291cmNlSWRlbnRpZmllcicpLFxuICAgICAgICAgICAgICAgICAgKSxcbiAgICAgICAgICAgICAgICAgIGZpZWxkczogW1xuICAgICAgICAgICAgICAgICAgICB7XG4gICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdBY2NvdW50JyxcbiAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLnByZXBhcmUudG9waWMudmFsdWVzLmFjY291bnQnKSxcbiAgICAgICAgICAgICAgICAgICAgICBzaG9ydDogdHJ1ZSxcbiAgICAgICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgICAgICAgICAge1xuICAgICAgICAgICAgICAgICAgICAgIHRpdGxlOiAnUmVnaW9uJyxcbiAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLnByZXBhcmUudG9waWMudmFsdWVzLnJlZ2lvbicpLFxuICAgICAgICAgICAgICAgICAgICAgIHNob3J0OiB0cnVlLFxuICAgICAgICAgICAgICAgICAgICB9LFxuICAgICAgICAgICAgICAgICAgICB7XG4gICAgICAgICAgICAgICAgICAgICAgdGl0bGU6ICdUeXBlJyxcbiAgICAgICAgICAgICAgICAgICAgICB2YWx1ZTogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlJyksXG4gICAgICAgICAgICAgICAgICAgICAgc2hvcnQ6IHRydWUsXG4gICAgICAgICAgICAgICAgICAgIH0sXG4gICAgICAgICAgICAgICAgICAgIHtcbiAgICAgICAgICAgICAgICAgICAgICB0aXRsZTogJ0lkZW50aWZpZXInLFxuICAgICAgICAgICAgICAgICAgICAgIHZhbHVlOiBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQuZXZlbnQuZGV0YWlsLlNvdXJjZUlkZW50aWZpZXInKSxcbiAgICAgICAgICAgICAgICAgICAgICBzaG9ydDogdHJ1ZSxcbiAgICAgICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgICAgICAgIF0sXG4gICAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgICAgXSxcbiAgICAgICAgICAgIH0sXG4gICAgICAgICAgfSxcbiAgICAgICAgfSk7XG4gICAgICAgIGdlbmVyYXRlQ29uc29sZUxpbmsubmV4dChnZW5lcmF0ZVRvcGljTWVzc2FnZSk7XG5cbiAgICAgICAgLy8g8J+RhyBTTlMgVG9waWMgUHVibGlzaFxuICAgICAgICBjb25zdCBwdWJsaXNoTWVzc2FnZSA9IG5ldyB0YXNrcy5TbnNQdWJsaXNoKHNjb3BlLCAnUHVibGlzaE1lc3NhZ2UnLCB7XG4gICAgICAgICAgdG9waWM6IHByb3BzLm5vdGlmaWNhdGlvblRvcGljLFxuICAgICAgICAgIHN1YmplY3Q6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5HZW5lcmF0ZS5Ub3BpYy5TdWJqZWN0JyksXG4gICAgICAgICAgbWVzc2FnZTogc2ZuLlRhc2tJbnB1dC5mcm9tT2JqZWN0KHtcbiAgICAgICAgICAgIGRlZmF1bHQ6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5HZW5lcmF0ZS5Ub3BpYy5UZXh0TWVzc2FnZScpLFxuICAgICAgICAgICAgZW1haWw6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5HZW5lcmF0ZS5Ub3BpYy5UZXh0TWVzc2FnZScpLFxuICAgICAgICAgICAgbGFtYmRhOiBzZm4uSnNvblBhdGguanNvblRvU3RyaW5nKHNmbi5Kc29uUGF0aC5vYmplY3RBdCgnJC5HZW5lcmF0ZS5Ub3BpYy5TbGFja0pzb25NZXNzYWdlJykpLFxuICAgICAgICAgIH0pLFxuICAgICAgICAgIG1lc3NhZ2VQZXJTdWJzY3JpcHRpb25UeXBlOiB0cnVlLFxuICAgICAgICAgIHJlc3VsdFBhdGg6ICckLnNuc1Jlc3VsdCcsXG4gICAgICAgIH0pO1xuICAgICAgICBnZW5lcmF0ZVRvcGljTWVzc2FnZS5uZXh0KHB1Ymxpc2hNZXNzYWdlKTtcblxuICAgICAgICBjb25zdCBzdWNjZWVkID0gbmV3IHNmbi5TdWNjZWVkKHNjb3BlLCAnU3VjY2VlZCcpO1xuXG4gICAgICAgIHB1Ymxpc2hNZXNzYWdlLm5leHQoc3VjY2VlZCk7XG5cbiAgICAgICAgY29uc3Qgc3RhcnRpbmdXYWl0ID0gbmV3IHNmbi5XYWl0KHNjb3BlLCAnU3RhcnRpbmdXYWl0Jywge1xuICAgICAgICAgIHRpbWU6IHNmbi5XYWl0VGltZS5kdXJhdGlvbihEdXJhdGlvbi5taW51dGVzKDEpKSxcbiAgICAgICAgfSk7XG5cbiAgICAgICAgc3RhcnRpbmdXYWl0Lm5leHQoc3RyaW5nTWFwcGluZ0RlZmluaXRpb24pO1xuXG4gICAgICAgIGNvbnN0IGRlc2NyaWJlREJJbnN0YW5jZXNUYXNrID0gbmV3IHRhc2tzLkNhbGxBd3NTZXJ2aWNlKHNjb3BlLCAnRGVzY3JpYmVEQkluc3RhbmNlcycsIHtcbiAgICAgICAgICBpYW1SZXNvdXJjZXM6IFtgYXJuOmF3czpyZHM6Kjoke2FjY291bnR9OmRiOipgXSxcbiAgICAgICAgICBzZXJ2aWNlOiAncmRzJyxcbiAgICAgICAgICBhY3Rpb246ICdkZXNjcmliZURCSW5zdGFuY2VzJyxcbiAgICAgICAgICBwYXJhbWV0ZXJzOiB7XG4gICAgICAgICAgICBEYkluc3RhbmNlSWRlbnRpZmllcjogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLmV2ZW50LmRldGFpbC5Tb3VyY2VJZGVudGlmaWVyJyksXG4gICAgICAgICAgfSxcbiAgICAgICAgICByZXN1bHRQYXRoOiAnJC5yZXN1bHQuZGVzY3JpYmUnLFxuICAgICAgICAgIHJlc3VsdFNlbGVjdG9yOiB7XG4gICAgICAgICAgICBzdGF0dXM6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5EYkluc3RhbmNlc1swXS5EYkluc3RhbmNlU3RhdHVzJyksXG4gICAgICAgICAgICBpZGVudGlmaWVyOiBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQuRGJJbnN0YW5jZXNbMF0uRGJJbnN0YW5jZUlkZW50aWZpZXInKSxcbiAgICAgICAgICAgIHRhZ3M6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5EYkluc3RhbmNlc1swXS5UYWdMaXN0JyksXG4gICAgICAgICAgfSxcbiAgICAgICAgfSk7XG5cbiAgICAgICAgY29uc3Qgc3RvcERCSW5zdGFuY2VUYXNrID0gbmV3IHRhc2tzLkNhbGxBd3NTZXJ2aWNlKHNjb3BlLCAnU3RvcERCSW5zdGFuY2UnLCB7XG4gICAgICAgICAgaWFtUmVzb3VyY2VzOiBbYGFybjphd3M6cmRzOio6JHthY2NvdW50fTpkYjoqYF0sXG4gICAgICAgICAgc2VydmljZTogJ3JkcycsXG4gICAgICAgICAgYWN0aW9uOiAnc3RvcERCSW5zdGFuY2UnLFxuICAgICAgICAgIHBhcmFtZXRlcnM6IHtcbiAgICAgICAgICAgIERiSW5zdGFuY2VJZGVudGlmaWVyOiBzZm4uSnNvblBhdGguc3RyaW5nQXQoJyQuZXZlbnQuZGV0YWlsLlNvdXJjZUlkZW50aWZpZXInKSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHJlc3VsdFBhdGg6ICckLnJlc3VsdC5zdG9wJyxcbiAgICAgICAgfSk7XG5cbiAgICAgICAgY29uc3QgZGVzY3JpYmVEQkNsdXN0ZXJzVGFzayA9IG5ldyB0YXNrcy5DYWxsQXdzU2VydmljZShzY29wZSwgJ0Rlc2NyaWJlREJDbHVzdGVycycsIHtcbiAgICAgICAgICBpYW1SZXNvdXJjZXM6IFtgYXJuOmF3czpyZHM6Kjoke2FjY291bnR9OmNsdXN0ZXI6KmBdLFxuICAgICAgICAgIHNlcnZpY2U6ICdyZHMnLFxuICAgICAgICAgIGFjdGlvbjogJ2Rlc2NyaWJlREJDbHVzdGVycycsXG4gICAgICAgICAgcGFyYW1ldGVyczoge1xuICAgICAgICAgICAgRGJDbHVzdGVySWRlbnRpZmllcjogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLmV2ZW50LmRldGFpbC5Tb3VyY2VJZGVudGlmaWVyJyksXG4gICAgICAgICAgfSxcbiAgICAgICAgICByZXN1bHRQYXRoOiAnJC5yZXN1bHQuZGVzY3JpYmUnLFxuICAgICAgICAgIHJlc3VsdFNlbGVjdG9yOiB7XG4gICAgICAgICAgICBzdGF0dXM6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5EYkNsdXN0ZXJzWzBdLlN0YXR1cycpLFxuICAgICAgICAgICAgaWRlbnRpZmllcjogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLkRiQ2x1c3RlcnNbMF0uRGJDbHVzdGVySWRlbnRpZmllcicpLFxuICAgICAgICAgICAgdGFnczogc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLkRiQ2x1c3RlcnNbMF0uVGFnTGlzdCcpLFxuICAgICAgICAgIH0sXG4gICAgICAgIH0pO1xuXG4gICAgICAgIGNvbnN0IHN0b3BEQkNsdXN0ZXJUYXNrID0gbmV3IHRhc2tzLkNhbGxBd3NTZXJ2aWNlKHNjb3BlLCAnU3RvcERCQ2x1c3RlcicsIHtcbiAgICAgICAgICBpYW1SZXNvdXJjZXM6IFtgYXJuOmF3czpyZHM6Kjoke2FjY291bnR9OmNsdXN0ZXI6KmBdLFxuICAgICAgICAgIHNlcnZpY2U6ICdyZHMnLFxuICAgICAgICAgIGFjdGlvbjogJ3N0b3BEQkNsdXN0ZXInLFxuICAgICAgICAgIHBhcmFtZXRlcnM6IHtcbiAgICAgICAgICAgIERiQ2x1c3RlcklkZW50aWZpZXI6IHNmbi5Kc29uUGF0aC5zdHJpbmdBdCgnJC5ldmVudC5kZXRhaWwuU291cmNlSWRlbnRpZmllcicpLFxuICAgICAgICAgIH0sXG4gICAgICAgICAgcmVzdWx0UGF0aDogJyQucmVzdWx0LnN0b3AnLFxuICAgICAgICB9KTtcblxuICAgICAgICBjb25zdCBkZXNjcmliZVR5cGVDaG9pY2UgPSBuZXcgc2ZuLkNob2ljZShzY29wZSwgJ0Rlc2NyaWJlVHlwZUNob2ljZScpXG4gICAgICAgICAgLndoZW4oXG4gICAgICAgICAgICBzZm4uQ29uZGl0aW9uLmFuZChcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLXR5cGUnLCAnUkRTIERCIEluc3RhbmNlIEV2ZW50JyksXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlJywgJ0RCX0lOU1RBTkNFJyksXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC5FdmVudElEJywgJ1JEUy1FVkVOVC0wMTU0JyksXG4gICAgICAgICAgICApLFxuICAgICAgICAgICAgZGVzY3JpYmVEQkluc3RhbmNlc1Rhc2ssXG4gICAgICAgICAgKVxuICAgICAgICAgIC53aGVuKFxuICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5hbmQoXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC10eXBlJywgJ1JEUyBEQiBDbHVzdGVyIEV2ZW50JyksXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlJywgJ0NMVVNURVInKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLkV2ZW50SUQnLCAnUkRTLUVWRU5ULTAxNTMnKSxcbiAgICAgICAgICAgICksXG4gICAgICAgICAgICBkZXNjcmliZURCQ2x1c3RlcnNUYXNrLFxuICAgICAgICAgIClcbiAgICAgICAgICAub3RoZXJ3aXNlKG5ldyBzZm4uRmFpbChzY29wZSwgJ1Vua25vd25UeXBlJykpO1xuXG4gICAgICAgIHN0cmluZ01hcHBpbmdEZWZpbml0aW9uLm5leHQoZGVzY3JpYmVUeXBlQ2hvaWNlKTtcblxuICAgICAgICBjb25zdCBzdGF0dXNDaGFuZ2VXYWl0ID0gbmV3IHNmbi5XYWl0KHNjb3BlLCAnU3RhdHVzQ2hhbmdlV2FpdCcsIHtcbiAgICAgICAgICB0aW1lOiBzZm4uV2FpdFRpbWUuZHVyYXRpb24oRHVyYXRpb24ubWludXRlcyg1KSksXG4gICAgICAgIH0pO1xuXG4gICAgICAgIHN0YXR1c0NoYW5nZVdhaXQubmV4dChkZXNjcmliZVR5cGVDaG9pY2UpO1xuXG4gICAgICAgIHN0b3BEQkluc3RhbmNlVGFzay5uZXh0KHN0YXR1c0NoYW5nZVdhaXQpO1xuXG4gICAgICAgIHN0b3BEQkNsdXN0ZXJUYXNrLm5leHQoc3RhdHVzQ2hhbmdlV2FpdCk7XG5cbiAgICAgICAgLy8g8J+RhyBTdGF0dXMgQ2hvaWNlXG4gICAgICAgIGNvbnN0IHN0YXR1c0Nob2ljZSA9IG5ldyBzZm4uQ2hvaWNlKHNjb3BlLCAnU3RhdHVzQ2hvaWNlJylcbiAgICAgICAgICAvLyBkYiBpbnN0YW5jZSBzdG9wIG9uIHN0YXR1cy5hdmFpbGFibGVcbiAgICAgICAgICAud2hlbihcbiAgICAgICAgICAgIHNmbi5Db25kaXRpb24uYW5kKFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5ldmVudC5kZXRhaWwtdHlwZScsICdSRFMgREIgSW5zdGFuY2UgRXZlbnQnKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLlNvdXJjZVR5cGUnLCAnREJfSU5TVEFOQ0UnKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLkV2ZW50SUQnLCAnUkRTLUVWRU5ULTAxNTQnKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQucmVzdWx0LmRlc2NyaWJlLnN0YXR1cycsICdhdmFpbGFibGUnKSxcbiAgICAgICAgICAgICksXG4gICAgICAgICAgICBzdG9wREJJbnN0YW5jZVRhc2ssXG4gICAgICAgICAgKVxuICAgICAgICAgIC8vIGRiIGNsdXN0ZXIgc3RvcCBvbiBzdGF0dXMuYXZhaWxhYmxlXG4gICAgICAgICAgLndoZW4oXG4gICAgICAgICAgICBzZm4uQ29uZGl0aW9uLmFuZChcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLXR5cGUnLCAnUkRTIERCIENsdXN0ZXIgRXZlbnQnKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLlNvdXJjZVR5cGUnLCAnQ0xVU1RFUicpLFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5ldmVudC5kZXRhaWwuRXZlbnRJRCcsICdSRFMtRVZFTlQtMDE1MycpLFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5yZXN1bHQuZGVzY3JpYmUuc3RhdHVzJywgJ2F2YWlsYWJsZScpLFxuICAgICAgICAgICAgKSxcbiAgICAgICAgICAgIHN0b3BEQkNsdXN0ZXJUYXNrLFxuICAgICAgICAgIClcbiAgICAgICAgICAud2hlbihcbiAgICAgICAgICAgIHNmbi5Db25kaXRpb24uYW5kKFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLm9yKFxuICAgICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uYW5kKFxuICAgICAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLXR5cGUnLCAnUkRTIERCIEluc3RhbmNlIEV2ZW50JyksXG4gICAgICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5ldmVudC5kZXRhaWwuU291cmNlVHlwZScsICdEQl9JTlNUQU5DRScpLFxuICAgICAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLkV2ZW50SUQnLCAnUkRTLUVWRU5ULTAxNTQnKSxcbiAgICAgICAgICAgICAgICApLFxuICAgICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uYW5kKFxuICAgICAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQuZXZlbnQuZGV0YWlsLXR5cGUnLCAnUkRTIERCIENsdXN0ZXIgRXZlbnQnKSxcbiAgICAgICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC5Tb3VyY2VUeXBlJywgJ0NMVVNURVInKSxcbiAgICAgICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLmV2ZW50LmRldGFpbC5FdmVudElEJywgJ1JEUy1FVkVOVC0wMTUzJyksXG4gICAgICAgICAgICAgICAgKSxcbiAgICAgICAgICAgICAgKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQucmVzdWx0LmRlc2NyaWJlLnN0YXR1cycsICdzdG9wcGVkJyksXG4gICAgICAgICAgICApLFxuICAgICAgICAgICAgcHJlcGFyZVRvcGljVmFsdWUsIC8vIGdlbmVyYXRlZCAmIHB1Ymxpc2ggbWVzc2FnZVxuICAgICAgICAgIClcbiAgICAgICAgICAud2hlbihcbiAgICAgICAgICAgIHNmbi5Db25kaXRpb24ub3IoXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLnJlc3VsdC5kZXNjcmliZS5zdGF0dXMnLCAnc3RhcnRpbmcnKSxcbiAgICAgICAgICAgICAgc2ZuLkNvbmRpdGlvbi5zdHJpbmdFcXVhbHMoJyQucmVzdWx0LmRlc2NyaWJlLnN0YXR1cycsICdjb25maWd1cmluZy1lbmhhbmNlZC1tb25pdG9yaW5nJyksXG4gICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uc3RyaW5nRXF1YWxzKCckLnJlc3VsdC5kZXNjcmliZS5zdGF0dXMnLCAnYmFja2luZy11cCcpLFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5yZXN1bHQuZGVzY3JpYmUuc3RhdHVzJywgJ21vZGlmeWluZycpLFxuICAgICAgICAgICAgICBzZm4uQ29uZGl0aW9uLnN0cmluZ0VxdWFscygnJC5yZXN1bHQuZGVzY3JpYmUuc3RhdHVzJywgJ3N0b3BwaW5nJyksXG4gICAgICAgICAgICApLFxuICAgICAgICAgICAgc3RhdHVzQ2hhbmdlV2FpdCxcbiAgICAgICAgICApXG4gICAgICAgICAgLm90aGVyd2lzZShuZXcgc2ZuLkZhaWwoc2NvcGUsICdTdGF0dXNGYWlsJywge1xuICAgICAgICAgICAgY2F1c2U6ICdkYiBpbnN0YW5jZSBvciBjbHVzdGVyIHN0YXR1cyBmYWlsLicsXG4gICAgICAgICAgfSkpO1xuXG4gICAgICAgIC8vIPCfkYcgVGFnIE1hdGNoXG4gICAgICAgIGNvbnN0IHRhZ01hdGNoQ2hvaWNlID0gbmV3IHNmbi5DaG9pY2Uoc2NvcGUsICdFeGlzdFRhZ0Nob2lkZScpXG4gICAgICAgICAgLndoZW4oXG4gICAgICAgICAgICBzZm4uQ29uZGl0aW9uLmlzUHJlc2VudCgnJC5yZXN1bHQuZGVzY3JpYmUudGFncycpLFxuICAgICAgICAgICAgbmV3IHNmbi5QYXNzKHNjb3BlLCAnQ29udGFpblRhZ1ZsdWUnLCB7XG4gICAgICAgICAgICAgIHJlc3VsdFBhdGg6ICckLmNoZWNrLnRhZycsXG4gICAgICAgICAgICAgIHBhcmFtZXRlcnM6IHtcbiAgICAgICAgICAgICAgICBpc0NvbnRhaW46IHNmbi5Kc29uUGF0aC5hcnJheUNvbnRhaW5zKFxuICAgICAgICAgICAgICAgICAgc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLnBhcmFtcy50YWdWYWx1ZXMnKSxcbiAgICAgICAgICAgICAgICAgIHNmbi5Kc29uUGF0aC5hcnJheUdldEl0ZW0oc2ZuLkpzb25QYXRoLnN0cmluZ0F0KCckLnJlc3VsdC5kZXNjcmliZS50YWdzWz8oQC5LZXkgPT0gJC5wYXJhbXMudGFnS2V5KV0uVmFsdWUnKSwgMCksXG4gICAgICAgICAgICAgICAgKSxcbiAgICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIH0pLm5leHQoXG4gICAgICAgICAgICAgIG5ldyBzZm4uQ2hvaWNlKHNjb3BlLCAnRmlsdGVyVGFnQ2hvaXNlJylcbiAgICAgICAgICAgICAgICAud2hlbihcbiAgICAgICAgICAgICAgICAgIHNmbi5Db25kaXRpb24uYm9vbGVhbkVxdWFscygnJC5jaGVjay50YWcuaXNDb250YWluJywgdHJ1ZSksXG4gICAgICAgICAgICAgICAgICBzdGF0dXNDaG9pY2UsXG4gICAgICAgICAgICAgICAgKVxuICAgICAgICAgICAgICAgIC5vdGhlcndpc2UoXG4gICAgICAgICAgICAgICAgICBuZXcgc2ZuLlBhc3Moc2NvcGUsICdOb1RhZ01hdGNoJywge1xuICAgICAgICAgICAgICAgICAgICBjb21tZW50OiAnbm8gdGFnIG1hdGNoJyxcbiAgICAgICAgICAgICAgICAgIH0pLFxuICAgICAgICAgICAgICAgICksXG4gICAgICAgICAgICApLFxuICAgICAgICAgIClcbiAgICAgICAgICAub3RoZXJ3aXNlKFxuICAgICAgICAgICAgbmV3IHNmbi5QYXNzKHNjb3BlLCAnTm9UYWdzRm91bmQnLCB7XG4gICAgICAgICAgICAgIGNvbW1lbnQ6ICdubyB0YWdzIGZvdW5kJyxcbiAgICAgICAgICAgIH0pLFxuICAgICAgICAgICk7XG5cbiAgICAgICAgLy8g8J+RhyBkZXNjcmliZSBuZXh0IHRhZyBmb3VuZCAmIG1hdGNoXG4gICAgICAgIGRlc2NyaWJlREJJbnN0YW5jZXNUYXNrLm5leHQodGFnTWF0Y2hDaG9pY2UpO1xuICAgICAgICBkZXNjcmliZURCQ2x1c3RlcnNUYXNrLm5leHQodGFnTWF0Y2hDaG9pY2UpO1xuXG4gICAgICAgIHJldHVybiBzZm4uRGVmaW5pdGlvbkJvZHkuZnJvbUNoYWluYWJsZShzdGFydGluZ1dhaXQpO1xuICAgICAgfSkoKSxcbiAgICB9KTtcbiAgfVxufSJdfQ==