UNPKG

cdk8s-plus-25

Version:

cdk8s+ is a software development framework that provides high level abstractions for authoring Kubernetes applications. cdk8s-plus-25 synthesizes Kubernetes manifests for Kubernetes 1.25.0

625 lines 85.2 kB
"use strict"; var _a, _b, _c, _d, _e, _f; Object.defineProperty(exports, "__esModule", { value: true }); exports.Env = exports.extractContainerPorts = exports.EnvFrom = exports.Cpu = exports.MountPropagation = exports.Container = exports.ImagePullPolicy = exports.EnvValue = exports.ResourceFieldPaths = exports.EnvFieldPaths = exports.ContainerSecurityContext = exports.Protocol = void 0; const JSII_RTTI_SYMBOL_1 = Symbol.for("jsii.rtti"); const cdk8s_1 = require("cdk8s"); const k8s = require("./imports/k8s"); const probe = require("./probe"); const utils_1 = require("./utils"); /** * Network protocols. */ var Protocol; (function (Protocol) { /** * TCP. */ Protocol["TCP"] = "TCP"; /** * UDP. */ Protocol["UDP"] = "UDP"; /** * SCTP. */ Protocol["SCTP"] = "SCTP"; })(Protocol = exports.Protocol || (exports.Protocol = {})); /** * Container security attributes and settings. */ class ContainerSecurityContext { constructor(props = {}) { this.ensureNonRoot = props.ensureNonRoot ?? true; this.privileged = props.privileged ?? false; this.readOnlyRootFilesystem = props.readOnlyRootFilesystem ?? true; this.user = props.user; this.group = props.group; this.allowPrivilegeEscalation = props.allowPrivilegeEscalation ?? false; } /** * @internal */ _toKube() { return { runAsGroup: this.group, runAsUser: this.user, runAsNonRoot: this.ensureNonRoot, privileged: this.privileged, readOnlyRootFilesystem: this.readOnlyRootFilesystem, allowPrivilegeEscalation: this.allowPrivilegeEscalation, }; } } exports.ContainerSecurityContext = ContainerSecurityContext; _a = JSII_RTTI_SYMBOL_1; ContainerSecurityContext[_a] = { fqn: "cdk8s-plus-25.ContainerSecurityContext", version: "2.22.79" }; var EnvFieldPaths; (function (EnvFieldPaths) { /** * The name of the pod. */ EnvFieldPaths["POD_NAME"] = "metadata.name"; /** * The namespace of the pod. */ EnvFieldPaths["POD_NAMESPACE"] = "metadata.namespace"; /** * The uid of the pod. */ EnvFieldPaths["POD_UID"] = "metadata.uid"; /** * The labels of the pod. */ EnvFieldPaths["POD_LABEL"] = "metadata.labels"; /** * The annotations of the pod. */ EnvFieldPaths["POD_ANNOTATION"] = "metadata.annotations"; /** * The ipAddress of the pod. */ EnvFieldPaths["POD_IP"] = "status.podIP"; /** * The service account name of the pod. */ EnvFieldPaths["SERVICE_ACCOUNT_NAME"] = "spec.serviceAccountName"; /** * The name of the node. */ EnvFieldPaths["NODE_NAME"] = "spec.nodeName"; /** * The ipAddress of the node. */ EnvFieldPaths["NODE_IP"] = "status.hostIP"; /** * The ipAddresess of the pod. */ EnvFieldPaths["POD_IPS"] = "status.podIPs"; })(EnvFieldPaths = exports.EnvFieldPaths || (exports.EnvFieldPaths = {})); var ResourceFieldPaths; (function (ResourceFieldPaths) { /** * CPU limit of the container. */ ResourceFieldPaths["CPU_LIMIT"] = "limits.cpu"; /** * Memory limit of the container. */ ResourceFieldPaths["MEMORY_LIMIT"] = "limits.memory"; /** * CPU request of the container. */ ResourceFieldPaths["CPU_REQUEST"] = "requests.cpu"; /** * Memory request of the container. */ ResourceFieldPaths["MEMORY_REQUEST"] = "requests.memory"; /** * Ephemeral storage limit of the container. */ ResourceFieldPaths["STORAGE_LIMIT"] = "limits.ephemeral-storage"; /** * Ephemeral storage request of the container. */ ResourceFieldPaths["STORAGE_REQUEST"] = "requests.ephemeral-storage"; })(ResourceFieldPaths = exports.ResourceFieldPaths || (exports.ResourceFieldPaths = {})); /** * Utility class for creating reading env values from various sources. */ class EnvValue { constructor(value, valueFrom) { this.value = value; this.valueFrom = valueFrom; } /** * Create a value by reading a specific key inside a config map. * * @param configMap - The config map. * @param key - The key to extract the value from. * @param options - Additional options. */ static fromConfigMap(configMap, key, options = {}) { const source = { configMapKeyRef: { name: configMap.name, key, optional: options.optional, }, }; return new EnvValue(undefined, source); } /** * Defines an environment value from a secret JSON value. * * @param secretValue The secret value (secrent + key) * @param options Additional options */ static fromSecretValue(secretValue, options = {}) { const source = { secretKeyRef: { name: secretValue.secret.name, key: secretValue.key, optional: options.optional, }, }; return new EnvValue(undefined, source); } /** * Create a value from the given argument. * * @param value - The value. */ static fromValue(value) { return new EnvValue(value); } /** * * Create a value from a field reference. * * @param fieldPath: The field reference. * @param options: Additional options. */ static fromFieldRef(fieldPath, options = {}) { let needsKey = false; if (fieldPath === EnvFieldPaths.POD_LABEL || fieldPath === EnvFieldPaths.POD_ANNOTATION) { needsKey = true; } if (needsKey && options.key === undefined) { throw new Error(`${fieldPath} requires a key`); } const source = { fieldRef: { fieldPath: (`${fieldPath}` + (needsKey ? `['${options.key}']` : '')), ...(options.apiVersion ? { apiVersion: options.apiVersion } : {}), }, }; return new EnvValue(undefined, source); } /** * Create a value from a resource. * * @param resource: Resource to select the value from. * @param options: Additional options. */ static fromResource(resource, options = {}) { const source = { resourceFieldRef: { resource: `${resource}`, ...(options.divisor ? { divisor: k8s.IntOrString.fromString(options.divisor) } : {}), ...(options.container ? { containerName: options.container.name } : {}), }, }; return new EnvValue(undefined, source); } /** * Create a value from a key in the current process environment. * * @param key - The key to read. * @param options - Additional options. */ static fromProcess(key, options = {}) { const value = process.env[key]; if (options.required && !value) { throw new Error(`Missing ${key} env variable`); } return EnvValue.fromValue(value); } } exports.EnvValue = EnvValue; _b = JSII_RTTI_SYMBOL_1; EnvValue[_b] = { fqn: "cdk8s-plus-25.EnvValue", version: "2.22.79" }; var ImagePullPolicy; (function (ImagePullPolicy) { /** * Every time the kubelet launches a container, the kubelet queries the container image registry * to resolve the name to an image digest. If the kubelet has a container image with that exact * digest cached locally, the kubelet uses its cached image; otherwise, the kubelet downloads * (pulls) the image with the resolved digest, and uses that image to launch the container. * * Default is Always if ImagePullPolicy is omitted and either the image tag is :latest or * the image tag is omitted. */ ImagePullPolicy["ALWAYS"] = "Always"; /** * The image is pulled only if it is not already present locally. * * Default is IfNotPresent if ImagePullPolicy is omitted and the image tag is present but * not :latest */ ImagePullPolicy["IF_NOT_PRESENT"] = "IfNotPresent"; /** * The image is assumed to exist locally. No attempt is made to pull the image. */ ImagePullPolicy["NEVER"] = "Never"; })(ImagePullPolicy = exports.ImagePullPolicy || (exports.ImagePullPolicy = {})); /** * A single application container that you want to run within a pod. */ class Container { constructor(props) { this._ports = []; if (props instanceof Container) { throw new Error('Attempted to construct a container from a Container object.'); } const defaultResourceSpec = { cpu: { request: Cpu.millis(1000), limit: Cpu.millis(1500), }, memory: { request: cdk8s_1.Size.mebibytes(512), limit: cdk8s_1.Size.mebibytes(2048), }, }; if (props.port && props.portNumber) { throw new Error('Either \'port\' or \'portNumber\' is allowed. Use \'portNumber\' since \'port\' is deprecated'); } const portNumber = props.portNumber ?? props.port; const defaultProbeConfiguration = probe.Probe.fromTcpSocket({ port: portNumber }); this.name = props.name ?? 'main'; this.image = props.image; this.portNumber = portNumber; this._command = props.command; this._args = props.args; this._readiness = props.readiness; this._liveness = props.liveness; this._startup = props.startup ?? (this.portNumber ? defaultProbeConfiguration : undefined); this._lifecycle = props.lifecycle; this.resources = props.resources ?? defaultResourceSpec; this.workingDir = props.workingDir; this.mounts = props.volumeMounts ?? []; this.imagePullPolicy = props.imagePullPolicy ?? ImagePullPolicy.ALWAYS; this.securityContext = new ContainerSecurityContext(props.securityContext); this.env = new Env(props.envFrom ?? [], props.envVariables ?? {}); if (this.portNumber) { this.addPort({ number: this.portNumber, }); } for (const port of props.ports ?? []) { this.addPort(port); } } /** * @deprecated - use `portNumber`. */ get port() { return this.portNumber; } /** * Ports exposed by this containers. * Returns a copy, use `addPort` to modify. */ get ports() { return [...this._ports]; } /** * Entrypoint array (the command to execute when the container starts). * @returns a copy of the entrypoint array, cannot be modified */ get command() { return this._command ? [...this._command] : undefined; } /** * Arguments to the entrypoint. * * @returns a copy of the arguments array, cannot be modified. */ get args() { return this._args ? [...this._args] : undefined; } /** * Mount a volume to a specific path so that it is accessible by the container. * Every pod that is configured to use this container will autmoatically have access to the volume. * * @param path - The desired path in the container. * @param storage - The storage to mount. */ mount(path, storage, options = {}) { this.mounts.push({ path, volume: storage.asVolume(), ...options }); } /** * Add a port to expose from this container. */ addPort(port) { const names = this._ports.map(p => p.name).filter(x => x); const numbers = this._ports.map(p => p.number); if (port.name && names.includes(port.name)) { throw new Error(`Port with name ${port.name} already exists`); } if (numbers.includes(port.number)) { throw new Error(`Port with number ${port.number} already exists`); } this._ports.push(port); } /** * @internal */ _toKube() { const volumeMounts = []; for (const mount of this.mounts) { volumeMounts.push({ name: mount.volume.name, mountPath: mount.path, readOnly: mount.readOnly, mountPropagation: mount.propagation, subPath: mount.subPath, subPathExpr: mount.subPathExpr, }); } const ports = new Array(); for (const port of this.ports) { ports.push({ containerPort: port.number, protocol: port.protocol?.toString(), name: port.name, hostPort: port.hostPort, hostIp: port.hostIp, }); } // Resource requests and limits const cpuLimit = this.resources?.cpu?.limit?.amount; const cpuRequest = this.resources?.cpu?.request?.amount; const memoryLimit = this.resources?.memory?.limit; const memoryRequest = this.resources?.memory?.request; const ephemeralStorageLimit = this.resources?.ephemeralStorage?.limit; const ephemeralStorageRequest = this.resources?.ephemeralStorage?.request; const limits = {}; const requests = {}; if (cpuLimit) { limits.cpu = k8s.Quantity.fromString(cpuLimit); } if (memoryLimit) { limits.memory = k8s.Quantity.fromString(memoryLimit.toMebibytes().toString() + 'Mi'); } if (ephemeralStorageLimit) { limits['ephemeral-storage'] = k8s.Quantity.fromString(ephemeralStorageLimit.toGibibytes().toString() + 'Gi'); } if (cpuRequest) { requests.cpu = k8s.Quantity.fromString(cpuRequest); } if (memoryRequest) { requests.memory = k8s.Quantity.fromString(memoryRequest.toMebibytes().toString() + 'Mi'); } if (ephemeralStorageRequest) { requests['ephemeral-storage'] = k8s.Quantity.fromString(ephemeralStorageRequest.toGibibytes().toString() + 'Gi'); } let resourceRequirements = undefined; if (Object.keys(limits).length > 0 || Object.keys(requests).length > 0) { resourceRequirements = { limits: utils_1.undefinedIfEmpty(limits), requests: utils_1.undefinedIfEmpty(requests), }; } const env = this.env._toKube(); return { name: this.name, image: this.image, imagePullPolicy: this.imagePullPolicy, ports: utils_1.undefinedIfEmpty(ports), volumeMounts: utils_1.undefinedIfEmpty(volumeMounts), command: this.command, args: this.args, workingDir: this.workingDir, env: env.variables, envFrom: env.from, readinessProbe: this._readiness?._toKube(this), livenessProbe: this._liveness?._toKube(this), startupProbe: this._startup?._toKube(this), lifecycle: this._lifecycle ? { postStart: this._lifecycle.postStart?._toKube(this), preStop: this._lifecycle.preStop?._toKube(this), } : undefined, resources: resourceRequirements, securityContext: this.securityContext._toKube(), }; } } exports.Container = Container; _c = JSII_RTTI_SYMBOL_1; Container[_c] = { fqn: "cdk8s-plus-25.Container", version: "2.22.79" }; var MountPropagation; (function (MountPropagation) { /** * This volume mount will not receive any subsequent mounts that are mounted * to this volume or any of its subdirectories by the host. In similar * fashion, no mounts created by the Container will be visible on the host. * * This is the default mode. * * This mode is equal to `private` mount propagation as described in the Linux * kernel documentation */ MountPropagation["NONE"] = "None"; /** * This volume mount will receive all subsequent mounts that are mounted to * this volume or any of its subdirectories. * * In other words, if the host mounts anything inside the volume mount, the * Container will see it mounted there. * * Similarly, if any Pod with Bidirectional mount propagation to the same * volume mounts anything there, the Container with HostToContainer mount * propagation will see it. * * This mode is equal to `rslave` mount propagation as described in the Linux * kernel documentation */ MountPropagation["HOST_TO_CONTAINER"] = "HostToContainer"; /** * This volume mount behaves the same the HostToContainer mount. In addition, * all volume mounts created by the Container will be propagated back to the * host and to all Containers of all Pods that use the same volume * * A typical use case for this mode is a Pod with a FlexVolume or CSI driver * or a Pod that needs to mount something on the host using a hostPath volume. * * This mode is equal to `rshared` mount propagation as described in the Linux * kernel documentation * * Caution: Bidirectional mount propagation can be dangerous. It can damage * the host operating system and therefore it is allowed only in privileged * Containers. Familiarity with Linux kernel behavior is strongly recommended. * In addition, any volume mounts created by Containers in Pods must be * destroyed (unmounted) by the Containers on termination. * */ MountPropagation["BIDIRECTIONAL"] = "Bidirectional"; })(MountPropagation = exports.MountPropagation || (exports.MountPropagation = {})); /** * Represents the amount of CPU. * The amount can be passed as millis or units. */ class Cpu { constructor(amount) { this.amount = amount; } static millis(amount) { return new Cpu(amount + 'm'); } static units(amount) { return new Cpu(amount.toString()); } } exports.Cpu = Cpu; _d = JSII_RTTI_SYMBOL_1; Cpu[_d] = { fqn: "cdk8s-plus-25.Cpu", version: "2.22.79" }; /** * A collection of env variables defined in other resources. */ class EnvFrom { constructor(configMap, prefix, sec) { this.configMap = configMap; this.prefix = prefix; this.sec = sec; } ; /** * @internal */ _toKube() { return { configMapRef: this.configMap ? { name: this.configMap.name, } : undefined, secretRef: this.sec ? { name: this.sec.name, } : undefined, prefix: this.prefix, }; } } exports.EnvFrom = EnvFrom; _e = JSII_RTTI_SYMBOL_1; EnvFrom[_e] = { fqn: "cdk8s-plus-25.EnvFrom", version: "2.22.79" }; function extractContainerPorts(selector) { if (!selector) { return []; } // we don't use instanceof intentionally since it can create // cyclic import problems. const containers = selector.containers ?? []; return containers.flatMap(c => c.ports); } exports.extractContainerPorts = extractContainerPorts; /** * Container environment variables. */ class Env { constructor(sources, variables) { this._sources = sources; this._variables = variables; } /** * Selects a ConfigMap to populate the environment variables with. * The contents of the target ConfigMap's Data field will represent * the key-value pairs as environment variables. */ static fromConfigMap(configMap, prefix) { return new EnvFrom(configMap, prefix, undefined); } /** * Selects a Secret to populate the environment variables with. * The contents of the target Secret's Data field will represent * the key-value pairs as environment variables. */ static fromSecret(secr) { return new EnvFrom(undefined, undefined, secr); } /** * Add a single variable by name and value. * The variable value can come from various dynamic sources such a secrets of config maps. * Use `EnvValue.fromXXX` to select sources. */ addVariable(name, value) { this._variables[name] = value; } /** * The environment variables for this container. * Returns a copy. To add environment variables use `container.env.addVariable()`. */ get variables() { return { ...this._variables }; } /** * Add a collection of variables by copying from another source. * Use `Env.fromXXX` functions to select sources. */ copyFrom(from) { this._sources.push(from); } /** * The list of sources used to populate the container environment, * in addition to the `variables`. * * Returns a copy. To add a source use `container.env.copyFrom()`. */ get sources() { return [...this._sources]; } renderEnv(env) { const result = new Array(); for (const [name, v] of Object.entries(env)) { result.push({ name, value: v.value, valueFrom: v.valueFrom, }); } return result; } /** * @internal */ _toKube() { return { from: utils_1.undefinedIfEmpty(this._sources.map(s => s._toKube())), variables: utils_1.undefinedIfEmpty(this.renderEnv(this._variables)), }; } } exports.Env = Env; _f = JSII_RTTI_SYMBOL_1; Env[_f] = { fqn: "cdk8s-plus-25.Env", version: "2.22.79" }; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY29udGFpbmVyLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vc3JjL2NvbnRhaW5lci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7OztBQUFBLGlDQUE2QjtBQUc3QixxQ0FBcUM7QUFDckMsaUNBQWlDO0FBRWpDLG1DQUEyQztBQW9HM0M7O0dBRUc7QUFDSCxJQUFZLFFBZ0JYO0FBaEJELFdBQVksUUFBUTtJQUVsQjs7T0FFRztJQUNILHVCQUFXLENBQUE7SUFFWDs7T0FFRztJQUNILHVCQUFXLENBQUE7SUFFWDs7T0FFRztJQUNILHlCQUFhLENBQUE7QUFDZixDQUFDLEVBaEJXLFFBQVEsR0FBUixnQkFBUSxLQUFSLGdCQUFRLFFBZ0JuQjtBQUdEOztHQUVHO0FBQ0gsTUFBYSx3QkFBd0I7SUFTbkMsWUFBWSxRQUF1QyxFQUFFO1FBQ25ELElBQUksQ0FBQyxhQUFhLEdBQUcsS0FBSyxDQUFDLGFBQWEsSUFBSSxJQUFJLENBQUM7UUFDakQsSUFBSSxDQUFDLFVBQVUsR0FBRyxLQUFLLENBQUMsVUFBVSxJQUFJLEtBQUssQ0FBQztRQUM1QyxJQUFJLENBQUMsc0JBQXNCLEdBQUcsS0FBSyxDQUFDLHNCQUFzQixJQUFJLElBQUksQ0FBQztRQUNuRSxJQUFJLENBQUMsSUFBSSxHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUM7UUFDdkIsSUFBSSxDQUFDLEtBQUssR0FBRyxLQUFLLENBQUMsS0FBSyxDQUFDO1FBQ3pCLElBQUksQ0FBQyx3QkFBd0IsR0FBRyxLQUFLLENBQUMsd0JBQXdCLElBQUksS0FBSyxDQUFDO0lBQzFFLENBQUM7SUFFRDs7T0FFRztJQUNJLE9BQU87UUFDWixPQUFPO1lBQ0wsVUFBVSxFQUFFLElBQUksQ0FBQyxLQUFLO1lBQ3RCLFNBQVMsRUFBRSxJQUFJLENBQUMsSUFBSTtZQUNwQixZQUFZLEVBQUUsSUFBSSxDQUFDLGFBQWE7WUFDaEMsVUFBVSxFQUFFLElBQUksQ0FBQyxVQUFVO1lBQzNCLHNCQUFzQixFQUFFLElBQUksQ0FBQyxzQkFBc0I7WUFDbkQsd0JBQXdCLEVBQUUsSUFBSSxDQUFDLHdCQUF3QjtTQUN4RCxDQUFDO0lBQ0osQ0FBQzs7QUE5QkgsNERBZ0NDOzs7QUFFRCxJQUFZLGFBa0RYO0FBbERELFdBQVksYUFBYTtJQUN2Qjs7T0FFRztJQUNILDJDQUEwQixDQUFBO0lBRTFCOztPQUVHO0lBQ0gscURBQW9DLENBQUE7SUFFcEM7O09BRUc7SUFDSCx5Q0FBd0IsQ0FBQTtJQUV4Qjs7T0FFRztJQUNILDhDQUE2QixDQUFBO0lBRTdCOztPQUVHO0lBQ0gsd0RBQXVDLENBQUE7SUFFdkM7O09BRUc7SUFDSCx3Q0FBdUIsQ0FBQTtJQUV2Qjs7T0FFRztJQUNILGlFQUFnRCxDQUFBO0lBRWhEOztPQUVHO0lBQ0gsNENBQTJCLENBQUE7SUFFM0I7O09BRUc7SUFDSCwwQ0FBeUIsQ0FBQTtJQUV6Qjs7T0FFRztJQUNILDBDQUF5QixDQUFBO0FBQzNCLENBQUMsRUFsRFcsYUFBYSxHQUFiLHFCQUFhLEtBQWIscUJBQWEsUUFrRHhCO0FBRUQsSUFBWSxrQkE4Qlg7QUE5QkQsV0FBWSxrQkFBa0I7SUFDNUI7O09BRUc7SUFDSCw4Q0FBd0IsQ0FBQTtJQUV4Qjs7T0FFRztJQUNILG9EQUE4QixDQUFBO0lBRTlCOztPQUVHO0lBQ0gsa0RBQTRCLENBQUE7SUFFNUI7O09BRUc7SUFDSCx3REFBa0MsQ0FBQTtJQUVsQzs7T0FFRztJQUNILGdFQUEwQyxDQUFBO0lBRTFDOztPQUVHO0lBQ0gsb0VBQThDLENBQUE7QUFDaEQsQ0FBQyxFQTlCVyxrQkFBa0IsR0FBbEIsMEJBQWtCLEtBQWxCLDBCQUFrQixRQThCN0I7QUF5RUQ7O0dBRUc7QUFDSCxNQUFhLFFBQVE7SUErR25CLFlBQW9DLEtBQVcsRUFBa0IsU0FBZTtRQUE1QyxVQUFLLEdBQUwsS0FBSyxDQUFNO1FBQWtCLGNBQVMsR0FBVCxTQUFTLENBQU07SUFBRyxDQUFDO0lBN0dwRjs7Ozs7O09BTUc7SUFDSSxNQUFNLENBQUMsYUFBYSxDQUFDLFNBQStCLEVBQUUsR0FBVyxFQUFFLFVBQXdDLEVBQUc7UUFFbkgsTUFBTSxNQUFNLEdBQXFCO1lBQy9CLGVBQWUsRUFBRTtnQkFDZixJQUFJLEVBQUUsU0FBUyxDQUFDLElBQUk7Z0JBQ3BCLEdBQUc7Z0JBQ0gsUUFBUSxFQUFFLE9BQU8sQ0FBQyxRQUFRO2FBQzNCO1NBQ0YsQ0FBQztRQUNGLE9BQU8sSUFBSSxRQUFRLENBQUMsU0FBUyxFQUFFLE1BQU0sQ0FBQyxDQUFDO0lBQ3pDLENBQUM7SUFFRDs7Ozs7T0FLRztJQUNJLE1BQU0sQ0FBQyxlQUFlLENBQUMsV0FBK0IsRUFBRSxVQUFxQyxFQUFFO1FBQ3BHLE1BQU0sTUFBTSxHQUFxQjtZQUMvQixZQUFZLEVBQUU7Z0JBQ1osSUFBSSxFQUFFLFdBQVcsQ0FBQyxNQUFNLENBQUMsSUFBSTtnQkFDN0IsR0FBRyxFQUFFLFdBQVcsQ0FBQyxHQUFHO2dCQUNwQixRQUFRLEVBQUUsT0FBTyxDQUFDLFFBQVE7YUFDM0I7U0FDRixDQUFDO1FBRUYsT0FBTyxJQUFJLFFBQVEsQ0FBQyxTQUFTLEVBQUUsTUFBTSxDQUFDLENBQUM7SUFDekMsQ0FBQztJQUVEOzs7O09BSUc7SUFDSSxNQUFNLENBQUMsU0FBUyxDQUFDLEtBQWE7UUFDbkMsT0FBTyxJQUFJLFFBQVEsQ0FBQyxLQUFLLENBQUMsQ0FBQztJQUM3QixDQUFDO0lBRUQ7Ozs7OztPQU1HO0lBQ0ksTUFBTSxDQUFDLFlBQVksQ0FBQyxTQUF3QixFQUFFLFVBQXVDLEVBQUU7UUFDNUYsSUFBSSxRQUFRLEdBQVksS0FBSyxDQUFDO1FBRTlCLElBQUksU0FBUyxLQUFLLGFBQWEsQ0FBQyxTQUFTLElBQUksU0FBUyxLQUFLLGFBQWEsQ0FBQyxjQUFjLEVBQUU7WUFDdkYsUUFBUSxHQUFHLElBQUksQ0FBQztTQUNqQjtRQUVELElBQUksUUFBUSxJQUFJLE9BQU8sQ0FBQyxHQUFHLEtBQUssU0FBUyxFQUFFO1lBQ3pDLE1BQU0sSUFBSSxLQUFLLENBQUMsR0FBRyxTQUFTLGlCQUFpQixDQUFDLENBQUM7U0FDaEQ7UUFFRCxNQUFNLE1BQU0sR0FBcUI7WUFDL0IsUUFBUSxFQUFFO2dCQUNSLFNBQVMsRUFBRSxDQUFDLEdBQUcsU0FBUyxFQUFFLEdBQUcsQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDLEtBQUssT0FBTyxDQUFDLEdBQUcsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQztnQkFDcEUsR0FBRyxDQUFDLE9BQU8sQ0FBQyxVQUFVLENBQUMsQ0FBQyxDQUFDLEVBQUUsVUFBVSxFQUFFLE9BQU8sQ0FBQyxVQUFVLEVBQUUsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDO2FBQ2xFO1NBQ0YsQ0FBQztRQUVGLE9BQU8sSUFBSSxRQUFRLENBQUMsU0FBUyxFQUFFLE1BQU0sQ0FBQyxDQUFDO0lBQ3pDLENBQUM7SUFFRDs7Ozs7T0FLRztJQUNJLE1BQU0sQ0FBQyxZQUFZLENBQUMsUUFBNEIsRUFBRSxVQUF1QyxFQUFFO1FBQ2hHLE1BQU0sTUFBTSxHQUFxQjtZQUMvQixnQkFBZ0IsRUFBRTtnQkFDaEIsUUFBUSxFQUFFLEdBQUcsUUFBUSxFQUFFO2dCQUN2QixHQUFJLENBQUMsT0FBTyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsRUFBRSxPQUFPLEVBQUUsR0FBRyxDQUFDLFdBQVcsQ0FBQyxVQUFVLENBQUMsT0FBTyxDQUFDLE9BQU8sQ0FBQyxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQztnQkFDckYsR0FBSSxDQUFDLE9BQU8sQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDLEVBQUUsYUFBYSxFQUFFLE9BQU8sQ0FBQyxTQUFTLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQzthQUN6RTtTQUNGLENBQUM7UUFFRixPQUFPLElBQUksUUFBUSxDQUFDLFNBQVMsRUFBRSxNQUFNLENBQUMsQ0FBQztJQUN6QyxDQUFDO0lBRUQ7Ozs7O09BS0c7SUFDSSxNQUFNLENBQUMsV0FBVyxDQUFDLEdBQVcsRUFBRSxVQUFzQyxFQUFFO1FBRTdFLE1BQU0sS0FBSyxHQUFHLE9BQU8sQ0FBQyxHQUFHLENBQUMsR0FBRyxDQUFDLENBQUM7UUFFL0IsSUFBSSxPQUFPLENBQUMsUUFBUSxJQUFJLENBQUMsS0FBSyxFQUFFO1lBQzlCLE1BQU0sSUFBSSxLQUFLLENBQUMsV0FBVyxHQUFHLGVBQWUsQ0FBQyxDQUFDO1NBQ2hEO1FBRUQsT0FBTyxRQUFRLENBQUMsU0FBUyxDQUFDLEtBQU0sQ0FBQyxDQUFDO0lBQ3BDLENBQUM7O0FBN0dILDRCQWdIQzs7O0FBRUQsSUFBWSxlQXdCWDtBQXhCRCxXQUFZLGVBQWU7SUFDekI7Ozs7Ozs7O09BUUc7SUFDSCxvQ0FBaUIsQ0FBQTtJQUVqQjs7Ozs7T0FLRztJQUNILGtEQUErQixDQUFBO0lBRS9COztPQUVHO0lBQ0gsa0NBQWUsQ0FBQTtBQUNqQixDQUFDLEVBeEJXLGVBQWUsR0FBZix1QkFBZSxLQUFmLHVCQUFlLFFBd0IxQjtBQXlNRDs7R0FFRztBQUNILE1BQWEsU0FBUztJQTBEcEIsWUFBWSxLQUFxQjtRQU5oQixXQUFNLEdBQW9CLEVBQUUsQ0FBQztRQU81QyxJQUFJLEtBQUssWUFBWSxTQUFTLEVBQUU7WUFDOUIsTUFBTSxJQUFJLEtBQUssQ0FBQyw2REFBNkQsQ0FBQyxDQUFDO1NBQ2hGO1FBRUQsTUFBTSxtQkFBbUIsR0FBdUI7WUFDOUMsR0FBRyxFQUFFO2dCQUNILE9BQU8sRUFBRSxHQUFHLENBQUMsTUFBTSxDQUFDLElBQUksQ0FBQztnQkFDekIsS0FBSyxFQUFFLEdBQUcsQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDO2FBQ3hCO1lBQ0QsTUFBTSxFQUFFO2dCQUNOLE9BQU8sRUFBRSxZQUFJLENBQUMsU0FBUyxDQUFDLEdBQUcsQ0FBQztnQkFDNUIsS0FBSyxFQUFFLFlBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDO2FBQzVCO1NBQ0YsQ0FBQztRQUVGLElBQUksS0FBSyxDQUFDLElBQUksSUFBSSxLQUFLLENBQUMsVUFBVSxFQUFFO1lBQ2xDLE1BQU0sSUFBSSxLQUFLLENBQUMsK0ZBQStGLENBQUMsQ0FBQztTQUNsSDtRQUVELE1BQU0sVUFBVSxHQUFHLEtBQUssQ0FBQyxVQUFVLElBQUksS0FBSyxDQUFDLElBQUksQ0FBQztRQUNsRCxNQUFNLHlCQUF5QixHQUFnQixLQUFLLENBQUMsS0FBSyxDQUFDLGFBQWEsQ0FBQyxFQUFFLElBQUksRUFBRSxVQUFVLEVBQUUsQ0FBQyxDQUFDO1FBRS9GLElBQUksQ0FBQyxJQUFJLEdBQUcsS0FBSyxDQUFDLElBQUksSUFBSSxNQUFNLENBQUM7UUFDakMsSUFBSSxDQUFDLEtBQUssR0FBRyxLQUFLLENBQUMsS0FBSyxDQUFDO1FBQ3pCLElBQUksQ0FBQyxVQUFVLEdBQUcsVUFBVSxDQUFDO1FBQzdCLElBQUksQ0FBQyxRQUFRLEdBQUcsS0FBSyxDQUFDLE9BQU8sQ0FBQztRQUM5QixJQUFJLENBQUMsS0FBSyxHQUFHLEtBQUssQ0FBQyxJQUFJLENBQUM7UUFDeEIsSUFBSSxDQUFDLFVBQVUsR0FBRyxLQUFLLENBQUMsU0FBUyxDQUFDO1FBQ2xDLElBQUksQ0FBQyxTQUFTLEdBQUcsS0FBSyxDQUFDLFFBQVEsQ0FBQztRQUNoQyxJQUFJLENBQUMsUUFBUSxHQUFHLEtBQUssQ0FBQyxPQUFPLElBQUksQ0FBQyxJQUFJLENBQUMsVUFBVSxDQUFDLENBQUMsQ0FBQyx5QkFBeUIsQ0FBQyxDQUFDLENBQUMsU0FBUyxDQUFDLENBQUM7UUFDM0YsSUFBSSxDQUFDLFVBQVUsR0FBRyxLQUFLLENBQUMsU0FBUyxDQUFDO1FBQ2xDLElBQUksQ0FBQyxTQUFTLEdBQUcsS0FBSyxDQUFDLFNBQVMsSUFBSSxtQkFBbUIsQ0FBQztRQUN4RCxJQUFJLENBQUMsVUFBVSxHQUFHLEtBQUssQ0FBQyxVQUFVLENBQUM7UUFDbkMsSUFBSSxDQUFDLE1BQU0sR0FBRyxLQUFLLENBQUMsWUFBWSxJQUFJLEVBQUUsQ0FBQztRQUN2QyxJQUFJLENBQUMsZUFBZSxHQUFHLEtBQUssQ0FBQyxlQUFlLElBQUksZUFBZSxDQUFDLE1BQU0sQ0FBQztRQUN2RSxJQUFJLENBQUMsZUFBZSxHQUFHLElBQUksd0JBQXdCLENBQUMsS0FBSyxDQUFDLGVBQWUsQ0FBQyxDQUFDO1FBQzNFLElBQUksQ0FBQyxHQUFHLEdBQUcsSUFBSSxHQUFHLENBQUMsS0FBSyxDQUFDLE9BQU8sSUFBSSxFQUFFLEVBQUUsS0FBSyxDQUFDLFlBQVksSUFBSSxFQUFFLENBQUMsQ0FBQztRQUVsRSxJQUFJLElBQUksQ0FBQyxVQUFVLEVBQUU7WUFDbkIsSUFBSSxDQUFDLE9BQU8sQ0FBQztnQkFDWCxNQUFNLEVBQUUsSUFBSSxDQUFDLFVBQVU7YUFDeEIsQ0FBQyxDQUFDO1NBQ0o7UUFFRCxLQUFLLE1BQU0sSUFBSSxJQUFJLEtBQUssQ0FBQyxLQUFLLElBQUksRUFBRSxFQUFFO1lBQ3BDLElBQUksQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLENBQUM7U0FDcEI7SUFDSCxDQUFDO0lBRUQ7O09BRUc7SUFDSCxJQUFXLElBQUk7UUFDYixPQUFPLElBQUksQ0FBQyxVQUFVLENBQUM7SUFDekIsQ0FBQztJQUVEOzs7T0FHRztJQUNILElBQVcsS0FBSztRQUNkLE9BQU8sQ0FBQyxHQUFHLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQztJQUMxQixDQUFDO0lBRUQ7OztPQUdHO0lBQ0gsSUFBVyxPQUFPO1FBQ2hCLE9BQU8sSUFBSSxDQUFDLFFBQVEsQ0FBQyxDQUFDLENBQUMsQ0FBQyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQyxDQUFDLENBQUMsU0FBUyxDQUFDO0lBQ3hELENBQUM7SUFFRDs7OztPQUlHO0lBQ0gsSUFBVyxJQUFJO1FBQ2IsT0FBTyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLEdBQUcsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQyxTQUFTLENBQUM7SUFDbEQsQ0FBQztJQUVEOzs7Ozs7T0FNRztJQUNJLEtBQUssQ0FBQyxJQUFZLEVBQUUsT0FBd0IsRUFBRSxVQUF3QixFQUFHO1FBQzlFLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLEVBQUUsSUFBSSxFQUFFLE1BQU0sRUFBRSxPQUFPLENBQUMsUUFBUSxFQUFFLEVBQUUsR0FBRyxPQUFPLEVBQUUsQ0FBQyxDQUFDO0lBQ3JFLENBQUM7SUFFRDs7T0FFRztJQUNJLE9BQU8sQ0FBQyxJQUFtQjtRQUVoQyxNQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsQ0FBQztRQUMxRCxNQUFNLE9BQU8sR0FBRyxJQUFJLENBQUMsTUFBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUUvQyxJQUFJLElBQUksQ0FBQyxJQUFJLElBQUksS0FBSyxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLEVBQUU7WUFDMUMsTUFBTSxJQUFJLEtBQUssQ0FBQyxrQkFBa0IsSUFBSSxDQUFDLElBQUksaUJBQWlCLENBQUMsQ0FBQztTQUMvRDtRQUVELElBQUksT0FBTyxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLEVBQUU7WUFDakMsTUFBTSxJQUFJLEtBQUssQ0FBQyxvQkFBb0IsSUFBSSxDQUFDLE1BQU0saUJBQWlCLENBQUMsQ0FBQztTQUNuRTtRQUVELElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxDQUFDO0lBQ3pCLENBQUM7SUFFRDs7T0FFRztJQUNJLE9BQU87UUFDWixNQUFNLFlBQVksR0FBc0IsRUFBRSxDQUFDO1FBRTNDLEtBQUssTUFBTSxLQUFLLElBQUksSUFBSSxDQUFDLE1BQU0sRUFBRTtZQUMvQixZQUFZLENBQUMsSUFBSSxDQUFDO2dCQUNoQixJQUFJLEVBQUUsS0FBSyxDQUFDLE1BQU0sQ0FBQyxJQUFJO2dCQUN2QixTQUFTLEVBQUUsS0FBSyxDQUFDLElBQUk7Z0JBQ3JCLFFBQVEsRUFBRSxLQUFLLENBQUMsUUFBUTtnQkFDeEIsZ0JBQWdCLEVBQUUsS0FBSyxDQUFDLFdBQVc7Z0JBQ25DLE9BQU8sRUFBRSxLQUFLLENBQUMsT0FBTztnQkFDdEIsV0FBVyxFQUFFLEtBQUssQ0FBQyxXQUFXO2FBQy9CLENBQUMsQ0FBQztTQUNKO1FBRUQsTUFBTSxLQUFLLEdBQUcsSUFBSSxLQUFLLEVBQXFCLENBQUM7UUFFN0MsS0FBSyxNQUFNLElBQUksSUFBSSxJQUFJLENBQUMsS0FBSyxFQUFFO1lBQzdCLEtBQUssQ0FBQyxJQUFJLENBQUM7Z0JBQ1QsYUFBYSxFQUFFLElBQUksQ0FBQyxNQUFNO2dCQUMxQixRQUFRLEVBQUUsSUFBSSxDQUFDLFFBQVEsRUFBRSxRQUFRLEVBQUU7Z0JBQ25DLElBQUksRUFBRSxJQUFJLENBQUMsSUFBSTtnQkFDZixRQUFRLEVBQUUsSUFBSSxDQUFDLFFBQVE7Z0JBQ3ZCLE1BQU0sRUFBRSxJQUFJLENBQUMsTUFBTTthQUNwQixDQUFDLENBQUM7U0FDSjtRQUVELCtCQUErQjtRQUMvQixNQUFNLFFBQVEsR0FBRyxJQUFJLENBQUMsU0FBUyxFQUFFLEdBQUcsRUFBRSxLQUFLLEVBQUUsTUFBTSxDQUFDO1FBQ3BELE1BQU0sVUFBVSxHQUFHLElBQUksQ0FBQyxTQUFTLEVBQUUsR0FBRyxFQUFFLE9BQU8sRUFBRSxNQUFNLENBQUM7UUFDeEQsTUFBTSxXQUFXLEdBQUcsSUFBSSxDQUFDLFNBQVMsRUFBRSxNQUFNLEVBQUUsS0FBSyxDQUFDO1FBQ2xELE1BQU0sYUFBYSxHQUFHLElBQUksQ0FBQyxTQUFTLEVBQUUsTUFBTSxFQUFFLE9BQU8sQ0FBQztRQUN0RCxNQUFNLHFCQUFxQixHQUFHLElBQUksQ0FBQyxTQUFTLEVBQUUsZ0JBQWdCLEVBQUUsS0FBSyxDQUFDO1FBQ3RFLE1BQU0sdUJBQXVCLEdBQUcsSUFBSSxDQUFDLFNBQVMsRUFBRSxnQkFBZ0IsRUFBRSxPQUFPLENBQUM7UUFFMUUsTUFBTSxNQUFNLEdBQW9DLEVBQUUsQ0FBQztRQUNuRCxNQUFNLFFBQVEsR0FBb0MsRUFBRSxDQUFDO1FBRXJELElBQUksUUFBUSxFQUFFO1lBQ1osTUFBTSxDQUFDLEdBQUcsR0FBRyxHQUFHLENBQUMsUUFBUSxDQUFDLFVBQVUsQ0FBQyxRQUFRLENBQUMsQ0FBQztTQUNoRDtRQUNELElBQUksV0FBVyxFQUFFO1lBQ2YsTUFBTSxDQUFDLE1BQU0sR0FBRyxHQUFHLENBQUMsUUFBUSxDQUFDLFVBQVUsQ0FBQyxXQUFXLENBQUMsV0FBVyxFQUFFLENBQUMsUUFBUSxFQUFFLEdBQUcsSUFBSSxDQUFDLENBQUM7U0FDdEY7UUFDRCxJQUFJLHFCQUFxQixFQUFFO1lBQ3pCLE1BQU0sQ0FBQyxtQkFBbUIsQ0FBQyxHQUFHLEdBQUcsQ0FBQyxRQUFRLENBQUMsVUFBVSxDQUFDLHFCQUFxQixDQUFDLFdBQVcsRUFBRSxDQUFDLFFBQVEsRUFBRSxHQUFHLElBQUksQ0FBQyxDQUFDO1NBQzlHO1FBQ0QsSUFBSSxVQUFVLEVBQUU7WUFDZCxRQUFRLENBQUMsR0FBRyxHQUFHLEdBQUcsQ0FBQyxRQUFRLENBQUMsVUFBVSxDQUFDLFVBQVUsQ0FBQyxDQUFDO1NBQ3BEO1FBQ0QsSUFBSSxhQUFhLEVBQUU7WUFDakIsUUFBUSxDQUFDLE1BQU0sR0FBRyxHQUFHLENBQUMsUUFBUSxDQUFDLFVBQVUsQ0FBQyxhQUFhLENBQUMsV0FBVyxFQUFFLENBQUMsUUFBUSxFQUFFLEdBQUcsSUFBSSxDQUFDLENBQUM7U0FDMUY7UUFDRCxJQUFJLHVCQUF1QixFQUFFO1lBQzNCLFFBQVEsQ0FBQyxtQkFBbUIsQ0FBQyxHQUFHLEdBQUcsQ0FBQyxRQUFRLENBQUMsVUFBVSxDQUFDLHVCQUF1QixDQUFDLFdBQVcsRUFBRSxDQUFDLFFBQVEsRUFBRSxHQUFHLElBQUksQ0FBQyxDQUFDO1NBQ2xIO1FBRUQsSUFBSSxvQkFBb0IsR0FBeUMsU0FBUyxDQUFDO1FBQzNFLElBQUksTUFBTSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsQ0FBQyxNQUFNLEdBQUcsQ0FBQyxJQUFJLE1BQU0sQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUMsTUFBTSxHQUFHLENBQUMsRUFBRTtZQUN0RSxvQkFBb0IsR0FBRztnQkFDckIsTUFBTSxFQUFFLHdCQUFnQixDQUFDLE1BQU0sQ0FBQztnQkFDaEMsUUFBUSxFQUFFLHdCQUFnQixDQUFDLFFBQVEsQ0FBQzthQUNyQyxDQUFDO1NBQ0g7UUFFRCxNQUFNLEdBQUcsR0FBRyxJQUFJLENBQUMsR0FBRyxDQUFDLE9BQU8sRUFBRSxDQUFDO1FBRS9CLE9BQU87WUFDTCxJQUFJLEVBQUUsSUFBSSxDQUFDLElBQUk7WUFDZixLQUFLLEVBQUUsSUFBSSxDQUFDLEtBQUs7WUFDakIsZUFBZSxFQUFFLElBQUksQ0FBQyxlQUFlO1lBQ3JDLEtBQUssRUFBRSx3QkFBZ0IsQ0FBQyxLQUFLLENBQUM7WUFDOUIsWUFBWSxFQUFFLHdCQUFnQixDQUFDLFlBQVksQ0FBQztZQUM1QyxPQUFPLEVBQUUsSUFBSSxDQUFDLE9BQU87WUFDckIsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJO1lBQ2YsVUFBVSxFQUFFLElBQUksQ0FBQyxVQUFVO1lBQzNCLEdBQUcsRUFBRSxHQUFHLENBQUMsU0FBUztZQUNsQixPQUFPLEVBQUUsR0FBRyxDQUFDLElBQUk7WUFDakIsY0FBYyxFQUFFLElBQUksQ0FBQyxVQUFVLEVBQUUsT0FBTyxDQUFDLElBQUksQ0FBQztZQUM5QyxhQUFhLEVBQUUsSUFBSSxDQUFDLFNBQVMsRUFBRSxPQUFPLENBQUMsSUFBSSxDQUFDO1lBQzVDLFlBQVksRUFBRSxJQUFJLENBQUMsUUFBUSxFQUFFLE9BQU8sQ0FBQyxJQUFJLENBQUM7WUFDMUMsU0FBUyxFQUFFLElBQUksQ0FBQyxVQUFVLENBQUMsQ0FBQyxDQUFDO2dCQUMzQixTQUFTLEVBQUUsSUFBSSxDQUFDLFVBQVUsQ0FBQyxTQUFTLEVBQUUsT0FBTyxDQUFDLElBQUksQ0FBQztnQkFDbkQsT0FBTyxFQUFFLElBQUksQ0FBQyxVQUFVLENBQUMsT0FBTyxFQUFFLE9BQU8sQ0FBQyxJQUFJLENBQUM7YUFDaEQsQ0FBQyxDQUFDLENBQUMsU0FBUztZQUNiLFNBQVMsRUFBRSxvQkFBb0I7WUFDL0IsZUFBZSxFQUFFLElBQUksQ0FBQyxlQUFlLENBQUMsT0FBTyxFQUFFO1NBQ2hELENBQUM7SUFDSixDQUFDOztBQXBRSCw4QkFxUUM7OztBQTZERCxJQUFZLGdCQWdEWDtBQWhERCxXQUFZLGdCQUFnQjtJQUMxQjs7Ozs7Ozs7O09BU0c7SUFDSCxpQ0FBYSxDQUFBO0lBRWI7Ozs7Ozs7Ozs7Ozs7T0FhRztJQUNILHlEQUFxQyxDQUFBO0lBRXJDOzs7Ozs7Ozs7Ozs7Ozs7OztPQWlCRztJQUNILG1EQUErQixDQUFBO0FBQ2pDLENBQUMsRUFoRFcsZ0JBQWdCLEdBQWhCLHdCQUFnQixLQUFoQix3QkFBZ0IsUUFnRDNCO0FBbUJEOzs7R0FHRztBQUNILE1BQWEsR0FBRztJQVFkLFlBQW9CLE1BQWM7UUFDaEMsSUFBSSxDQUFDLE1BQU0sR0FBRyxNQUFNLENBQUM7SUFDdkIsQ0FBQztJQVRELE1BQU0sQ0FBQyxNQUFNLENBQUMsTUFBYztRQUMxQixPQUFPLElBQUksR0FBRyxDQUFDLE1BQU0sR0FBRyxHQUFHLENBQUMsQ0FBQztJQUMvQixDQUFDO0lBQ0QsTUFBTSxDQUFDLEtBQUssQ0FBQyxNQUFjO1FBQ3pCLE9BQU8sSUFBSSxHQUFHLENBQUMsTUFBTSxDQUFDLFFBQVEsRUFBRSxDQUFDLENBQUM7SUFDcEMsQ0FBQzs7QUFOSCxrQkFXQzs7O0FBa0JEOztHQUVHO0FBQ0gsTUFBYSxPQUFPO0lBRWxCLFlBQ21CLFNBQWdDLEVBQ2hDLE1BQWUsRUFDZixHQUFvQjtRQUZwQixjQUFTLEdBQVQsU0FBUyxDQUF1QjtRQUNoQyxXQUFNLEdBQU4sTUFBTSxDQUFTO1FBQ2YsUUFBRyxHQUFILEdBQUcsQ0FBaUI7SUFBRyxDQUFDO0lBQUEsQ0FBQztJQUU1Qzs7T0FFRztJQUNJLE9BQU87UUFDWixPQUFPO1lBQ0wsWUFBWSxFQUFFLElBQUksQ0FBQyxTQUFTLENBQUMsQ0FBQyxDQUFDO2dCQUM3QixJQUFJLEVBQUUsSUFBSSxDQUFDLFNBQVMsQ0FBQyxJQUFJO2FBQzFCLENBQUMsQ0FBQyxDQUFDLFNBQVM7WUFDYixTQUFTLEVBQUUsSUFBSSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUM7Z0JBQ3BCLElBQUksRUFBRSxJQUFJLENBQUMsR0FBRyxDQUFDLElBQUk7YUFDcEIsQ0FBQyxDQUFDLENBQUMsU0FBUztZQUNiLE1BQU0sRUFBRSxJQUFJLENBQUMsTUFBTTtTQUNwQixDQUFDO0lBQ0osQ0FBQzs7QUFwQkgsMEJBc0JDOzs7QUFFRCxTQUFnQixxQkFBcUIsQ0FBQyxRQUFjO0lBRWxELElBQUksQ0FBQyxRQUFRLEVBQUU7UUFBRSxPQUFPLEVBQUUsQ0FBQztLQUFFO0lBRTdCLDREQUE0RDtJQUM1RCwwQkFBMEI7SUFDMUIsTUFBTSxVQUFVLEdBQWlCLFFBQWdCLENBQUMsVUFBVSxJQUFJLEVBQUUsQ0FBQztJQUVuRSxPQUFPLFVBQVUsQ0FBQyxPQUFPLENBQUMsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUMsS0FBSyxDQUFDLENBQUM7QUFDMUMsQ0FBQztBQVRELHNEQVNDO0FBRUQ7O0dBRUc7QUFDSCxNQUFhLEdBQUc7SUF1QmQsWUFBbUIsT0FBa0IsRUFBRSxTQUF1QztRQUM1RSxJQUFJLENBQUMsUUFBUSxHQUFHLE9BQU8sQ0FBQztRQUN4QixJQUFJLENBQUMsVUFBVSxHQUFHLFNBQVMsQ0FBQztJQUM5QixDQUFDO0lBeEJEOzs7O09BSUc7SUFDSSxNQUFNLENBQUMsYUFBYSxDQUFDLFNBQStCLEVBQUUsTUFBZTtRQUMxRSxPQUFPLElBQUksT0FBTyxDQUFDLFNBQVMsRUFBRSxNQUFNLEVBQUUsU0FBUyxDQUFDLENBQUM7SUFDbkQsQ0FBQztJQUVEOzs7O09BSUc7SUFDSSxNQUFNLENBQUMsVUFBVSxDQUFDLElBQW9CO1FBQzNDLE9BQU8sSUFBSSxPQUFPLENBQUMsU0FBUyxFQUFFLFNBQVMsRUFBRSxJQUFJLENBQUMsQ0FBQztJQUNqRCxDQUFDO0lBVUQ7Ozs7T0FJRztJQUNJLFdBQVcsQ0FBQyxJQUFZLEVBQUUsS0FBZTtRQUM5QyxJQUFJLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxHQUFHLEtBQUssQ0FBQztJQUNoQyxDQUFDO0lBRUQ7OztPQUdHO0lBQ0gsSUFBVyxTQUFTO1FBQ2xCLE9BQU8sRUFBRSxHQUFHLElBQUksQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNoQyxDQUFDO0lBRUQ7OztPQUdHO0lBQ0ksUUFBUSxDQUFDLElBQWE7UUFDM0IsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7SUFDM0IsQ0FBQztJQUVEOzs7OztPQUtHO0lBQ0gsSUFBVyxPQUFPO1FBQ2hCLE9BQU8sQ0FBQyxHQUFHLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQztJQUM1QixDQUFDO0lBRU8sU0FBUyxDQUFDLEdBQWlDO1FBQ2pELE1BQU0sTUFBTSxHQUFHLElBQUksS0FBSyxFQUFjLENBQUM7UUFDdkMsS0FBSyxNQUFNLENBQUMsSUFBSSxFQUFFLENBQUMsQ0FBQyxJQUFJLE1BQU0sQ0FBQyxPQUFPLENBQUMsR0FBRyxDQUFDLEVBQUU7WUFDM0MsTUFBTSxDQUFDLElBQUksQ0FBQztnQkFDVixJQUFJO2dCQUNKLEtBQUssRUFBRSxDQUFDLENBQUMsS0FBSztnQkFDZCxTQUFTLEVBQUUsQ0FBQyxDQUFDLFNBQVM7YUFDdkIsQ0FBQyxDQUFDO1NBQ0o7UUFDRCxPQUFPLE1BQU0sQ0FBQztJQUNoQixDQUFDO0lBRUQ7O09BRUc7SUFDSSxPQUFPO1FBQ1osT0FBTztZQUNMLElBQUksRUFBRSx3QkFBZ0IsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsRUFBRSxDQUFDLENBQUMsQ0FBQyxPQUFPLEVBQUUsQ0FBQyxDQUFDO1lBQzNELFNBQVMsRUFBRSx3QkFBZ0IsQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsQ0FBQztTQUM3RCxDQUFDO0lBQ0osQ0FBQzs7QUFuRkgsa0JBb0ZDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgU2l6ZSB9IGZyb20gJ2NkazhzJztcbmltcG9ydCAqIGFzIGNvbmZpZ21hcCBmcm9tICcuL2NvbmZpZy1tYXAnO1xuaW1wb3J0ICogYXMgaGFuZGxlciBmcm9tICcuL2hhbmRsZXInO1xuaW1wb3J0ICogYXMgazhzIGZyb20gJy4vaW1wb3J0cy9rOHMnO1xuaW1wb3J0ICogYXMgcHJvYmUgZnJvbSAnLi9wcm9iZSc7XG5pbXBvcnQgKiBhcyBzZWNyZXQgZnJvbSAnLi9zZWNyZXQnO1xuaW1wb3J0IHsgdW5kZWZpbmVkSWZFbXB0eSB9IGZyb20gJy4vdXRpbHMnO1xuaW1wb3J0ICogYXMgdm9sdW1lIGZyb20gJy4vdm9sdW1lJztcblxuLyoqXG4gKiBQcm9wZXJ0aWVzIGZvciBgQ29udGFpbmVyU2VjdXJpdHlDb250ZXh0YFxuICovXG5leHBvcnQgaW50ZXJmYWNlIENvbnRhaW5lclNlY3VyaXR5Q29udGV4dFByb3BzIHtcblxuICAvKipcbiAgICAqIFRoZSBVSUQgdG8gcnVuIHRoZSBlbnRyeXBvaW50IG9mIHRoZSBjb250YWluZXIgcHJvY2Vzcy5cbiAgICAqXG4gICAgKiBAZGVmYXVsdCAtIDI1MDAwLiBBbiBhcmJpdHJhcnkgbnVtYmVyIGJpZ2dlciB0aGFuIDk5OTkgaXMgc2VsZWN0ZWQgaGVyZS5cbiAgICAqIFRoaXMgaXMgc28gdGhhdCB0aGUgY29udGFpbmVyIGlzIGJsb2NrZWQgdG8gYWNjZXNzIGhvc3QgZmlsZXMgZXZlbiBpZlxuICAgICogc29tZWhvdyBpdCBtYW5hZ2VzIHRvIGdldCBhY2Nlc3MgdG8gaG9zdCBmaWxlIHN5c3RlbS5cbiAgICAqL1xuICByZWFkb25seSB1c2VyPzogbnVtYmVyO1xuXG4gIC8qKlxuICAgICogVGhlIEdJRCB0byBydW4gdGhlIGVudHJ5cG9pbnQgb2YgdGhlIGNvbnRhaW5lciBwcm9jZXNzLlxuICAgICpcbiAgICAqIEBkZWZhdWx0IC0gMjYwMDAuIEFuIGFyYml0cmFyeSBudW1iZXIgYmlnZ2VyIHRoYW4gOTk5OSBpcyBzZWxlY3RlZCBoZXJlLlxuICAgICogVGhpcyBpcyBzbyB0aGF0IHRoZSBjb250YWluZXIgaXMgYmxvY2tlZCB0byBhY2Nlc3MgaG9zdCBmaWxlcyBldmVuIGlmXG4gICAgKiBzb21laG93IGl0IG1hbmFnZXMgdG8gZ2V0IGFjY2VzcyB0byBob3N0IGZpbGUgc3lzdGVtLlxuICAgICovXG4gIHJlYWRvbmx5IGdyb3VwPzogbnVtYmVyO1xuXG4gIC8qKlxuICAgICogSW5kaWNhdGVzIHRoYXQgdGhlIGNvbnRhaW5lciBtdXN0IHJ1biBhcyBhIG5vbi1yb290IHVzZXIuXG4gICAgKiBJZiB0cnVlLCB0aGUgS3ViZWxldCB3aWxsIHZhbGlkYXRlIHRoZSBpbWFnZSBhdCBydW50aW1lIHRvIGVuc3VyZSB0aGF0IGl0IGRvZXNcbiAgICAqIG5vdCBydW4gYXMgVUlEIDAgKHJvb3QpIGFuZCBmYWlsIHRvIHN0YXJ0IHRoZSBjb250YWluZXIgaWYgaXQgZG9lcy5cbiAgICAqXG4gICAgKiBAZGVmYXVsdCB0cnVlXG4gICAgKi9cbiAgcmVhZG9ubHkgZW5zdXJlTm9uUm9vdD86IGJvb2xlYW47XG5cbiAgLyoqXG4gICAqIFJ1biBjb250YWluZXIgaW4gcHJpdmlsZWdlZCBtb2RlLiBQcm9jZXNzZXMgaW4gcHJpdmlsZWdlZCBjb250YWluZXJzIGFyZSBlc3NlbnRpYWxseSBlcXVpdmFsZW50IHRvIHJvb3Qgb24gdGhlIGhvc3QuXG4gICAqXG4gICAqIEBkZWZhdWx0IGZhbHNlXG4gICAqL1xuICByZWFkb25seSBwcml2aWxlZ2VkPzogYm9vbGVhbjtcblxuICAvKipcbiAgICogV2hldGhlciB0aGlzIGNvbnRhaW5lciBoYXMgYSByZWFkLW9ubHkgcm9vdCBmaWxlc3lzdGVtLlxuICAgKlxuICAgKiBAZGVmYXVsdCB0cnVlXG4gICAqL1xuICByZWFkb25seSByZWFkT25seVJvb3RGaWxlc3lzdGVtPzogYm9vbGVhbjtcblxuICAvKipcbiAgICogV2hldGhlciBhIHByb2Nlc3MgY2FuIGdhaW4gbW9yZSBwcml2aWxlZ2VzIHRoYW4gaXRzIHBhcmVudCBwcm9jZXNzLlxuICAgKlxuICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgKi9cbiAgcmVhZG9ubHkgYWxsb3dQcml2aWxlZ2VFc2NhbGF0aW9uPzogYm9vbGVhbjtcbn1cblxuLyoqXG4gKiBSZXByZXNlbnRzIGEgbmV0d29yayBwb3J0IGluIGEgc2luZ2xlIGNvbnRhaW5lci5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBDb250YWluZXJQb3J0IHtcblxuICAvKipcbiAgICogTnVtYmVyIG9mIHBvcnQgdG8gZXhwb3NlIG9uIHRoZSBwb2QncyBJUCBhZGRyZXNzLiBUaGlzIG11c3QgYmUgYSB2YWxpZCBwb3J0IG51bWJlciwgMCA8IHggPCA2NTUzNi5cbiAgICovXG4gIHJlYWRvbmx5IG51bWJlcjogbnVtYmVyO1xuXG4gIC8qKlxuICAgKiBXaGF0IGhvc3QgSVAgdG8gYmluZCB0aGUgZXh0ZXJuYWwgcG9ydCB0by5cbiAgICpcbiAgICogQGRlZmF1bHQgLSAxMjcuMC4wLjEuXG4gICAqL1xuICByZWFkb25seSBob3N0SXA/OiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIE51bWJlciBvZiBwb3J0IHRvIGV4cG9zZSBvbiB0aGUgaG9zdC4gSWYgc3BlY2lmaWVkLCB0aGlzIG11c3QgYmUgYSB2YWxpZCBwb3J0IG51bWJlciwgMCA8IHggPCA2NTUzNi5cbiAgICogTW9zdCBjb250YWluZXJzIGRvIG5vdCBuZWVkIHRoaXMuXG4gICAqXG4gICAqIEBkZWZhdWx0IC0gYXV0byBnZW5lcmF0ZWQgYnkga3ViZXJuZXRlcyBhbmQgbWlnaHQgY2hhbmdlIG9uIHJlc3RhcnRzLlxuICAgKi9cbiAgcmVhZG9ubHkgaG9zdFBvcnQ/OiBudW1iZXI7XG5cbiAgLyoqXG4gICAqIElmIHNwZWNpZmllZCwgdGhpcyBtdXN0IGJlIGFuIElBTkFfU1ZDX05BTUUgYW5kIHVuaXF1ZSB3aXRoaW4gdGhlIHBvZC5cbiAgICogRWFjaCBuYW1lZCBwb3J0IGluIGEgcG9kIG11c3QgaGF2ZSBhIHVuaXF1ZSBuYW1lLlxuICAgKiBOYW1lIGZvciB0aGUgcG9ydCB0aGF0IGNhbiBiZSByZWZlcnJlZCB0byBieSBzZXJ2aWNlcy5cbiAgICpcbiAgICogQGRlZmF1bHQgLSBwb3J0IGlzIG5vdCBuYW1lZC5cbiAgICovXG4gIHJlYWRvbmx5IG5hbWU/OiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIFByb3RvY29sIGZvciBwb3J0LiBNdXN0IGJlIFVEUCwgVENQLCBvciBTQ1RQLiBEZWZhdWx0cyB0byBcIlRDUFwiLlxuICAgKlxuICAgKiBAZGVmYXVsdCBQcm90b2NvbC5UQ1BcbiAgICovXG4gIHJlYWRvbmx5IHByb3RvY29sPzogUHJvdG9jb2w7XG5cbn1cblxuLyoqXG4gKiBOZXR3b3JrIHByb3RvY29scy5cbiAqL1xuZXhwb3J0IGVudW0gUHJvdG9jb2wge1xuXG4gIC8qKlxuICAgKiBUQ1AuXG4gICAqL1xuICBUQ1AgPSAnVENQJyxcblxuICAvKipcbiAgICogVURQLlxuICAgKi9cbiAgVURQID0gJ1VEUCcsXG5cbiAgLyoqXG4gICAqIFNDVFAuXG4gICAqL1xuICBTQ1RQID0gJ1NDVFAnXG59XG5cblxuLyoqXG4gKiBDb250YWluZXIgc2VjdXJpdHkgYXR0cmlidXRlcyBhbmQgc2V0dGluZ3MuXG4gKi9cbmV4cG9ydCBjbGFzcyBDb250YWluZXJTZWN1cml0eUNvbnRleHQge1xuXG4gIHB1YmxpYyByZWFkb25seSBlbnN1cmVOb25Sb290OiBib29sZWFuO1xuICBwdWJsaWMgcmVhZG9ubHkgcHJpdmlsZWdlZDogYm9vbGVhbjtcbiAgcHVibGljIHJlYWRvbmx5IHJlYWRPbmx5Um9vdEZpbGVzeXN0ZW06IGJvb2xlYW47XG4gIHB1YmxpYyByZWFkb25seSB1c2VyPzogbnVtYmVyO1xuICBwdWJsaWMgcmVhZG9ubHkgZ3JvdXA/OiBudW1iZXI7XG4gIHB1YmxpYyByZWFkb25seSBhbGxvd1ByaXZpbGVnZUVzY2FsYXRpb24/OiBib29sZWFuO1xuXG4gIGNvbnN0cnVjdG9yKHByb3BzOiBDb250YWluZXJTZWN1cml0eUNvbnRleHRQcm9wcyA9IHt9KSB7XG4gICAgdGhpcy5lbnN1cmVOb25Sb290ID0gcHJvcHMuZW5zdXJlTm9uUm9vdCA/PyB0cnVlO1xuICAgIHRoaXMucHJpdmlsZWdlZCA9IHByb3BzLnByaXZpbGVnZWQgPz8gZmFsc2U7XG4gICAgdGhpcy5yZWFkT25seVJvb3RGaWxlc3lzdGVtID0gcHJvcHMucmVhZE9ubHlSb290RmlsZXN5c3RlbSA/PyB0cnVlO1xuICAgIHRoaXMudXNlciA9IHByb3BzLnVzZXI7XG4gICAgdGhpcy5ncm91cCA9IHByb3BzLmdyb3VwO1xuICAgIHRoaXMuYWxsb3dQcml2aWxlZ2VFc2NhbGF0aW9uID0gcHJvcHMuYWxsb3dQcml2aWxlZ2VFc2NhbGF0aW9uID8/IGZhbHNlO1xuICB9XG5cbiAgLyoqXG4gICAqIEBpbnRlcm5hbFxuICAgKi9cbiAgcHVibGljIF90b0t1YmUoKTogazhzLlNlY3VyaXR5Q29udGV4dCB7XG4gICAgcmV0dXJuIHtcbiAgICAgIHJ1bkFzR3JvdXA6IHRoaXMuZ3JvdXAsXG4gICAgICBydW5Bc1VzZXI6IHRoaXMudXNlcixcbiAgICAgIHJ1bkFzTm9uUm9vdDogdGhpcy5lbnN1cmVOb25Sb290LFxuICAgICAgcHJpdmlsZWdlZDogdGhpcy5wcml2aWxlZ2VkLFxuICAgICAgcmVhZE9ubHlSb290RmlsZXN5c3RlbTogdGhpcy5yZWFkT25seVJvb3RGaWxlc3lzdGVtLFxuICAgICAgYWxsb3dQcml2aWxlZ2VFc2NhbGF0aW9uOiB0aGlzLmFsbG93UHJpdmlsZWdlRXNjYWxhdGlvbixcbiAgICB9O1xuICB9XG5cbn1cblxuZXhwb3J0IGVudW0gRW52RmllbGRQYXRocyB7XG4gIC8qKlxuICAgKiBUaGUgbmFtZSBvZiB0aGUgcG9kLlxuICAgKi9cbiAgUE9EX05BTUUgPSAnbWV0YWRhdGEubmFtZScsXG5cbiAgLyoqXG4gICAqIFRoZSBuYW1lc3BhY2Ugb2YgdGhlIHBvZC5cbiAgICovXG4gIFBPRF9OQU1FU1BBQ0UgPSAnbWV0YWRhdGEubmFtZXNwYWNlJyxcblxuICAvKipcbiAgICogVGhlIHVpZCBvZiB0aGUgcG9kLlxuICAgKi9cbiAgUE9EX1VJRCA9ICdtZXRhZGF0YS51aWQnLFxuXG4gIC8qKlxuICAgKiBUaGUgbGFiZWxzIG9mIHRoZSBwb2QuXG4gICAqL1xuICBQT0RfTEFCRUwgPSAnbWV0YWRhdGEubGFiZWxzJyxcblxuICAvKipcbiAgICogVGhlIGFubm90YXRpb25zIG9mIHRoZSBwb2QuXG4gICAqL1xuICBQT0RfQU5OT1RBVElPTiA9ICdtZXRhZGF0YS5hbm5vdGF0aW9ucycsXG5cbiAgLyoqXG4gICAqIFRoZSBpcEFkZHJlc3Mgb2YgdGhlIHBvZC5cbiAgICovXG4gIFBPRF9JUCA9ICdzdGF0dXMucG9kSVAnLFxuXG4gIC8qKlxuICAgKiBUaGUgc2VydmljZSBhY2NvdW50IG5hbWUgb2YgdGhlIHBvZC5cbiAgICovXG4gIFNFUlZJQ0VfQUNDT1VOVF9OQU1FID0gJ3NwZWMuc2VydmljZUFjY291bnROYW1lJyxcblxuICAvKipcbiAgICogVGhlIG5hbWUgb2YgdGhlIG5vZGUuXG4gICAqL1xuICBOT0RFX05BTUUgPSAnc3BlYy5ub2RlTmFtZScsXG5cbiAgLyoqXG4gICAqIFRoZSBpcEFkZHJlc3Mgb2YgdGhlIG5vZGUuXG4gICAqL1xuICBOT0RFX0lQID0gJ3N0YXR1cy5ob3N0SVAnLFxuXG4gIC8qKlxuICAgKiBUaGUgaXBBZGRyZXNlc3Mgb2YgdGhlIHBvZC5cbiAgICovXG4gIFBPRF9JUFMgPSAnc3RhdHVzLnBvZElQcycsXG59XG5cbmV4cG9ydCBlbnVtIFJlc291cmNlRmllbGRQYXRocyB7XG4gIC8qKlxuICAgKiBDUFUgbGltaXQgb2YgdGhlIGNvbnRhaW5lci5cbiAgICovXG4gIENQVV9MSU1JVCA9ICdsaW1pdHMuY3B1JyxcblxuICAvKipcbiAgICogTWVtb3J5IGxpbWl0IG9mIHRoZSBjb250YWluZXIuXG4gICAqL1xuICBNRU1PUllfTElNSVQgPSAnbGltaXRzLm1lbW9yeScsXG5cbiAgLyoqXG4gICAqIENQVSByZXF1ZXN0IG9mIHRoZSBjb250YWluZXIuXG4gICAqL1xuICBDUFVfUkVRVUVTVCA9ICdyZXF1ZXN0cy5jcHUnLFxuXG4gIC8qKlxuICAgKiBNZW1vcnkgcmVxdWVzdCBvZiB0aGUgY29udGFpbmVyLlxuICAgKi9cbiAgTUVNT1JZX1JFUVVFU1QgPSAncmVxdWVzdHMubWVtb3J5JyxcblxuICAvKipcbiAgICogRXBoZW1lcmFsIHN0b3JhZ2UgbGltaXQgb2YgdGhlIGNvbnRhaW5lci5cbiAgICovXG4gIFNUT1JBR0VfTElNSVQgPSAnbGltaXRzLmVwaGVtZXJhbC1zdG9yYWdlJyxcblxuICAvKipcbiAgICogRXBoZW1lcmFsIHN0b3JhZ2UgcmVxdWVzdCBvZiB0aGUgY29udGFpbmVyLlxuICAgKi9cbiAgU1RPUkFHRV9SRVFVRVNUID0gJ3JlcXVlc3RzLmVwaGVtZXJhbC1zdG9yYWdlJyxcbn1cblxuLyoqXG4gKiBPcHRpb25zIHRvIHNwZWNpZnkgYW4gZW52aW9ubWVudCB2YXJpYWJsZSB2YWx1ZSBmcm9tIGEgQ29uZmlnTWFwIGtleS5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBFbnZWYWx1ZUZyb21Db25maWdNYXBPcHRpb25zIHtcblxuICAvKipcbiAgICogU3BlY2lmeSB3aGV0aGVyIHRoZSBDb25maWdNYXAgb3IgaXRzIGtleSBtdXN0IGJlIGRlZmluZWQuXG4gICAqXG4gICAqIEBkZWZhdWx0IGZhbHNlXG4gICAqL1xuICByZWFkb25seSBvcHRpb25hbD86IGJvb2xlYW47XG59XG5cbi8qKlxuICogT3B0aW9ucyB0byBzcGVjaWZ5IGFuIGVudmlyb25tZW50IHZhcmlhYmxlIHZhbHVlIGZyb20gYSBTZWNyZXQuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgRW52VmFsdWVGcm9tU2VjcmV0T3B0aW9ucyB7XG5cbiAgLyoqXG4gICAqIFNwZWNpZnkgd2hldGhlciB0aGUgU2VjcmV0IG9yIGl0cyBrZXkgbXVzdCBiZSBkZWZpbmVkLlxuICAgKlxuICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgKi9cbiAgcmVhZG9ubHkgb3B0aW9uYWw/OiBib29sZWFuO1xuXG59XG5cbi8qKlxuICogT3B0aW9ucyB0byBzcGVjaWZ5IGFuIGVudmlyb25tZW50IHZhcmlhYmxlIHZhbHVlIGZyb20gdGhlIHByb2Nlc3MgZW52aXJvbm1lbnQuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgRW52VmFsdWVGcm9tUHJvY2Vzc09wdGlvbnMge1xuXG4gIC8qKlxuICAgKiBTcGVjaWZ5IHdoZXRoZXIgdGhlIGtleSBtdXN0IGV4aXN0IGluIHRoZSBlbnZpcm9ubWVudC5cbiAgICogSWYgdGhpcyBpcyBzZXQgdG8gdHJ1ZSwgYW5kIHRoZSBrZXkgZG9lcyBub3QgZXhpc3QsIGFuIGVycm9yIHdpbGwgdGhyb3duLlxuICAgKlxuICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgKi9cbiAgcmVhZG9ubHkgcmVxdWlyZWQ/OiBib29sZWFuO1xufVxuXG4vKipcbiAqIE9wdGlvbnMgdG8gc3BlY2lmeSBhbiBlbnZpcm9ubWVudCB2YXJpYWJsZSB2YWx1ZSBmcm9tIGEgZmllbGQgcmVmZXJlbmNlLlxuICovXG5leHBvcnQgaW50ZXJmYWNlIEVudlZhbHVlRnJvbUZpZWxkUmVmT3B0aW9ucyB7XG4gIC8qKlxuICAgKiBWZXJzaW9uIG9mIHRoZSBzY2hlbWEgdGhlIEZpZWxkUGF0aCBpcyB3cml0dGVuIGluIHRlcm1zIG9mLlxuICAgKi9cbiAgcmVhZG9ubHkgYXBpVmVyc2lvbj86IHN0cmluZztcblxuICAvKipcbiAgICogVGhlIGtleSB0byBzZWxlY3QgdGhlIHBvZCBsYWJlbCBvciBhbm5vdGF0aW9uLlxuICAgKi9cbiAgcmVhZG9ubHkga2V5Pzogc3RyaW5nO1xufVxuXG4vKipcbiAqIE9wdGlvbnMgdG8gc3BlY2lmeSBhbiBlbnZpcm9ubWVudCB2YXJpYWJsZSB2YWx1ZSBmcm9tIGEgcmVzb3VyY2UuXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgRW52VmFsdWVGcm9tUmVzb3VyY2VPcHRpb25zIHtcbiAgLyoqXG4gICAqIFRoZSBjb250YWluZXIgdG8gc2VsZWN0IHRoZSB2YWx1ZSBmcm9tLlxuICAgKi9cbiAgcmVhZG9ubHkgY29udGFpbmVyPzogQ29udGFpbmVyO1xuXG4gIC8qKlxuICAgKiBUaGUgb3V0cHV0IGZvcm1hdCBvZiB0aGUgZXhwb3NlZCByZXNvdXJjZS5cbiAgICovXG4gIHJlYWRvbmx5IGRpdmlzb3I/OiBzdHJpbmc7XG59XG5cbi8qKlxuICogVXRpbGl0eSBjbGFzcyBmb3IgY3JlYXRpbmcgcmVhZGluZyBlbnYgdmFsdWVzIGZyb20gdmFyaW91cyBzb3VyY2VzLlxuICovXG5leHBvcnQgY2xhc3MgRW52VmFsdWUge1xuXG4gIC8qKlxuICAgKiBDcmVhdGUgYSB2YWx1ZSBieSByZWFkaW5nIGEgc3BlY2lmaWMga2V5IGluc2lkZSBhIGNvbmZpZyBtYXAuXG4gICAqXG4gICAqIEBwYXJhbSBjb25maWdNYXAgLSBUaGUgY29uZmlnIG1hcC5cbiAgICogQHBhcmFtIGtleSAtIFRoZSBrZXkgdG8gZXh0cmFjdCB0aGUgdmFsdWUgZnJvbS5cbiAgICogQHBhcmFtIG9wdGlvbnMgLSBBZGRpdGlvbmFsIG9wdGlvbnMuXG4gICAqL1xuICBwdWJsaWMgc3RhdGljIGZyb21Db25maWdNYXAoY29uZmlnTWFwOiBjb25maWdtYXAuSUNvbmZpZ01hcCwga2V5OiBzdHJpbmcsIG9wdGlvbnM6IEVudlZhbHVlRnJvbUNvbmZpZ01hcE9wdGlvbnMgPSB7IH0pOiBFbnZWYWx1ZSB7XG5cbiAgICBjb25zdCBzb3VyY2U6IGs4cy5FbnZWYXJTb3VyY2UgPSB7XG4gICAgICBjb25maWdNYXBLZXlSZWY6IHtcbiAgICAgICAgbmFtZTogY29uZmlnTWFwLm5hbWUsXG4gICAgICAgIGtleSxcbiAgICAgICAgb3B0aW9uYWw6IG9wdGlvbnMub3B0aW9uYWwsXG4gICAgICB9LFxuICAgIH07XG4gICAgcmV0dXJuIG5ldyBFbnZWYWx1ZSh1bmRlZmluZWQsIHNvdXJjZSk7XG4gIH1cblxuICAvKipcbiAgICogRGVmaW5lcyBhbiBlbnZpcm9ubWVudCB2YWx1ZSBmcm9tIGEgc2VjcmV0IEpTT04gdmFsdWUuXG4gICAqXG4gICAqIEBwYXJhbSBzZWNyZXRWYWx1ZSBUaGUgc2VjcmV0IHZhbHVlIChzZWNyZW50ICsga2V5KVxuICAgKiBAcGFyYW0gb3B0aW9ucyBBZGRpdGlvbmFsIG9wdGlvbnNcbiAgICovXG4gIHB1YmxpYyBzdGF0aWMgZnJvbVNlY3JldFZhbHVlKHNlY3JldFZhbHVlOiBzZWNyZXQuU2VjcmV0VmFsdWUsIG9wdGlvbnM6IEVudlZhbHVlRnJvbVNlY3JldE9wdGlvbnMgPSB7fSk6IEVudlZhbHVlIHtcbiAgICBjb25zdCBzb3VyY2U6IGs4cy5FbnZWYXJTb3VyY2UgPSB7XG4gICAgICBzZWNyZXRLZXlSZWY6IHtcbiAgICAgICAgbmFtZTogc2VjcmV0VmFsdWUuc2VjcmV0Lm5hbWUsXG4gICAgICAgIGtleTogc2VjcmV0VmFsdWUua2V5LFxuICAgICAgICBvcHRpb25hbDogb3B0aW9ucy5vcHRpb25hbCxcbiAgICAgIH0sXG4gICAgfTtcblxuICAgIHJldHVybiBuZXcgRW52VmFsdWUodW5kZWZpbmVkLCBzb3VyY2UpO1xuICB9XG5cbiAgLyoqXG4gICAqIENyZWF0ZSBhIHZhbHVlIGZyb20gdGhlIGdpdmVuIGFyZ3VtZW50LlxuICAgKlxuICAgKiBAcGFyYW0gdmFsdWUgLSBUaGUgdmFsdWUuXG4gICAqL1xuICBwdWJsaWMgc3RhdGljIGZyb21WYWx1ZSh2YWx1ZTogc3RyaW5nKTogRW52VmFsdWUge1xuICAgIHJldHVybiBuZ