UNPKG

iam-floyd

Version:

AWS IAM policy statement generator with fluent interface

674 lines 68.1 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.Elasticloadbalancing = void 0; const shared_1 = require("../../shared"); /** * Statement provider for service [elasticloadbalancing](https://docs.aws.amazon.com/service-authorization/latest/reference/list_awselasticloadbalancing.html). * * @param sid [SID](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_sid.html) of the statement */ class Elasticloadbalancing extends shared_1.PolicyStatement { /** * Statement provider for service [elasticloadbalancing](https://docs.aws.amazon.com/service-authorization/latest/reference/list_awselasticloadbalancing.html). * * @param sid [SID](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_sid.html) of the statement */ constructor(sid) { super(sid); this.servicePrefix = 'elasticloadbalancing'; this.accessLevelList = { Tagging: [ 'AddTags', 'RemoveTags' ], Write: [ 'ApplySecurityGroupsToLoadBalancer', 'AttachLoadBalancerToSubnets', 'ConfigureHealthCheck', 'CreateAppCookieStickinessPolicy', 'CreateLBCookieStickinessPolicy', 'CreateLoadBalancer', 'CreateLoadBalancerListeners', 'CreateLoadBalancerPolicy', 'DeleteLoadBalancer', 'DeleteLoadBalancerListeners', 'DeleteLoadBalancerPolicy', 'DeregisterInstancesFromLoadBalancer', 'DetachLoadBalancerFromSubnets', 'DisableAvailabilityZonesForLoadBalancer', 'EnableAvailabilityZonesForLoadBalancer', 'ModifyLoadBalancerAttributes', 'RegisterInstancesWithLoadBalancer', 'SetLoadBalancerListenerSSLCertificate', 'SetLoadBalancerPoliciesForBackendServer', 'SetLoadBalancerPoliciesOfListener' ], Read: [ 'DescribeInstanceHealth', 'DescribeLoadBalancerAttributes', 'DescribeLoadBalancerPolicies', 'DescribeLoadBalancerPolicyTypes', 'DescribeTags' ], List: [ 'DescribeLoadBalancers' ] }; } /** * Grants permission to add the specified tags to the specified load balancer. Each load balancer can have a maximum of 10 tags * * Access Level: Tagging * * Possible conditions: * - .ifAwsRequestTag() * - .ifAwsTagKeys() * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifCreateAction() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_AddTags.html */ toAddTags() { return this.to('AddTags'); } /** * Grants permission to associate one or more security groups with your load balancer in a virtual private cloud (VPC) * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifSecurityGroup() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_ApplySecurityGroupsToLoadBalancer.html */ toApplySecurityGroupsToLoadBalancer() { return this.to('ApplySecurityGroupsToLoadBalancer'); } /** * Grants permission to add one or more subnets to the set of configured subnets for the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifSubnet() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_AttachLoadBalancerToSubnets.html */ toAttachLoadBalancerToSubnets() { return this.to('AttachLoadBalancerToSubnets'); } /** * Grants permission to specify the health check settings to use when evaluating the health state of your back-end instances * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_ConfigureHealthCheck.html */ toConfigureHealthCheck() { return this.to('ConfigureHealthCheck'); } /** * Grants permission to generate a stickiness policy with sticky session lifetimes that follow that of an application-generated cookie * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_CreateAppCookieStickinessPolicy.html */ toCreateAppCookieStickinessPolicy() { return this.to('CreateAppCookieStickinessPolicy'); } /** * Grants permission to generate a stickiness policy with sticky session lifetimes controlled by the lifetime of the browser (user-agent) or a specified expiration period * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_CreateLBCookieStickinessPolicy.html */ toCreateLBCookieStickinessPolicy() { return this.to('CreateLBCookieStickinessPolicy'); } /** * Grants permission to create a load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsRequestTag() * - .ifAwsTagKeys() * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifSecurityGroup() * - .ifSubnet() * - .ifScheme() * - .ifListenerProtocol() * * Dependent actions: * - elasticloadbalancing:AddTags * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_CreateLoadBalancer.html */ toCreateLoadBalancer() { return this.to('CreateLoadBalancer'); } /** * Grants permission to create one or more listeners for the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifListenerProtocol() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_CreateLoadBalancerListeners.html */ toCreateLoadBalancerListeners() { return this.to('CreateLoadBalancerListeners'); } /** * Grants permission to create a policy with the specified attributes for the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifSecurityPolicy() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_CreateLoadBalancerPolicy.html */ toCreateLoadBalancerPolicy() { return this.to('CreateLoadBalancerPolicy'); } /** * Grants permission to delete the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DeleteLoadBalancer.html */ toDeleteLoadBalancer() { return this.to('DeleteLoadBalancer'); } /** * Grants permission to delete the specified listeners from the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DeleteLoadBalancerListeners.html */ toDeleteLoadBalancerListeners() { return this.to('DeleteLoadBalancerListeners'); } /** * Grants permission to delete the specified policy from the specified load balancer. This policy must not be enabled for any listeners * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DeleteLoadBalancerPolicy.html */ toDeleteLoadBalancerPolicy() { return this.to('DeleteLoadBalancerPolicy'); } /** * Grants permission to deregister the specified instances from the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DeregisterInstancesFromLoadBalancer.html */ toDeregisterInstancesFromLoadBalancer() { return this.to('DeregisterInstancesFromLoadBalancer'); } /** * Grants permission to describe the state of the specified instances with respect to the specified load balancer * * Access Level: Read * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeInstanceHealth.html */ toDescribeInstanceHealth() { return this.to('DescribeInstanceHealth'); } /** * Grants permission to describe the attributes for the specified load balancer * * Access Level: Read * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeLoadBalancerAttributes.html */ toDescribeLoadBalancerAttributes() { return this.to('DescribeLoadBalancerAttributes'); } /** * Grants permission to describe the specified policies * * Access Level: Read * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeLoadBalancerPolicies.html */ toDescribeLoadBalancerPolicies() { return this.to('DescribeLoadBalancerPolicies'); } /** * Grants permission to describe the specified load balancer policy types * * Access Level: Read * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeLoadBalancerPolicyTypes.html */ toDescribeLoadBalancerPolicyTypes() { return this.to('DescribeLoadBalancerPolicyTypes'); } /** * Grants permission to describe the specified the load balancers. If no load balancers are specified, the call describes all of your load balancers * * Access Level: List * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeLoadBalancers.html */ toDescribeLoadBalancers() { return this.to('DescribeLoadBalancers'); } /** * Grants permission to describe the tags associated with the specified load balancers * * Access Level: Read * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DescribeTags.html */ toDescribeTags() { return this.to('DescribeTags'); } /** * Grants permission to remove the specified subnets from the set of configured subnets for the load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DetachLoadBalancerFromSubnets.html */ toDetachLoadBalancerFromSubnets() { return this.to('DetachLoadBalancerFromSubnets'); } /** * Grants permission to remove the specified Availability Zones from the set of Availability Zones for the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_DisableAvailabilityZonesForLoadBalancer.html */ toDisableAvailabilityZonesForLoadBalancer() { return this.to('DisableAvailabilityZonesForLoadBalancer'); } /** * Grants permission to add the specified Availability Zones to the set of Availability Zones for the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_EnableAvailabilityZonesForLoadBalancer.html */ toEnableAvailabilityZonesForLoadBalancer() { return this.to('EnableAvailabilityZonesForLoadBalancer'); } /** * Grants permission to modify the attributes of the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_ModifyLoadBalancerAttributes.html */ toModifyLoadBalancerAttributes() { return this.to('ModifyLoadBalancerAttributes'); } /** * Grants permission to add the specified instances to the specified load balancer * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_RegisterInstancesWithLoadBalancer.html */ toRegisterInstancesWithLoadBalancer() { return this.to('RegisterInstancesWithLoadBalancer'); } /** * Grants permission to remove one or more tags from the specified load balancer * * Access Level: Tagging * * Possible conditions: * - .ifAwsRequestTag() * - .ifAwsTagKeys() * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_RemoveTags.html */ toRemoveTags() { return this.to('RemoveTags'); } /** * Grants permission to set the certificate that terminates the specified listener's SSL connections * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_SetLoadBalancerListenerSSLCertificate.html */ toSetLoadBalancerListenerSSLCertificate() { return this.to('SetLoadBalancerListenerSSLCertificate'); } /** * Grants permission to replace the set of policies associated with the specified port on which the back-end server is listening with a new set of policies * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_SetLoadBalancerPoliciesForBackendServer.html */ toSetLoadBalancerPoliciesForBackendServer() { return this.to('SetLoadBalancerPoliciesForBackendServer'); } /** * Grants permission to replace the current set of policies for the specified load balancer port with the specified set of policies * * Access Level: Write * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() * - .ifSecurityPolicy() * * https://docs.aws.amazon.com/elasticloadbalancing/2012-06-01/APIReference/API_SetLoadBalancerPoliciesOfListener.html */ toSetLoadBalancerPoliciesOfListener() { return this.to('SetLoadBalancerPoliciesOfListener'); } /** * Adds a resource of type loadbalancer to the statement * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/what-is-load-balancing.html * * @param loadBalancerName - Identifier for the loadBalancerName. * @param account - Account of the resource; defaults to `*`, unless using the CDK, where the default is the current Stack's account. * @param region - Region of the resource; defaults to `*`, unless using the CDK, where the default is the current Stack's region. * @param partition - Partition of the AWS account [aws, aws-cn, aws-us-gov]; defaults to `aws`, unless using the CDK, where the default is the current Stack's partition. * * Possible conditions: * - .ifAwsResourceTag() * - .ifResourceTag() */ onLoadbalancer(loadBalancerName, account, region, partition) { return this.on(`arn:${partition ?? this.defaultPartition}:elasticloadbalancing:${region ?? this.defaultRegion}:${account ?? this.defaultAccount}:loadbalancer/${loadBalancerName}`); } /** * Filters access by a tag key and value pair that is allowed in the request * * https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_condition-keys.html#condition-keys-requesttag * * Applies to actions: * - .toAddTags() * - .toCreateLoadBalancer() * - .toRemoveTags() * * @param tagKey The tag key to check * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifAwsRequestTag(tagKey, value, operator) { return this.if(`aws:RequestTag/${tagKey}`, value, operator ?? 'StringLike'); } /** * Filters access by a tag key and value pair of a resource * * https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_condition-keys.html#condition-keys-resourcetag * * Applies to actions: * - .toAddTags() * - .toApplySecurityGroupsToLoadBalancer() * - .toAttachLoadBalancerToSubnets() * - .toConfigureHealthCheck() * - .toCreateAppCookieStickinessPolicy() * - .toCreateLBCookieStickinessPolicy() * - .toCreateLoadBalancer() * - .toCreateLoadBalancerListeners() * - .toCreateLoadBalancerPolicy() * - .toDeleteLoadBalancer() * - .toDeleteLoadBalancerListeners() * - .toDeleteLoadBalancerPolicy() * - .toDeregisterInstancesFromLoadBalancer() * - .toDetachLoadBalancerFromSubnets() * - .toDisableAvailabilityZonesForLoadBalancer() * - .toEnableAvailabilityZonesForLoadBalancer() * - .toModifyLoadBalancerAttributes() * - .toRegisterInstancesWithLoadBalancer() * - .toRemoveTags() * - .toSetLoadBalancerListenerSSLCertificate() * - .toSetLoadBalancerPoliciesForBackendServer() * - .toSetLoadBalancerPoliciesOfListener() * * Applies to resource types: * - loadbalancer * * @param tagKey The tag key to check * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifAwsResourceTag(tagKey, value, operator) { return this.if(`aws:ResourceTag/${tagKey}`, value, operator ?? 'StringLike'); } /** * Filters access by a list of tag keys that are allowed in the request * * https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_condition-keys.html#condition-keys-tagkeys * * Applies to actions: * - .toAddTags() * - .toCreateLoadBalancer() * - .toRemoveTags() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifAwsTagKeys(value, operator) { return this.if(`aws:TagKeys`, value, operator ?? 'StringLike'); } /** * Filters access by the name of a resource-creating API action * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/tagging-resources-during-creation.html * * Applies to actions: * - .toAddTags() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifCreateAction(value, operator) { return this.if(`CreateAction`, value, operator ?? 'StringLike'); } /** * Filters access by the listener protocols that are allowed in the request * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/security_iam_service-with-iam.html#listenerprotocol-condition * * Applies to actions: * - .toCreateLoadBalancer() * - .toCreateLoadBalancerListeners() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifListenerProtocol(value, operator) { return this.if(`ListenerProtocol`, value, operator ?? 'StringLike'); } /** * Filters access by the preface string for a tag key and value pair that are attached to a resource * * https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_condition-keys.html#condition-keys-resourcetag * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifResourceTagExists(value, operator) { return this.if(`ResourceTag/`, value, operator ?? 'StringLike'); } /** * Filters access by the preface string for a tag key and value pair that are attached to a resource * * https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_condition-keys.html#condition-keys-resourcetag * * Applies to actions: * - .toAddTags() * - .toApplySecurityGroupsToLoadBalancer() * - .toAttachLoadBalancerToSubnets() * - .toConfigureHealthCheck() * - .toCreateAppCookieStickinessPolicy() * - .toCreateLBCookieStickinessPolicy() * - .toCreateLoadBalancer() * - .toCreateLoadBalancerListeners() * - .toCreateLoadBalancerPolicy() * - .toDeleteLoadBalancer() * - .toDeleteLoadBalancerListeners() * - .toDeleteLoadBalancerPolicy() * - .toDeregisterInstancesFromLoadBalancer() * - .toDetachLoadBalancerFromSubnets() * - .toDisableAvailabilityZonesForLoadBalancer() * - .toEnableAvailabilityZonesForLoadBalancer() * - .toModifyLoadBalancerAttributes() * - .toRegisterInstancesWithLoadBalancer() * - .toRemoveTags() * - .toSetLoadBalancerListenerSSLCertificate() * - .toSetLoadBalancerPoliciesForBackendServer() * - .toSetLoadBalancerPoliciesOfListener() * * Applies to resource types: * - loadbalancer * * @param tagKey The tag key to check * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifResourceTag(tagKey, value, operator) { return this.if(`ResourceTag/${tagKey}`, value, operator ?? 'StringLike'); } /** * Filters access by the load balancer scheme that are allowed in the request * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/security_iam_service-with-iam.html#scheme-condition * * Applies to actions: * - .toCreateLoadBalancer() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifScheme(value, operator) { return this.if(`Scheme`, value, operator ?? 'StringLike'); } /** * Filters access by the security-group IDs that are allowed in the request * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/security_iam_service-with-iam.html#securitygroup-condition * * Applies to actions: * - .toApplySecurityGroupsToLoadBalancer() * - .toCreateLoadBalancer() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifSecurityGroup(value, operator) { return this.if(`SecurityGroup`, value, operator ?? 'StringLike'); } /** * Filters access by the SSL Security Policies that are allowed in the request * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/security_iam_service-with-iam.html#securitypolicy-condition * * Applies to actions: * - .toCreateLoadBalancerPolicy() * - .toSetLoadBalancerPoliciesOfListener() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifSecurityPolicy(value, operator) { return this.if(`SecurityPolicy`, value, operator ?? 'StringLike'); } /** * Filters access by the subnet IDs that are allowed in the request * * https://docs.aws.amazon.com/elasticloadbalancing/latest/userguide/security_iam_service-with-iam.html#subnet-condition * * Applies to actions: * - .toAttachLoadBalancerToSubnets() * - .toCreateLoadBalancer() * * @param value The value(s) to check * @param operator Works with [string operators](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_condition_operators.html#Conditions_String). **Default:** `StringLike` */ ifSubnet(value, operator) { return this.if(`Subnet`, value, operator ?? 'StringLike'); } } exports.Elasticloadbalancing = Elasticloadbalancing; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZWxhc3RpY2xvYWRiYWxhbmNpbmcuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyJlbGFzdGljbG9hZGJhbGFuY2luZy50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7QUFDQSx5Q0FBeUQ7QUFFekQ7Ozs7R0FJRztBQUNILE1BQWEsb0JBQXFCLFNBQVEsd0JBQWU7SUFHdkQ7Ozs7T0FJRztJQUNILFlBQVksR0FBWTtRQUN0QixLQUFLLENBQUMsR0FBRyxDQUFDLENBQUM7UUFSTixrQkFBYSxHQUFHLHNCQUFzQixDQUFDO1FBMGFwQyxvQkFBZSxHQUFvQjtZQUMzQyxPQUFPLEVBQUU7Z0JBQ1AsU0FBUztnQkFDVCxZQUFZO2FBQ2I7WUFDRCxLQUFLLEVBQUU7Z0JBQ0wsbUNBQW1DO2dCQUNuQyw2QkFBNkI7Z0JBQzdCLHNCQUFzQjtnQkFDdEIsaUNBQWlDO2dCQUNqQyxnQ0FBZ0M7Z0JBQ2hDLG9CQUFvQjtnQkFDcEIsNkJBQTZCO2dCQUM3QiwwQkFBMEI7Z0JBQzFCLG9CQUFvQjtnQkFDcEIsNkJBQTZCO2dCQUM3QiwwQkFBMEI7Z0JBQzFCLHFDQUFxQztnQkFDckMsK0JBQStCO2dCQUMvQix5Q0FBeUM7Z0JBQ3pDLHdDQUF3QztnQkFDeEMsOEJBQThCO2dCQUM5QixtQ0FBbUM7Z0JBQ25DLHVDQUF1QztnQkFDdkMseUNBQXlDO2dCQUN6QyxtQ0FBbUM7YUFDcEM7WUFDRCxJQUFJLEVBQUU7Z0JBQ0osd0JBQXdCO2dCQUN4QixnQ0FBZ0M7Z0JBQ2hDLDhCQUE4QjtnQkFDOUIsaUNBQWlDO2dCQUNqQyxjQUFjO2FBQ2Y7WUFDRCxJQUFJLEVBQUU7Z0JBQ0osdUJBQXVCO2FBQ3hCO1NBQ0YsQ0FBQztJQXRjRixDQUFDO0lBRUQ7Ozs7Ozs7Ozs7Ozs7T0FhRztJQUNJLFNBQVM7UUFDZCxPQUFPLElBQUksQ0FBQyxFQUFFLENBQUMsU0FBUyxDQUFDLENBQUM7SUFDNUIsQ0FBQztJQUVEOzs7Ozs7Ozs7OztPQVdHO0lBQ0ksbUNBQW1DO1FBQ3hDLE9B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QixFQUFFLFFBQTRCO1FBQ3pGLE9BQU8sSUFBSSxDQUFDLEVBQUUsQ0FBQyxlQUFnQixNQUFPLEVBQUUsRUFBRSxLQUFLLEVBQUUsUUFBUSxJQUFJLFlBQVksQ0FBQyxDQUFDO0lBQzdFLENBQUM7SUFFRDs7Ozs7Ozs7OztPQVVHO0lBQ0ksUUFBUSxDQUFDLEtBQXdCLEVBQUUsUUFBNEI7UUFDcEUsT0FBTyxJQUFJLENBQUMsRUFBRSxDQUFDLFFBQVEsRUFBRSxLQUFLLEVBQUUsUUFBUSxJQUFJLFlBQVksQ0FBQyxDQUFDO0lBQzVELENBQUM7SUFFRDs7Ozs7Ozs7Ozs7T0FXRztJQUNJLGVBQWUsQ0FBQyxLQUF3QixFQUFFLFFBQTRCO1FBQzNFLE9BQU8sSUFBSSxDQUFDLEVBQUUsQ0FBQyxlQUFlLEVBQUUsS0FBSyxFQUFFLFFBQVEsSUFBSSxZQUFZLENBQUMsQ0FBQztJQUNuRSxDQUFDO0lBRUQ7Ozs7Ozs7Ozs7O09BV0c7SUFDSSxnQkFBZ0IsQ0FBQyxLQUF3QixFQUFFLFFBQTRCO1FBQzVFLE9BQU8sSUFBSSxDQUFDLEVBQUUsQ0FBQyxnQkFBZ0IsRUFBRSxLQUFLLEVBQUUsUUFBUSxJQUFJLFlBQVksQ0FBQyxDQUFDO0lBQ3BFLENBQUM7SUFFRDs7Ozs7Ozs7Ozs7T0FXRztJQUNJLFFBQVEsQ0FBQyxLQUF3QixFQUFFLFFBQTRCO1FBQ3BFLE9BQU8sSUFBSSxDQUFDLEVBQUUsQ0FBQyxRQUFRLEVBQUUsS0FBSyxFQUFFLFFBQVEsSUFBSSxZQUFZLENBQUMsQ0FBQztJQUM1RCxDQUFDO0NBQ0Y7QUFoc0JELG9EQWdzQkMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBBY2Nlc3NMZXZlbExpc3QgfSBmcm9tICcuLi8uLi9zaGFyZWQvYWNjZXNzLWxldmVsJztcbmltcG9ydCB7IFBvbGljeVN0YXRlbWVudCwgT3BlcmF0b3IgfSBmcm9tICcuLi8uLi9zaGFyZWQnO1xuXG4vKipcbiAqIFN0YXRlbWVudCBwcm92aWRlciBmb3Igc2VydmljZSBbZWxhc3RpY2xvYWRiYWxhbmNpbmddKGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9zZXJ2aWNlLWF1dGhvcml6YXRpb24vbGF0ZXN0L3JlZmVyZW5jZS9saXN0X2F3c2VsYXN0aWNsb2FkYmFsYW5jaW5nLmh0bWwpLlxuICpcbiAqIEBwYXJhbSBzaWQgW1NJRF0oaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL0lBTS9sYXRlc3QvVXNlckd1aWRlL3JlZmVyZW5jZV9wb2xpY2llc19lbGVtZW50c19zaWQuaHRtbCkgb2YgdGhlIHN0YXRlbWVudFxuICovXG5leHBvcnQgY2xhc3MgRWxhc3RpY2xvYWRiYWxhbmNpbmcgZXh0ZW5kcyBQb2xpY3lTdGF0ZW1lbnQge1xuICBwdWJsaWMgc2VydmljZVByZWZpeCA9ICdlbGFzdGljbG9hZGJhbGFuY2luZyc7XG5cbiAgLyoqXG4gICAqIFN0YXRlbWVudCBwcm92aWRlciBmb3Igc2VydmljZSBbZWxhc3RpY2xvYWRiYWxhbmNpbmddKGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9zZXJ2aWNlLWF1dGhvcml6YXRpb24vbGF0ZXN0L3JlZmVyZW5jZS9saXN0X2F3c2VsYXN0aWNsb2FkYmFsYW5jaW5nLmh0bWwpLlxuICAgKlxuICAgKiBAcGFyYW0gc2lkIFtTSURdKGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9JQU0vbGF0ZXN0L1VzZXJHdWlkZS9yZWZlcmVuY2VfcG9saWNpZXNfZWxlbWVudHNfc2lkLmh0bWwpIG9mIHRoZSBzdGF0ZW1lbnRcbiAgICovXG4gIGNvbnN0cnVjdG9yKHNpZD86IHN0cmluZykge1xuICAgIHN1cGVyKHNpZCk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gYWRkIHRoZSBzcGVjaWZpZWQgdGFncyB0byB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXIuIEVhY2ggbG9hZCBiYWxhbmNlciBjYW4gaGF2ZSBhIG1heGltdW0gb2YgMTAgdGFnc1xuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFRhZ2dpbmdcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXF1ZXN0VGFnKClcbiAgICogLSAuaWZBd3NUYWdLZXlzKClcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZkNyZWF0ZUFjdGlvbigpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfQWRkVGFncy5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9BZGRUYWdzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdBZGRUYWdzJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gYXNzb2NpYXRlIG9uZSBvciBtb3JlIHNlY3VyaXR5IGdyb3VwcyB3aXRoIHlvdXIgbG9hZCBiYWxhbmNlciBpbiBhIHZpcnR1YWwgcHJpdmF0ZSBjbG91ZCAoVlBDKVxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICogLSAuaWZTZWN1cml0eUdyb3VwKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9BcHBseVNlY3VyaXR5R3JvdXBzVG9Mb2FkQmFsYW5jZXIuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvQXBwbHlTZWN1cml0eUdyb3Vwc1RvTG9hZEJhbGFuY2VyKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdBcHBseVNlY3VyaXR5R3JvdXBzVG9Mb2FkQmFsYW5jZXInKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBhZGQgb25lIG9yIG1vcmUgc3VibmV0cyB0byB0aGUgc2V0IG9mIGNvbmZpZ3VyZWQgc3VibmV0cyBmb3IgdGhlIHNwZWNpZmllZCBsb2FkIGJhbGFuY2VyXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogV3JpdGVcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlN1Ym5ldCgpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfQXR0YWNoTG9hZEJhbGFuY2VyVG9TdWJuZXRzLmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0F0dGFjaExvYWRCYWxhbmNlclRvU3VibmV0cygpIHtcbiAgICByZXR1cm4gdGhpcy50bygnQXR0YWNoTG9hZEJhbGFuY2VyVG9TdWJuZXRzJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gc3BlY2lmeSB0aGUgaGVhbHRoIGNoZWNrIHNldHRpbmdzIHRvIHVzZSB3aGVuIGV2YWx1YXRpbmcgdGhlIGhlYWx0aCBzdGF0ZSBvZiB5b3VyIGJhY2stZW5kIGluc3RhbmNlc1xuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9Db25maWd1cmVIZWFsdGhDaGVjay5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9Db25maWd1cmVIZWFsdGhDaGVjaygpIHtcbiAgICByZXR1cm4gdGhpcy50bygnQ29uZmlndXJlSGVhbHRoQ2hlY2snKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBnZW5lcmF0ZSBhIHN0aWNraW5lc3MgcG9saWN5IHdpdGggc3RpY2t5IHNlc3Npb24gbGlmZXRpbWVzIHRoYXQgZm9sbG93IHRoYXQgb2YgYW4gYXBwbGljYXRpb24tZ2VuZXJhdGVkIGNvb2tpZVxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9DcmVhdGVBcHBDb29raWVTdGlja2luZXNzUG9saWN5Lmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0NyZWF0ZUFwcENvb2tpZVN0aWNraW5lc3NQb2xpY3koKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ0NyZWF0ZUFwcENvb2tpZVN0aWNraW5lc3NQb2xpY3knKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBnZW5lcmF0ZSBhIHN0aWNraW5lc3MgcG9saWN5IHdpdGggc3RpY2t5IHNlc3Npb24gbGlmZXRpbWVzIGNvbnRyb2xsZWQgYnkgdGhlIGxpZmV0aW1lIG9mIHRoZSBicm93c2VyICh1c2VyLWFnZW50KSBvciBhIHNwZWNpZmllZCBleHBpcmF0aW9uIHBlcmlvZFxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9DcmVhdGVMQkNvb2tpZVN0aWNraW5lc3NQb2xpY3kuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvQ3JlYXRlTEJDb29raWVTdGlja2luZXNzUG9saWN5KCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdDcmVhdGVMQkNvb2tpZVN0aWNraW5lc3NQb2xpY3knKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBjcmVhdGUgYSBsb2FkIGJhbGFuY2VyXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogV3JpdGVcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXF1ZXN0VGFnKClcbiAgICogLSAuaWZBd3NUYWdLZXlzKClcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlNlY3VyaXR5R3JvdXAoKVxuICAgKiAtIC5pZlN1Ym5ldCgpXG4gICAqIC0gLmlmU2NoZW1lKClcbiAgICogLSAuaWZMaXN0ZW5lclByb3RvY29sKClcbiAgICpcbiAgICogRGVwZW5kZW50IGFjdGlvbnM6XG4gICAqIC0gZWxhc3RpY2xvYWRiYWxhbmNpbmc6QWRkVGFnc1xuICAgKlxuICAgKiBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvMjAxMi0wNi0wMS9BUElSZWZlcmVuY2UvQVBJX0NyZWF0ZUxvYWRCYWxhbmNlci5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9DcmVhdGVMb2FkQmFsYW5jZXIoKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ0NyZWF0ZUxvYWRCYWxhbmNlcicpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdyYW50cyBwZXJtaXNzaW9uIHRvIGNyZWF0ZSBvbmUgb3IgbW9yZSBsaXN0ZW5lcnMgZm9yIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlclxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICogLSAuaWZMaXN0ZW5lclByb3RvY29sKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9DcmVhdGVMb2FkQmFsYW5jZXJMaXN0ZW5lcnMuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvQ3JlYXRlTG9hZEJhbGFuY2VyTGlzdGVuZXJzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdDcmVhdGVMb2FkQmFsYW5jZXJMaXN0ZW5lcnMnKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBjcmVhdGUgYSBwb2xpY3kgd2l0aCB0aGUgc3BlY2lmaWVkIGF0dHJpYnV0ZXMgZm9yIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlclxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICogLSAuaWZTZWN1cml0eVBvbGljeSgpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfQ3JlYXRlTG9hZEJhbGFuY2VyUG9saWN5Lmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0NyZWF0ZUxvYWRCYWxhbmNlclBvbGljeSgpIHtcbiAgICByZXR1cm4gdGhpcy50bygnQ3JlYXRlTG9hZEJhbGFuY2VyUG9saWN5Jyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gZGVsZXRlIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlclxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9EZWxldGVMb2FkQmFsYW5jZXIuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVsZXRlTG9hZEJhbGFuY2VyKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZWxldGVMb2FkQmFsYW5jZXInKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBkZWxldGUgdGhlIHNwZWNpZmllZCBsaXN0ZW5lcnMgZnJvbSB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXJcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBXcml0ZVxuICAgKlxuICAgKiBQb3NzaWJsZSBjb25kaXRpb25zOlxuICAgKiAtIC5pZkF3c1Jlc291cmNlVGFnKClcbiAgICogLSAuaWZSZXNvdXJjZVRhZygpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRGVsZXRlTG9hZEJhbGFuY2VyTGlzdGVuZXJzLmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0RlbGV0ZUxvYWRCYWxhbmNlckxpc3RlbmVycygpIHtcbiAgICByZXR1cm4gdGhpcy50bygnRGVsZXRlTG9hZEJhbGFuY2VyTGlzdGVuZXJzJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gZGVsZXRlIHRoZSBzcGVjaWZpZWQgcG9saWN5IGZyb20gdGhlIHNwZWNpZmllZCBsb2FkIGJhbGFuY2VyLiBUaGlzIHBvbGljeSBtdXN0IG5vdCBiZSBlbmFibGVkIGZvciBhbnkgbGlzdGVuZXJzXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogV3JpdGVcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKlxuICAgKiBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvMjAxMi0wNi0wMS9BUElSZWZlcmVuY2UvQVBJX0RlbGV0ZUxvYWRCYWxhbmNlclBvbGljeS5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9EZWxldGVMb2FkQmFsYW5jZXJQb2xpY3koKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ0RlbGV0ZUxvYWRCYWxhbmNlclBvbGljeScpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdyYW50cyBwZXJtaXNzaW9uIHRvIGRlcmVnaXN0ZXIgdGhlIHNwZWNpZmllZCBpbnN0YW5jZXMgZnJvbSB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXJcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBXcml0ZVxuICAgKlxuICAgKiBQb3NzaWJsZSBjb25kaXRpb25zOlxuICAgKiAtIC5pZkF3c1Jlc291cmNlVGFnKClcbiAgICogLSAuaWZSZXNvdXJjZVRhZygpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRGVyZWdpc3Rlckluc3RhbmNlc0Zyb21Mb2FkQmFsYW5jZXIuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVyZWdpc3Rlckluc3RhbmNlc0Zyb21Mb2FkQmFsYW5jZXIoKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ0RlcmVnaXN0ZXJJbnN0YW5jZXNGcm9tTG9hZEJhbGFuY2VyJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gZGVzY3JpYmUgdGhlIHN0YXRlIG9mIHRoZSBzcGVjaWZpZWQgaW5zdGFuY2VzIHdpdGggcmVzcGVjdCB0byB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXJcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBSZWFkXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRGVzY3JpYmVJbnN0YW5jZUhlYWx0aC5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9EZXNjcmliZUluc3RhbmNlSGVhbHRoKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXNjcmliZUluc3RhbmNlSGVhbHRoJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gZGVzY3JpYmUgdGhlIGF0dHJpYnV0ZXMgZm9yIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlclxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFJlYWRcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9EZXNjcmliZUxvYWRCYWxhbmNlckF0dHJpYnV0ZXMuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVzY3JpYmVMb2FkQmFsYW5jZXJBdHRyaWJ1dGVzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXNjcmliZUxvYWRCYWxhbmNlckF0dHJpYnV0ZXMnKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBkZXNjcmliZSB0aGUgc3BlY2lmaWVkIHBvbGljaWVzXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogUmVhZFxuICAgKlxuICAgKiBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvMjAxMi0wNi0wMS9BUElSZWZlcmVuY2UvQVBJX0Rlc2NyaWJlTG9hZEJhbGFuY2VyUG9saWNpZXMuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVzY3JpYmVMb2FkQmFsYW5jZXJQb2xpY2llcygpIHtcbiAgICByZXR1cm4gdGhpcy50bygnRGVzY3JpYmVMb2FkQmFsYW5jZXJQb2xpY2llcycpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdyYW50cyBwZXJtaXNzaW9uIHRvIGRlc2NyaWJlIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlciBwb2xpY3kgdHlwZXNcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBSZWFkXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRGVzY3JpYmVMb2FkQmFsYW5jZXJQb2xpY3lUeXBlcy5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9EZXNjcmliZUxvYWRCYWxhbmNlclBvbGljeVR5cGVzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXNjcmliZUxvYWRCYWxhbmNlclBvbGljeVR5cGVzJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gZGVzY3JpYmUgdGhlIHNwZWNpZmllZCB0aGUgbG9hZCBiYWxhbmNlcnMuIElmIG5vIGxvYWQgYmFsYW5jZXJzIGFyZSBzcGVjaWZpZWQsIHRoZSBjYWxsIGRlc2NyaWJlcyBhbGwgb2YgeW91ciBsb2FkIGJhbGFuY2Vyc1xuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IExpc3RcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9EZXNjcmliZUxvYWRCYWxhbmNlcnMuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVzY3JpYmVMb2FkQmFsYW5jZXJzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXNjcmliZUxvYWRCYWxhbmNlcnMnKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBkZXNjcmliZSB0aGUgdGFncyBhc3NvY2lhdGVkIHdpdGggdGhlIHNwZWNpZmllZCBsb2FkIGJhbGFuY2Vyc1xuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFJlYWRcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9EZXNjcmliZVRhZ3MuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRGVzY3JpYmVUYWdzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXNjcmliZVRhZ3MnKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byByZW1vdmUgdGhlIHNwZWNpZmllZCBzdWJuZXRzIGZyb20gdGhlIHNldCBvZiBjb25maWd1cmVkIHN1Ym5ldHMgZm9yIHRoZSBsb2FkIGJhbGFuY2VyXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogV3JpdGVcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKlxuICAgKiBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvMjAxMi0wNi0wMS9BUElSZWZlcmVuY2UvQVBJX0RldGFjaExvYWRCYWxhbmNlckZyb21TdWJuZXRzLmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0RldGFjaExvYWRCYWxhbmNlckZyb21TdWJuZXRzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdEZXRhY2hMb2FkQmFsYW5jZXJGcm9tU3VibmV0cycpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdyYW50cyBwZXJtaXNzaW9uIHRvIHJlbW92ZSB0aGUgc3BlY2lmaWVkIEF2YWlsYWJpbGl0eSBab25lcyBmcm9tIHRoZSBzZXQgb2YgQXZhaWxhYmlsaXR5IFpvbmVzIGZvciB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXJcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBXcml0ZVxuICAgKlxuICAgKiBQb3NzaWJsZSBjb25kaXRpb25zOlxuICAgKiAtIC5pZkF3c1Jlc291cmNlVGFnKClcbiAgICogLSAuaWZSZXNvdXJjZVRhZygpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRGlzYWJsZUF2YWlsYWJpbGl0eVpvbmVzRm9yTG9hZEJhbGFuY2VyLmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b0Rpc2FibGVBdmFpbGFiaWxpdHlab25lc0ZvckxvYWRCYWxhbmNlcigpIHtcbiAgICByZXR1cm4gdGhpcy50bygnRGlzYWJsZUF2YWlsYWJpbGl0eVpvbmVzRm9yTG9hZEJhbGFuY2VyJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gYWRkIHRoZSBzcGVjaWZpZWQgQXZhaWxhYmlsaXR5IFpvbmVzIHRvIHRoZSBzZXQgb2YgQXZhaWxhYmlsaXR5IFpvbmVzIGZvciB0aGUgc3BlY2lmaWVkIGxvYWQgYmFsYW5jZXJcbiAgICpcbiAgICogQWNjZXNzIExldmVsOiBXcml0ZVxuICAgKlxuICAgKiBQb3NzaWJsZSBjb25kaXRpb25zOlxuICAgKiAtIC5pZkF3c1Jlc291cmNlVGFnKClcbiAgICogLSAuaWZSZXNvdXJjZVRhZygpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfRW5hYmxlQXZhaWxhYmlsaXR5Wm9uZXNGb3JMb2FkQmFsYW5jZXIuaHRtbFxuICAgKi9cbiAgcHVibGljIHRvRW5hYmxlQXZhaWxhYmlsaXR5Wm9uZXNGb3JMb2FkQmFsYW5jZXIoKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ0VuYWJsZUF2YWlsYWJpbGl0eVpvbmVzRm9yTG9hZEJhbGFuY2VyJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gbW9kaWZ5IHRoZSBhdHRyaWJ1dGVzIG9mIHRoZSBzcGVjaWZpZWQgbG9hZCBiYWxhbmNlclxuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5pZlJlc291cmNlVGFnKClcbiAgICpcbiAgICogaHR0cHM6Ly9kb2NzLmF3cy5hbWF6b24uY29tL2VsYXN0aWNsb2FkYmFsYW5jaW5nLzIwMTItMDYtMDEvQVBJUmVmZXJlbmNlL0FQSV9Nb2RpZnlMb2FkQmFsYW5jZXJBdHRyaWJ1dGVzLmh0bWxcbiAgICovXG4gIHB1YmxpYyB0b01vZGlmeUxvYWRCYWxhbmNlckF0dHJpYnV0ZXMoKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ01vZGlmeUxvYWRCYWxhbmNlckF0dHJpYnV0ZXMnKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHcmFudHMgcGVybWlzc2lvbiB0byBhZGQgdGhlIHNwZWNpZmllZCBpbnN0YW5jZXMgdG8gdGhlIHNwZWNpZmllZCBsb2FkIGJhbGFuY2VyXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogV3JpdGVcbiAgICpcbiAgICogUG9zc2libGUgY29uZGl0aW9uczpcbiAgICogLSAuaWZBd3NSZXNvdXJjZVRhZygpXG4gICAqIC0gLmlmUmVzb3VyY2VUYWcoKVxuICAgKlxuICAgKiBodHRwczovL2RvY3MuYXdzLmFtYXpvbi5jb20vZWxhc3RpY2xvYWRiYWxhbmNpbmcvMjAxMi0wNi0wMS9BUElSZWZlcmVuY2UvQVBJX1JlZ2lzdGVySW5zdGFuY2VzV2l0aExvYWRCYWxhbmNlci5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9SZWdpc3Rlckluc3RhbmNlc1dpdGhMb2FkQmFsYW5jZXIoKSB7XG4gICAgcmV0dXJuIHRoaXMudG8oJ1JlZ2lzdGVySW5zdGFuY2VzV2l0aExvYWRCYWxhbmNlcicpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdyYW50cyBwZXJtaXNzaW9uIHRvIHJlbW92ZSBvbmUgb3IgbW9yZSB0YWdzIGZyb20gdGhlIHNwZWNpZmllZCBsb2FkIGJhbGFuY2VyXG4gICAqXG4gICAqIEFjY2VzcyBMZXZlbDogVGFnZ2luZ1xuICAgKlxuICAgKiBQb3NzaWJsZSBjb25kaXRpb25zOlxuICAgKiAtIC5pZkF3c1JlcXVlc3RUYWcoKVxuICAgKiAtIC5pZkF3c1RhZ0tleXMoKVxuICAgKiAtIC5pZkF3c1Jlc291cmNlVGFnKClcbiAgICogLSAuaWZSZXNvdXJjZVRhZygpXG4gICAqXG4gICAqIGh0dHBzOi8vZG9jcy5hd3MuYW1hem9uLmNvbS9lbGFzdGljbG9hZGJhbGFuY2luZy8yMDEyLTA2LTAxL0FQSVJlZmVyZW5jZS9BUElfUmVtb3ZlVGFncy5odG1sXG4gICAqL1xuICBwdWJsaWMgdG9SZW1vdmVUYWdzKCkge1xuICAgIHJldHVybiB0aGlzLnRvKCdSZW1vdmVUYWdzJyk7XG4gIH1cblxuICAvKipcbiAgICogR3JhbnRzIHBlcm1pc3Npb24gdG8gc2V0IHRoZSBjZXJ0aWZpY2F0ZSB0aGF0IHRlcm1pbmF0ZXMgdGhlIHNwZWNpZmllZCBsaXN0ZW5lcidzIFNTTCBjb25uZWN0aW9uc1xuICAgKlxuICAgKiBBY2Nlc3MgTGV2ZWw6IFdyaXRlXG4gICAqXG4gICAqIFBvc3NpYmxlIGNvbmRpdGlvbnM6XG4gICAqIC0gLmlmQXdzUmVzb3VyY2VUYWcoKVxuICAgKiAtIC5