UNPKG

@decaf-ts/fabric-weaver

Version:
530 lines 92.2 kB
import { Logging } from "@decaf-ts/logging";
import path from "path";
import fs from "fs";
import { readFileYaml, writeFileYaml } from "../../utils/yaml";
export class FabricOrdererConfigBuilder {
    constructor(logger) {
        this.config = readFileYaml(path.join(__dirname, "../../../config/orderer.yaml"));
        if (!logger)
            this.log = Logging.for(FabricOrdererConfigBuilder);
        else
            this.log = logger.for(FabricOrdererConfigBuilder.name);
    }
    setKafka(kafka) {
        if (kafka !== undefined) {
            if (kafka.Retry !== undefined) {
                if (kafka.Retry.ShortInterval !== undefined) {
                    this.log.debug(`Setting Kafka retry short interval to ${kafka.Retry.ShortInterval}`);
                    this.config.Kafka.Retry.ShortInterval = kafka.Retry.ShortInterval;
                }
                if (kafka.Retry.ShortTotal !== undefined) {
                    this.log.debug(`Setting Kafka retry short total to ${kafka.Retry.ShortTotal}`);
                    this.config.Kafka.Retry.ShortTotal = kafka.Retry.ShortTotal;
                }
                if (kafka.Retry.LongInterval !== undefined) {
                    this.log.debug(`Setting Kafka retry long interval to ${kafka.Retry.LongInterval}`);
                    this.config.Kafka.Retry.LongInterval = kafka.Retry.LongInterval;
                }
                if (kafka.Retry.LongTotal !== undefined) {
                    this.log.debug(`Setting Kafka retry long total to ${kafka.Retry.LongTotal}`);
                    this.config.Kafka.Retry.LongTotal = kafka.Retry.LongTotal;
                }
                if (kafka.Retry.NetworkTimeouts !== undefined) {
                    if (kafka.Retry.NetworkTimeouts.DialTimeout !== undefined) {
                        this.log.debug(`Setting Kafka retry network timeouts dial timeout to ${kafka.Retry.NetworkTimeouts.DialTimeout}`);
                        this.config.Kafka.Retry.NetworkTimeouts.DialTimeout =
                            kafka.Retry.NetworkTimeouts.DialTimeout;
                    }
                    if (kafka.Retry.NetworkTimeouts.ReadTimeout !== undefined) {
                        this.log.debug(`Setting Kafka retry network timeouts read timeout to ${kafka.Retry.NetworkTimeouts.ReadTimeout}`);
                        this.config.Kafka.Retry.NetworkTimeouts.ReadTimeout =
                            kafka.Retry.NetworkTimeouts.ReadTimeout;
                    }
                    if (kafka.Retry.NetworkTimeouts.WriteTimeout !== undefined) {
                        this.log.debug(`Setting Kafka retry network timeouts write timeout to ${kafka.Retry.NetworkTimeouts.WriteTimeout}`);
                        this.config.Kafka.Retry.NetworkTimeouts.WriteTimeout =
                            kafka.Retry.NetworkTimeouts.WriteTimeout;
                    }
                }
                if (kafka.Retry.Metadata !== undefined) {
                    if (kafka.Retry.Metadata.RetryBackoff !== undefined) {
                        this.log.debug(`Setting Kafka retry metadata retry backoff to ${kafka.Retry.Metadata.RetryBackoff}`);
                        this.config.Kafka.Retry.Metadata.RetryBackoff =
                            kafka.Retry.Metadata.RetryBackoff;
                    }
                    if (kafka.Retry.Metadata.RetryMax !== undefined) {
                        this.log.debug(`Setting Kafka retry metadata retry max to ${kafka.Retry.Metadata.RetryMax}`);
                        this.config.Kafka.Retry.Metadata.RetryMax =
                            kafka.Retry.Metadata.RetryMax;
                    }
                }
                if (kafka.Retry.Producer !== undefined) {
                    if (kafka.Retry.Producer.RetryBackoff !== undefined) {
                        this.log.debug(`Setting Kafka retry producer retry backoff to ${kafka.Retry.Producer.RetryBackoff}`);
                        this.config.Kafka.Retry.Producer.RetryBackoff =
                            kafka.Retry.Producer.RetryBackoff;
                    }
                    if (kafka.Retry.Producer.RetryMax !== undefined) {
                        this.log.debug(`Setting Kafka retry producer retry max to ${kafka.Retry.Producer.RetryMax}`);
                        this.config.Kafka.Retry.Producer.RetryMax =
                            kafka.Retry.Producer.RetryMax;
                    }
                }
                if (kafka.Retry.Consumer !== undefined) {
                    if (kafka.Retry.Consumer.RetryBackoff !== undefined) {
                        this.log.debug(`Setting Kafka retry consumer retry backoff to ${kafka.Retry.Consumer.RetryBackoff}`);
                        this.config.Kafka.Retry.Consumer.RetryBackoff =
                            kafka.Retry.Consumer.RetryBackoff;
                    }
                }
            }
            if (kafka.Topic !== undefined) {
                if (kafka.Topic.ReplicationFactor !== undefined) {
                    this.log.debug(`Setting Kafka topic replication factor to ${kafka.Topic.ReplicationFactor}`);
                    this.config.Kafka.Topic.ReplicationFactor =
                        kafka.Topic.ReplicationFactor;
                }
            }
            if (kafka.Verbose !== undefined) {
                this.log.debug(`Setting Kafka verbose to ${kafka.Verbose}`);
                this.config.Kafka.Verbose = kafka.Verbose;
            }
            if (kafka.TLS !== undefined) {
                if (kafka.TLS.Enabled !== undefined) {
                    this.log.debug(`Setting Kafka TLS enabled to ${kafka.TLS.Enabled}`);
                    this.config.Kafka.TLS.Enabled = kafka.TLS.Enabled;
                }
                if (kafka.TLS.Certificate !== undefined) {
                    this.log.debug(`Setting Kafka TLS certificate to ${kafka.TLS.Certificate}`);
                    this.config.Kafka.TLS.Certificate = kafka.TLS.Certificate;
                }
                if (kafka.TLS.PrivateKey !== undefined) {
                    this.log.debug(`Setting Kafka TLS private key to ${kafka.TLS.PrivateKey}`);
                    this.config.Kafka.TLS.PrivateKey = kafka.TLS.PrivateKey;
                }
                if (kafka.TLS.RootCAs !== undefined) {
                    this.log.debug(`Setting Kafka TLS root CAs to ${kafka.TLS.RootCAs}`);
                    this.config.Kafka.TLS.RootCAs = kafka.TLS.RootCAs;
                }
            }
            if (kafka.Version !== undefined) {
                this.log.debug(`Setting Kafka version to ${kafka.Version}`);
                this.config.Kafka.Version = kafka.Version;
            }
            if (kafka.SASLPlain !== undefined) {
                if (kafka.SASLPlain.Enabled !== undefined) {
                    this.log.debug(`Setting Kafka SASL plain enabled to ${kafka.SASLPlain.Enabled}`);
                    this.config.Kafka.SASLPlain.Enabled = kafka.SASLPlain.Enabled;
                }
                if (kafka.SASLPlain.User !== undefined) {
                    this.log.debug(`Setting Kafka SASL plain user to ${kafka.SASLPlain.User}`);
                    this.config.Kafka.SASLPlain.User = kafka.SASLPlain.User;
                }
                if (kafka.SASLPlain.Password !== undefined) {
                    this.log.debug(`Setting Kafka SASL plain password to ${kafka.SASLPlain.Password}`);
                    this.config.Kafka.SASLPlain.Password = kafka.SASLPlain.Password;
                }
            }
        }
        return this;
    }
    setFileLedgerLocation(fileLedgerLocation) {
        if (fileLedgerLocation !== undefined) {
            this.log.debug(`Setting file ledger location to ${fileLedgerLocation}`);
            this.config.FileLedger.Location = fileLedgerLocation;
        }
        return this;
    }
    setAuthWindow(authWindow) {
        if (authWindow !== undefined) {
            this.log.debug(`Setting auth window to ${authWindow}`);
            this.config.General.Authentication.TimeWindow = authWindow;
        }
        return this;
    }
    setBCCSP(bccsp) {
        if (bccsp !== undefined) {
            if (bccsp.Default !== undefined) {
                this.log.debug(`Setting BCCSP default to ${bccsp.Default}`);
                this.config.General.BCCSP.Default = bccsp.Default;
            }
            if (bccsp.SW !== undefined) {
                if (bccsp.SW.Hash !== undefined) {
                    this.log.debug(`Setting BCCSP SW hash to ${bccsp.SW.Hash}`);
                    this.config.General.BCCSP.SW.Hash = bccsp.SW.Hash;
                }
                if (bccsp.SW.Security !== undefined) {
                    this.log.debug(`Setting BCCSP SW security to ${bccsp.SW.Security}`);
                    this.config.General.BCCSP.SW.Security = bccsp.SW.Security;
                }
                if (bccsp.SW.FileKeyStore !== undefined) {
                    if (bccsp.SW.FileKeyStore.KeyStore !== undefined) {
                        this.log.debug(`Setting BCCSP SW FileKeyStore key store to ${bccsp.SW.FileKeyStore.KeyStore}`);
                        this.config.General.BCCSP.SW.FileKeyStore.KeyStore =
                            bccsp.SW.FileKeyStore.KeyStore;
                    }
                }
            }
            if (bccsp.PKCS11 !== undefined) {
                if (bccsp.PKCS11.Library !== undefined) {
                    this.log.debug(`Setting BCCSP PKCS11 library to ${bccsp.PKCS11.Library}`);
                    this.config.General.BCCSP.PKCS11.Library = bccsp.PKCS11.Library;
                }
                if (bccsp.PKCS11.Label !== undefined) {
                    this.log.debug(`Setting BCCSP PKCS11 label to ${bccsp.PKCS11.Label}`);
                    this.config.General.BCCSP.PKCS11.Label = bccsp.PKCS11.Label;
                }
                if (bccsp.PKCS11.Pin !== undefined) {
                    this.log.debug(`Setting BCCSP PKCS11 pin to ${bccsp.PKCS11.Pin}`);
                    this.config.General.BCCSP.PKCS11.Pin = bccsp.PKCS11.Pin;
                }
                if (bccsp.PKCS11.Hash !== undefined) {
                    this.log.debug(`Setting BCCSP PKCS11 hash to ${bccsp.PKCS11.Hash}`);
                    this.config.General.BCCSP.PKCS11.Hash = bccsp.PKCS11.Hash;
                }
                if (bccsp.PKCS11.Security !== undefined) {
                    this.log.debug(`Setting BCCSP PKCS11 security to ${bccsp.PKCS11.Security}`);
                    this.config.General.BCCSP.PKCS11.Security = bccsp.PKCS11.Security;
                }
                if (bccsp.PKCS11.FileKeyStore !== undefined) {
                    if (bccsp.PKCS11.FileKeyStore.KeyStore !== undefined) {
                        this.log.debug(`Setting BCCSP PKCS11 FileKeyStore key store to ${bccsp.PKCS11.FileKeyStore.KeyStore}`);
                        this.config.General.BCCSP.PKCS11.FileKeyStore.KeyStore =
                            bccsp.PKCS11.FileKeyStore.KeyStore;
                    }
                }
            }
        }
        return this;
    }
    setDebug(debug) {
        if (debug !== undefined) {
            if (debug.BroadcastTraceDir !== undefined) {
                this.log.debug(`Setting debug broadcast trace directory to ${debug.BroadcastTraceDir}`);
                this.config.Debug.BroadcastTraceDir = debug.BroadcastTraceDir;
            }
            if (debug.DeliverTraceDir !== undefined) {
                this.log.debug(`Setting debug deliver trace directory to ${debug.DeliverTraceDir}`);
                this.config.Debug.DeliverTraceDir = debug.DeliverTraceDir;
            }
        }
        return this;
    }
    setOperations(operations) {
        if (operations !== undefined) {
            if (operations.ListenAddress !== undefined) {
                this.log.debug(`Setting operations listen address to ${operations.ListenAddress}`);
                this.config.Operations.ListenAddress = operations.ListenAddress;
            }
            if (operations.TLS !== undefined) {
                if (operations.TLS.Enabled !== undefined) {
                    this.log.debug(`Setting TLS enabled to ${operations.TLS.Enabled}`);
                    this.config.Operations.TLS.Enabled = operations.TLS.Enabled;
                }
                if (operations.TLS.Certificate !== undefined) {
                    this.log.debug(`Setting TLS certificate to ${operations.TLS.Certificate}`);
                    this.config.Operations.TLS.Certificate = operations.TLS.Certificate;
                }
                if (operations.TLS.PrivateKey !== undefined) {
                    this.log.debug(`Setting TLS private key to ${operations.TLS.PrivateKey}`);
                    this.config.Operations.TLS.PrivateKey = operations.TLS.PrivateKey;
                }
                if (operations.TLS.ClientAuthRequired !== undefined) {
                    this.log.debug(`Setting TLS client authentication required to ${operations.TLS.ClientAuthRequired}`);
                    this.config.Operations.TLS.ClientAuthRequired =
                        operations.TLS.ClientAuthRequired;
                }
                if (operations.TLS.ClientRootCAs !== undefined) {
                    this.log.debug(`Setting TLS client root CAs to ${operations.TLS.ClientRootCAs}`);
                    this.config.Operations.TLS.ClientRootCAs =
                        operations.TLS.ClientRootCAs;
                }
            }
        }
        return this;
    }
    setMetrics(metrics) {
        if (metrics !== undefined) {
            if (metrics.Provider !== undefined) {
                this.log.debug(`Setting metrics provider to ${metrics.Provider}`);
                this.config.Metrics.Provider = metrics.Provider;
            }
            if (metrics.Statsd !== undefined) {
                if (metrics.Statsd.Network !== undefined) {
                    this.log.debug(`Setting statsd network to ${metrics.Statsd.Network}`);
                    this.config.Metrics.Statsd.Network = metrics.Statsd.Network;
                }
                if (metrics.Statsd.Address !== undefined) {
                    this.log.debug(`Setting statsd address to ${metrics.Statsd.Address}`);
                    this.config.Metrics.Statsd.Address = metrics.Statsd.Address;
                }
                if (metrics.Statsd.WriteInterval !== undefined) {
                    this.log.debug(`Setting statsd write interval to ${metrics.Statsd.WriteInterval}`);
                    this.config.Metrics.Statsd.WriteInterval =
                        metrics.Statsd.WriteInterval;
                }
                if (metrics.Statsd.Prefix !== undefined) {
                    this.log.debug(`Setting statsd prefix to ${metrics.Statsd.Prefix}`);
                    this.config.Metrics.Statsd.Prefix = metrics.Statsd.Prefix;
                }
            }
        }
        return this;
    }
    setProfile(profile) {
        if (profile !== undefined) {
            if (profile.Enabled !== undefined) {
                this.log.debug(`Setting profile to ${profile.Enabled}`);
                this.config.General.Profile = profile;
            }
            if (profile.Address !== undefined) {
                this.log.debug(`Setting profile address to ${profile.Address}`);
                this.config.General.Profile.Address = profile.Address;
            }
        }
        return this;
    }
    setLocalMSP(msp) {
        if (msp !== undefined) {
            if (msp.LocalMSPDir !== undefined) {
                this.log.debug(`Setting local MSP directory to ${msp.LocalMSPDir}`);
                this.config.General.LocalMSPDir = msp.LocalMSPDir;
            }
            if (msp.LocalMSPID !== undefined) {
                this.log.debug(`Setting local MSP ID to ${msp.LocalMSPID}`);
                this.config.General.LocalMSPID = msp.LocalMSPID;
            }
        }
        return this;
    }
    setBootstrap(boot) {
        if (boot !== undefined) {
            if (boot.BootstrapFile !== undefined) {
                this.log.debug(`Setting bootstrap file to ${boot.BootstrapFile}`);
                this.config.General.BootstrapFile = boot.BootstrapFile;
            }
            if (boot.BootstrapMethod) {
                this.log.debug(`Setting bootstrap method to ${boot.BootstrapMethod}`);
                this.config.General.BootstrapMethod = boot.BootstrapMethod;
            }
        }
        return this;
    }
    setCluster(cluster) {
        if (cluster !== undefined) {
            if (cluster.SendBufferSize !== undefined) {
                this.log.debug(`Setting send buffer size to ${cluster.SendBufferSize}`);
                this.config.General.Cluster.SendBufferSize = cluster.SendBufferSize;
            }
            if (cluster.ClientCertificate !== undefined) {
                this.log.debug(`Setting client certificate to ${cluster.ClientCertificate}`);
                this.config.General.Cluster.ClientCertificate =
                    cluster.ClientCertificate;
            }
            if (cluster.ClientPrivateKey !== undefined) {
                this.log.debug(`Setting client private key to ${cluster.ClientPrivateKey}`);
                this.config.General.Cluster.ClientPrivateKey =
                    cluster.ClientPrivateKey;
            }
            if (cluster.ListenAddress !== undefined) {
                this.log.debug(`Setting listen address to ${cluster.ListenAddress}`);
                this.config.General.Cluster.ListenAddress = cluster.ListenAddress;
            }
            if (cluster.ListenPort !== undefined) {
                this.log.debug(`Setting listen port to ${cluster.ListenPort}`);
                this.config.General.Cluster.ListenPort = cluster.ListenPort;
            }
            if (cluster.ServerCertificate !== undefined) {
                this.log.debug(`Setting server certificate to ${cluster.ServerCertificate}`);
                this.config.General.Cluster.ServerCertificate =
                    cluster.ServerCertificate;
            }
            if (cluster.ServerPrivateKey !== undefined) {
                this.log.debug(`Setting server private key to ${cluster.ServerPrivateKey}`);
                this.config.General.Cluster.ServerPrivateKey =
                    cluster.ServerPrivateKey;
            }
        }
        return this;
    }
    setMSGSize(cfg) {
        if (cfg !== undefined) {
            if (cfg.MaxRecvMsgSize !== undefined) {
                this.log.debug(`Setting max receive message size to ${cfg.MaxRecvMsgSize}`);
                this.config.General.MaxRecvMsgSize = cfg.MaxRecvMsgSize;
            }
            if (cfg.MaxSendMsgSize !== undefined) {
                this.log.debug(`Setting max send message size to ${cfg.MaxSendMsgSize}`);
                this.config.General.MaxSendMsgSize = cfg.MaxSendMsgSize;
            }
        }
        return this;
    }
    setKeepAlive(keepAlive) {
        if (keepAlive !== undefined) {
            if (keepAlive.ServerInterval !== undefined) {
                this.log.debug(`Setting server interval to ${keepAlive.ServerInterval}`);
                this.config.General.Keepalive.ServerInterval =
                    keepAlive.ServerInterval;
            }
            if (keepAlive.ServerMinInterval !== undefined) {
                this.log.debug(`Setting server minimum interval to ${keepAlive.ServerMinInterval}`);
                this.config.General.Keepalive.ServerMinInterval =
                    keepAlive.ServerMinInterval;
            }
            if (keepAlive.ServerTimeout !== undefined) {
                this.log.debug(`Setting server timeout to ${keepAlive.ServerTimeout}`);
                this.config.General.Keepalive.ServerTimeout = keepAlive.ServerTimeout;
            }
        }
        return this;
    }
    setListenAddress(address) {
        if (address !== undefined) {
            this.log.debug(`Setting listen address to ${address}`);
            this.config.General.ListenAddress = address;
        }
        return this;
    }
    setPort(port) {
        if (port !== undefined) {
            this.log.debug(`Setting port to ${port}`);
            this.config.General.ListenPort = port;
        }
        return this;
    }
    setTLS(tls) {
        if (tls !== undefined) {
            if (tls.Enabled !== undefined) {
                this.log.debug(`Setting TLS enabled to ${tls.Enabled}`);
                this.config.General.TLS.Enabled = tls.Enabled;
            }
            if (tls.Certificate !== undefined) {
                this.log.debug(`Setting TLS certificate to ${tls.Certificate}`);
                this.config.General.TLS.Certificate = tls.Certificate;
            }
            if (tls.PrivateKey !== undefined) {
                this.log.debug(`Setting TLS private key to ${tls.PrivateKey}`);
                this.config.General.TLS.PrivateKey = tls.PrivateKey;
            }
            if (tls.RootCAs !== undefined) {
                this.log.debug(`Setting TLS root CAs to ${tls.RootCAs.join(", ")}`);
                this.config.General.TLS.RootCAs = tls.RootCAs;
            }
            if (tls.ClientAuthRequired !== undefined) {
                this.log.debug(`Setting TLS client auth required to ${tls.ClientAuthRequired}`);
                this.config.General.TLS.ClientAuthRequired = tls.ClientAuthRequired;
            }
            if (tls.ClientRootCAs !== undefined) {
                this.log.debug(`Setting TLS client root CAs to ${tls.ClientRootCAs.join(", ")}`);
                this.config.General.TLS.ClientRootCAs = tls.ClientRootCAs;
            }
        }
        return this;
    }
    setAdmin(cfg) {
        if (cfg !== undefined) {
            if (cfg.ListenAddress !== undefined) {
                this.log.debug(`Setting admin listen address to ${cfg.ListenAddress}`);
                this.config.Admin.ListenAddress = cfg.ListenAddress;
            }
            if (cfg.TLS !== undefined) {
                if (cfg.TLS.Enabled !== undefined) {
                    this.log.debug(`Setting admin TLS enabled to ${cfg.TLS.Enabled}`);
                    this.config.Admin.TLS.Enabled = cfg.TLS.Enabled;
                }
                if (cfg.TLS.PrivateKey !== undefined) {
                    this.log.debug(`Setting admin TLS private key to ${cfg.TLS.PrivateKey}`);
                    this.config.Admin.TLS.PrivateKey = cfg.TLS.PrivateKey;
                }
                if (cfg.TLS.Certificate !== undefined) {
                    this.log.debug(`Setting admin TLS certificate to ${cfg.TLS.Certificate}`);
                    this.config.Admin.TLS.Certificate = cfg.TLS.Certificate;
                }
                if (cfg.TLS.RootCAs !== undefined) {
                    this.log.debug(`Setting admin TLS root CAs files: ${cfg.TLS.RootCAs.join(", ")}`);
                    this.config.Admin.TLS.RootCAs = cfg.TLS.RootCAs;
                }
                if (cfg.TLS.ClientAuthRequired !== undefined) {
                    this.log.debug(`Setting admin TLS client auth required to ${cfg.TLS.ClientAuthRequired}`);
                    this.config.Admin.TLS.ClientAuthRequired =
                        cfg.TLS.ClientAuthRequired;
                }
                if (cfg.TLS.ClientRootCAs !== undefined) {
                    if (cfg.TLS.ClientRootCAs !== undefined) {
                        this.log.debug(`Setting admin TLS client root CAs files: ${cfg.TLS.ClientRootCAs.join(", ")}`);
                        this.config.Admin.TLS.ClientRootCAs = cfg.TLS.ClientRootCAs;
                    }
                }
            }
        }
        return this;
    }
    setChannelParticipation(channelParticipation) {
        if (channelParticipation !== undefined) {
            if (channelParticipation.Enabled !== undefined) {
                this.log.debug(`Setting channel participation to ${channelParticipation.Enabled}`);
                this.config.ChannelParticipation.Enabled =
                    channelParticipation.Enabled;
            }
            if (channelParticipation.MaxRequestBodySize !== undefined) {
                this.log.debug(`Setting max request body size to ${channelParticipation.MaxRequestBodySize}`);
                this.config.ChannelParticipation.MaxRequestBodySize =
                    channelParticipation.MaxRequestBodySize;
            }
        }
        return this;
    }
    setConsensus(consensus) {
        if (consensus !== undefined) {
            if (consensus.WALDir !== undefined) {
                this.log.debug(`Setting WAL directory to ${consensus.WALDir}`);
                this.config.Consensus.WALDir = consensus.WALDir;
            }
            if (consensus.SnapDir !== undefined) {
                this.log.debug(`Setting snapshot directory to ${consensus.SnapDir}`);
                this.config.Consensus.SnapDir = consensus.SnapDir;
            }
        }
        return this;
    }
    /**
     * @description Saves the current configuration to a file.
     * @summary Writes the current Fabric CA Server configuration to a YAML file at the specified path. If the directory doesn't exist, it will be created.
     * @param {string} cpath - The path where the configuration file should be saved.
     * @return {this} The current instance of the builder for method chaining.
     * @example
     * const builder = new FabricCAServerCommandBuilder();
     * builder.save('/path/to/config/fabric-ca-server.yaml');
     *
     * @mermaid
     * sequenceDiagram
     *   participant Client
     *   participant Builder as FabricCAServerCommandBuilder
     *   participant FileSystem as File System
     *   Client->>Builder: saveConfig('/path/to/config/fabric-ca-server.yaml')
     *   Builder->>Builder: Check if cpath is defined
     *   alt cpath is defined
     *     Builder->>FileSystem: Check if directory exists
     *     alt Directory doesn't exist
     *       Builder->>FileSystem: Create directory
     *     end
     *     Builder->>Builder: Log debug message
     *     Builder->>FileSystem: Write YAML configuration to file
     *   end
     *   Builder-->>Client: Return this
     */
    save(cpath) {
        if (cpath === undefined)
            return this;
        if (!fs.existsSync(path.join(cpath)))
            fs.mkdirSync(path.join(cpath), { recursive: true });
        if (!cpath.endsWith(".yaml"))
            cpath = path.join(cpath, "orderer.yaml");
        this.log.debug(`Writing configuration to ${cpath}`);
        this.log.debug(`Config file: ${JSON.stringify(this.config, null, 2)}`);
        writeFileYaml(cpath, this.config);
        return this;
    }
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmFicmljLW9yZGVyZXItY29uZmlnLWJ1aWxkZXIuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvZmFicmljL29yZGVyZXIvZmFicmljLW9yZGVyZXItY29uZmlnLWJ1aWxkZXIudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFVLE9BQU8sRUFBRSxNQUFNLG1CQUFtQixDQUFDO0FBbUJwRCxPQUFPLElBQUksTUFBTSxNQUFNLENBQUM7QUFDeEIsT0FBTyxFQUFFLE1BQU0sSUFBSSxDQUFDO0FBQ3BCLE9BQU8sRUFBRSxZQUFZLEVBQUUsYUFBYSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFFL0QsTUFBTSxPQUFPLDBCQUEwQjtJQU9yQyxZQUFZLE1BQWU7UUFKbkIsV0FBTSxHQUFrQixZQUFZLENBQzFDLElBQUksQ0FBQyxJQUFJLENBQUMsU0FBUyxFQUFFLDhCQUE4QixDQUFDLENBQ3BDLENBQUM7UUFHakIsSUFBSSxDQUFDLE1BQU07WUFBRSxJQUFJLENBQUMsR0FBRyxHQUFHLE9BQU8sQ0FBQyxHQUFHLENBQUMsMEJBQTBCLENBQUMsQ0FBQzs7WUFDM0QsSUFBSSxDQUFDLEdBQUcsR0FBRyxNQUFNLENBQUMsR0FBRyxDQUFDLDBCQUEwQixDQUFDLElBQUksQ0FBQyxDQUFDO0lBQzlELENBQUM7SUFFRCxRQUFRLENBQUMsS0FBbUI7UUFDMUIsSUFBSSxLQUFLLEtBQUssU0FBUyxFQUFFLENBQUM7WUFDeEIsSUFBSSxLQUFLLENBQUMsS0FBSyxLQUFLLFNBQVMsRUFBRSxDQUFDO2dCQUM5QixJQUFJLEtBQUssQ0FBQyxLQUFLLENBQUMsYUFBYSxLQUFLLFNBQVMsRUFBRSxDQUFDO29CQUM1QyxJQUFJLENBQUMsR0FBRyxDQUFDLEtBQUssQ0FDWix5Q0FBeUMsS0FBSyxDQUFDLEtBQUssQ0FBQyxhQUFhLEVBQUUsQ0FDckUsQ0FBQztvQkFDRixJQUFJLENBQUMsTUFBTSxDQUFDLEtBQU0sQ0FBQyxL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T0F5Qkc7SUFDSCxJQUFJLENBQUMsS0FBYztRQUNqQixJQUFJLEtBQUssS0FBSyxTQUFTO1lBQUUsT0FBTyxJQUFJLENBQUM7UUFFckMsSUFBSSxDQUFDLEVBQUUsQ0FBQyxVQUFVLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxLQUFLLENBQUMsQ0FBQztZQUNsQyxFQUFFLENBQUMsU0FBUyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLEVBQUUsRUFBRSxTQUFTLEVBQUUsSUFBSSxFQUFFLENBQUMsQ0FBQztRQUV0RCxJQUFJLENBQUMsS0FBSyxDQUFDLFFBQVEsQ0FBQyxPQUFPLENBQUM7WUFBRSxLQUFLLEdBQUcsSUFBSSxDQUFDLElBQUksQ0FBQyxLQUFLLEVBQUUsY0FBYyxDQUFDLENBQUM7UUFFdkUsSUFBSSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsNEJBQTRCLEtBQUssRUFBRSxDQUFDLENBQUM7UUFDcEQsSUFBSSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsZ0JBQWdCLElBQUksQ0FBQyxTQUFTLENBQUMsSUFBSSxDQUFDLE1BQU0sRUFBRSxJQUFJLEVBQUUsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDO1FBQ3ZFLGFBQWEsQ0FBQyxLQUFLLEVBQUUsSUFBSSxDQUFDLE1BQU0sQ0FBQyxDQUFDO1FBRWxDLE9BQU8sSUFBSSxDQUFDO0lBQ2QsQ0FBQztDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgTG9nZ2VyLCBMb2dnaW5nIH0gZnJvbSBcIkBkZWNhZi10cy9sb2dnaW5nXCI7XG5pbXBvcnQge1xuICBBZG1pbkNvbmZpZyxcbiAgQkNDU1BDb25maWcsXG4gIEJvb3RzdHJhcENvbmZpZyxcbiAgQ2hhbm5lbFBhcnRpY2lwYXRpb25Db25maWcsXG4gIENsdXN0ZXJDb25maWcsXG4gIENvbnNlbnN1c0NvbmZpZyxcbiAgRGVidWdDb25maWcsXG4gIEthZmthQ29uZmlnLFxuICBLZWVwQWxpdmVDb25maWcsXG4gIE1ldHJpY3NDb25maWcsXG4gIE1TR1NpemVDb25maWcsXG4gIE1TUENvbmZpZyxcbiAgT3BlcmF0aW9uc0NvbmZpZyxcbiAgT3JkZXJlckNvbmZpZyxcbiAgUHJvZmlsZUNvbmZpZyxcbiAgVExTQ29uZmlnLFxufSBmcm9tIFwiLi4vaW50ZXJmYWNlcy9mYWJyaWMvb3JkZXJlci1jb25maWdcIjtcbmltcG9ydCBwYXRoIGZyb20gXCJwYXRoXCI7XG5pbXBvcnQgZnMgZnJvbSBcImZzXCI7XG5pbXBvcnQgeyByZWFkRmlsZVlhbWwsIHdyaXRlRmlsZVlhbWwgfSBmcm9tIFwiLi4vLi4vdXRpbHMveWFtbFwiO1xuXG5leHBvcnQgY2xhc3MgRmFicmljT3JkZXJlckNvbmZpZ0J1aWxkZXIge1xuICBwcml2YXRlIGxvZzogTG9nZ2VyO1xuXG4gIHByaXZhdGUgY29uZmlnOiBPcmRlcmVyQ29uZmlnID0gcmVhZEZpbGVZYW1sKFxuICAgIHBhdGguam9pbihfX2Rpcm5hbWUsIFwiLi4vLi4vLi4vY29uZmlnL29yZGVyZXIueWFtbFwiKVxuICApIGFzIE9yZGVyZXJDb25maWc7XG5cbiAgY29uc3RydWN0b3IobG9nZ2VyPzogTG9nZ2VyKSB7XG4gICAgaWYgKCFsb2dnZXIpIHRoaXMubG9nID0gTG9nZ2luZy5mb3IoRmFicmljT3JkZXJlckNvbmZpZ0J1aWxkZXIpO1xuICAgIGVsc2UgdGhpcy5sb2cgPSBsb2dnZXIuZm9yKEZhYnJpY09yZGVyZXJDb25maWdCdWlsZGVyLm5hbWUpO1xuICB9XG5cbiAgc2V0S2Fma2Eoa2Fma2E/OiBLYWZrYUNvbmZpZyk6IHRoaXMge1xuICAgIGlmIChrYWZrYSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAoa2Fma2EuUmV0cnkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuU2hvcnRJbnRlcnZhbCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBzaG9ydCBpbnRlcnZhbCB0byAke2thZmthLlJldHJ5LlNob3J0SW50ZXJ2YWx9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlJldHJ5IS5TaG9ydEludGVydmFsID0ga2Fma2EuUmV0cnkuU2hvcnRJbnRlcnZhbDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuU2hvcnRUb3RhbCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBzaG9ydCB0b3RhbCB0byAke2thZmthLlJldHJ5LlNob3J0VG90YWx9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlJldHJ5IS5TaG9ydFRvdGFsID0ga2Fma2EuUmV0cnkuU2hvcnRUb3RhbDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuTG9uZ0ludGVydmFsICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IGxvbmcgaW50ZXJ2YWwgdG8gJHtrYWZrYS5SZXRyeS5Mb25nSW50ZXJ2YWx9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlJldHJ5IS5Mb25nSW50ZXJ2YWwgPSBrYWZrYS5SZXRyeS5Mb25nSW50ZXJ2YWw7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGthZmthLlJldHJ5LkxvbmdUb3RhbCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBsb25nIHRvdGFsIHRvICR7a2Fma2EuUmV0cnkuTG9uZ1RvdGFsfWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5SZXRyeSEuTG9uZ1RvdGFsID0ga2Fma2EuUmV0cnkuTG9uZ1RvdGFsO1xuICAgICAgICB9XG4gICAgICAgIGlmIChrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuRGlhbFRpbWVvdXQgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IG5ldHdvcmsgdGltZW91dHMgZGlhbCB0aW1lb3V0IHRvICR7a2Fma2EuUmV0cnkuTmV0d29ya1RpbWVvdXRzLkRpYWxUaW1lb3V0fWBcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuUmV0cnkhLk5ldHdvcmtUaW1lb3V0cyEuRGlhbFRpbWVvdXQgPVxuICAgICAgICAgICAgICBrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuRGlhbFRpbWVvdXQ7XG4gICAgICAgICAgfVxuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuUmVhZFRpbWVvdXQgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IG5ldHdvcmsgdGltZW91dHMgcmVhZCB0aW1lb3V0IHRvICR7a2Fma2EuUmV0cnkuTmV0d29ya1RpbWVvdXRzLlJlYWRUaW1lb3V0fWBcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuUmV0cnkhLk5ldHdvcmtUaW1lb3V0cyEuUmVhZFRpbWVvdXQgPVxuICAgICAgICAgICAgICBrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuUmVhZFRpbWVvdXQ7XG4gICAgICAgICAgfVxuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuV3JpdGVUaW1lb3V0ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBuZXR3b3JrIHRpbWVvdXRzIHdyaXRlIHRpbWVvdXQgdG8gJHtrYWZrYS5SZXRyeS5OZXR3b3JrVGltZW91dHMuV3JpdGVUaW1lb3V0fWBcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuUmV0cnkhLk5ldHdvcmtUaW1lb3V0cyEuV3JpdGVUaW1lb3V0ID1cbiAgICAgICAgICAgICAga2Fma2EuUmV0cnkuTmV0d29ya1RpbWVvdXRzLldyaXRlVGltZW91dDtcbiAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuTWV0YWRhdGEgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5NZXRhZGF0YS5SZXRyeUJhY2tvZmYgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IG1ldGFkYXRhIHJldHJ5IGJhY2tvZmYgdG8gJHtrYWZrYS5SZXRyeS5NZXRhZGF0YS5SZXRyeUJhY2tvZmZ9YFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5SZXRyeSEuTWV0YWRhdGEhLlJldHJ5QmFja29mZiA9XG4gICAgICAgICAgICAgIGthZmthLlJldHJ5Lk1ldGFkYXRhLlJldHJ5QmFja29mZjtcbiAgICAgICAgICB9XG4gICAgICAgICAgaWYgKGthZmthLlJldHJ5Lk1ldGFkYXRhLlJldHJ5TWF4ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBtZXRhZGF0YSByZXRyeSBtYXggdG8gJHtrYWZrYS5SZXRyeS5NZXRhZGF0YS5SZXRyeU1heH1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlJldHJ5IS5NZXRhZGF0YSEuUmV0cnlNYXggPVxuICAgICAgICAgICAgICBrYWZrYS5SZXRyeS5NZXRhZGF0YS5SZXRyeU1heDtcbiAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuUHJvZHVjZXIgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5Qcm9kdWNlci5SZXRyeUJhY2tvZmYgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IHByb2R1Y2VyIHJldHJ5IGJhY2tvZmYgdG8gJHtrYWZrYS5SZXRyeS5Qcm9kdWNlci5SZXRyeUJhY2tvZmZ9YFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5SZXRyeSEuUHJvZHVjZXIhLlJldHJ5QmFja29mZiA9XG4gICAgICAgICAgICAgIGthZmthLlJldHJ5LlByb2R1Y2VyLlJldHJ5QmFja29mZjtcbiAgICAgICAgICB9XG4gICAgICAgICAgaWYgKGthZmthLlJldHJ5LlByb2R1Y2VyLlJldHJ5TWF4ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgICBgU2V0dGluZyBLYWZrYSByZXRyeSBwcm9kdWNlciByZXRyeSBtYXggdG8gJHtrYWZrYS5SZXRyeS5Qcm9kdWNlci5SZXRyeU1heH1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlJldHJ5IS5Qcm9kdWNlciEuUmV0cnlNYXggPVxuICAgICAgICAgICAgICBrYWZrYS5SZXRyeS5Qcm9kdWNlci5SZXRyeU1heDtcbiAgICAgICAgICB9XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoa2Fma2EuUmV0cnkuQ29uc3VtZXIgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGlmIChrYWZrYS5SZXRyeS5Db25zdW1lci5SZXRyeUJhY2tvZmYgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHJldHJ5IGNvbnN1bWVyIHJldHJ5IGJhY2tvZmYgdG8gJHtrYWZrYS5SZXRyeS5Db25zdW1lci5SZXRyeUJhY2tvZmZ9YFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5SZXRyeSEuQ29uc3VtZXIhLlJldHJ5QmFja29mZiA9XG4gICAgICAgICAgICAgIGthZmthLlJldHJ5LkNvbnN1bWVyLlJldHJ5QmFja29mZjtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgaWYgKGthZmthLlRvcGljICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgaWYgKGthZmthLlRvcGljLlJlcGxpY2F0aW9uRmFjdG9yICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIHRvcGljIHJlcGxpY2F0aW9uIGZhY3RvciB0byAke2thZmthLlRvcGljLlJlcGxpY2F0aW9uRmFjdG9yfWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5Ub3BpYyEuUmVwbGljYXRpb25GYWN0b3IgPVxuICAgICAgICAgICAga2Fma2EuVG9waWMuUmVwbGljYXRpb25GYWN0b3I7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgaWYgKGthZmthLlZlcmJvc2UgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBLYWZrYSB2ZXJib3NlIHRvICR7a2Fma2EuVmVyYm9zZX1gKTtcbiAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlZlcmJvc2UgPSBrYWZrYS5WZXJib3NlO1xuICAgICAgfVxuXG4gICAgICBpZiAoa2Fma2EuVExTICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgaWYgKGthZmthLlRMUy5FbmFibGVkICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBLYWZrYSBUTFMgZW5hYmxlZCB0byAke2thZmthLlRMUy5FbmFibGVkfWApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5UTFMhLkVuYWJsZWQgPSBrYWZrYS5UTFMuRW5hYmxlZDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoa2Fma2EuVExTLkNlcnRpZmljYXRlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICAgIGBTZXR0aW5nIEthZmthIFRMUyBjZXJ0aWZpY2F0ZSB0byAke2thZmthLlRMUy5DZXJ0aWZpY2F0ZX1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuVExTIS5DZXJ0aWZpY2F0ZSA9IGthZmthLlRMUy5DZXJ0aWZpY2F0ZTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChrYWZrYS5UTFMuUHJpdmF0ZUtleSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSBUTFMgcHJpdmF0ZSBrZXkgdG8gJHtrYWZrYS5UTFMuUHJpdmF0ZUtleX1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuVExTIS5Qcml2YXRlS2V5ID0ga2Fma2EuVExTLlByaXZhdGVLZXk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoa2Fma2EuVExTLlJvb3RDQXMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIEthZmthIFRMUyByb290IENBcyB0byAke2thZmthLlRMUy5Sb290Q0FzfWApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5UTFMhLlJvb3RDQXMgPSBrYWZrYS5UTFMuUm9vdENBcztcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICBpZiAoa2Fma2EuVmVyc2lvbiAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIEthZmthIHZlcnNpb24gdG8gJHtrYWZrYS5WZXJzaW9ufWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuVmVyc2lvbiA9IGthZmthLlZlcnNpb247XG4gICAgICB9XG5cbiAgICAgIGlmIChrYWZrYS5TQVNMUGxhaW4gIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBpZiAoa2Fma2EuU0FTTFBsYWluLkVuYWJsZWQgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgS2Fma2EgU0FTTCBwbGFpbiBlbmFibGVkIHRvICR7a2Fma2EuU0FTTFBsYWluLkVuYWJsZWR9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuS2Fma2EhLlNBU0xQbGFpbiEuRW5hYmxlZCA9IGthZmthLlNBU0xQbGFpbi5FbmFibGVkO1xuICAgICAgICB9XG4gICAgICAgIGlmIChrYWZrYS5TQVNMUGxhaW4uVXNlciAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSBTQVNMIHBsYWluIHVzZXIgdG8gJHtrYWZrYS5TQVNMUGxhaW4uVXNlcn1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5LYWZrYSEuU0FTTFBsYWluIS5Vc2VyID0ga2Fma2EuU0FTTFBsYWluLlVzZXI7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGthZmthLlNBU0xQbGFpbi5QYXNzd29yZCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBLYWZrYSBTQVNMIHBsYWluIHBhc3N3b3JkIHRvICR7a2Fma2EuU0FTTFBsYWluLlBhc3N3b3JkfWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkthZmthIS5TQVNMUGxhaW4hLlBhc3N3b3JkID0ga2Fma2EuU0FTTFBsYWluLlBhc3N3b3JkO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0RmlsZUxlZGdlckxvY2F0aW9uKGZpbGVMZWRnZXJMb2NhdGlvbj86IHN0cmluZyk6IHRoaXMge1xuICAgIGlmIChmaWxlTGVkZ2VyTG9jYXRpb24gIT09IHVuZGVmaW5lZCkge1xuICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgZmlsZSBsZWRnZXIgbG9jYXRpb24gdG8gJHtmaWxlTGVkZ2VyTG9jYXRpb259YCk7XG4gICAgICB0aGlzLmNvbmZpZy5GaWxlTGVkZ2VyIS5Mb2NhdGlvbiA9IGZpbGVMZWRnZXJMb2NhdGlvbjtcbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXRBdXRoV2luZG93KGF1dGhXaW5kb3c/OiBzdHJpbmcpOiB0aGlzIHtcbiAgICBpZiAoYXV0aFdpbmRvdyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBhdXRoIHdpbmRvdyB0byAke2F1dGhXaW5kb3d9YCk7XG4gICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5BdXRoZW50aWNhdGlvbiEuVGltZVdpbmRvdyA9IGF1dGhXaW5kb3c7XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0QkNDU1AoYmNjc3A/OiBCQ0NTUENvbmZpZyk6IHRoaXMge1xuICAgIGlmIChiY2NzcCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAoYmNjc3AuRGVmYXVsdCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIEJDQ1NQIGRlZmF1bHQgdG8gJHtiY2NzcC5EZWZhdWx0fWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5CQ0NTUCEuRGVmYXVsdCA9IGJjY3NwLkRlZmF1bHQ7XG4gICAgICB9XG4gICAgICBpZiAoYmNjc3AuU1cgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBpZiAoYmNjc3AuU1cuSGFzaCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgQkNDU1AgU1cgaGFzaCB0byAke2JjY3NwLlNXLkhhc2h9YCk7XG4gICAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQkNDU1AhLlNXIS5IYXNoID0gYmNjc3AuU1cuSGFzaDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoYmNjc3AuU1cuU2VjdXJpdHkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIEJDQ1NQIFNXIHNlY3VyaXR5IHRvICR7YmNjc3AuU1cuU2VjdXJpdHl9YCk7XG4gICAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQkNDU1AhLlNXIS5TZWN1cml0eSA9IGJjY3NwLlNXLlNlY3VyaXR5O1xuICAgICAgICB9XG4gICAgICAgIGlmIChiY2NzcC5TVy5GaWxlS2V5U3RvcmUgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIGlmIChiY2NzcC5TVy5GaWxlS2V5U3RvcmUuS2V5U3RvcmUgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEJDQ1NQIFNXIEZpbGVLZXlTdG9yZSBrZXkgc3RvcmUgdG8gJHtiY2NzcC5TVy5GaWxlS2V5U3RvcmUuS2V5U3RvcmV9YFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJDQ1NQIS5TVyEuRmlsZUtleVN0b3JlIS5LZXlTdG9yZSA9XG4gICAgICAgICAgICAgIGJjY3NwLlNXLkZpbGVLZXlTdG9yZS5LZXlTdG9yZTtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgaWYgKGJjY3NwLlBLQ1MxMSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIGlmIChiY2NzcC5QS0NTMTEuTGlicmFyeSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBCQ0NTUCBQS0NTMTEgbGlicmFyeSB0byAke2JjY3NwLlBLQ1MxMS5MaWJyYXJ5fWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJDQ1NQIS5QS0NTMTEhLkxpYnJhcnkgPSBiY2NzcC5QS0NTMTEuTGlicmFyeTtcbiAgICAgICAgfVxuICAgICAgICBpZiAoYmNjc3AuUEtDUzExLkxhYmVsICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBCQ0NTUCBQS0NTMTEgbGFiZWwgdG8gJHtiY2NzcC5QS0NTMTEuTGFiZWx9YCk7XG4gICAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQkNDU1AhLlBLQ1MxMSEuTGFiZWwgPSBiY2NzcC5QS0NTMTEuTGFiZWw7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGJjY3NwLlBLQ1MxMS5QaW4gIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIEJDQ1NQIFBLQ1MxMSBwaW4gdG8gJHtiY2NzcC5QS0NTMTEuUGlufWApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJDQ1NQIS5QS0NTMTEhLlBpbiA9IGJjY3NwLlBLQ1MxMS5QaW47XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGJjY3NwLlBLQ1MxMS5IYXNoICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBCQ0NTUCBQS0NTMTEgaGFzaCB0byAke2JjY3NwLlBLQ1MxMS5IYXNofWApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJDQ1NQIS5QS0NTMTEhLkhhc2ggPSBiY2NzcC5QS0NTMTEuSGFzaDtcbiAgICAgICAgfVxuICAgICAgICBpZiAoYmNjc3AuUEtDUzExLlNlY3VyaXR5ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICAgIGBTZXR0aW5nIEJDQ1NQIFBLQ1MxMSBzZWN1cml0eSB0byAke2JjY3NwLlBLQ1MxMS5TZWN1cml0eX1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5CQ0NTUCEuUEtDUzExIS5TZWN1cml0eSA9IGJjY3NwLlBLQ1MxMS5TZWN1cml0eTtcbiAgICAgICAgfVxuICAgICAgICBpZiAoYmNjc3AuUEtDUzExLkZpbGVLZXlTdG9yZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgaWYgKGJjY3NwLlBLQ1MxMS5GaWxlS2V5U3RvcmUuS2V5U3RvcmUgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICAgIGBTZXR0aW5nIEJDQ1NQIFBLQ1MxMSBGaWxlS2V5U3RvcmUga2V5IHN0b3JlIHRvICR7YmNjc3AuUEtDUzExLkZpbGVLZXlTdG9yZS5LZXlTdG9yZX1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQkNDU1AhLlBLQ1MxMSEuRmlsZUtleVN0b3JlIS5LZXlTdG9yZSA9XG4gICAgICAgICAgICAgIGJjY3NwLlBLQ1MxMS5GaWxlS2V5U3RvcmUuS2V5U3RvcmU7XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXREZWJ1ZyhkZWJ1Zz86IERlYnVnQ29uZmlnKTogdGhpcyB7XG4gICAgaWYgKGRlYnVnICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmIChkZWJ1Zy5Ccm9hZGNhc3RUcmFjZURpciAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIGRlYnVnIGJyb2FkY2FzdCB0cmFjZSBkaXJlY3RvcnkgdG8gJHtkZWJ1Zy5Ccm9hZGNhc3RUcmFjZURpcn1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkRlYnVnIS5Ccm9hZGNhc3RUcmFjZURpciA9IGRlYnVnLkJyb2FkY2FzdFRyYWNlRGlyO1xuICAgICAgfVxuICAgICAgaWYgKGRlYnVnLkRlbGl2ZXJUcmFjZURpciAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIGRlYnVnIGRlbGl2ZXIgdHJhY2UgZGlyZWN0b3J5IHRvICR7ZGVidWcuRGVsaXZlclRyYWNlRGlyfWBcbiAgICAgICAgKTtcbiAgICAgICAgdGhpcy5jb25maWcuRGVidWchLkRlbGl2ZXJUcmFjZURpciA9IGRlYnVnLkRlbGl2ZXJUcmFjZURpcjtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXRPcGVyYXRpb25zKG9wZXJhdGlvbnM/OiBPcGVyYXRpb25zQ29uZmlnKTogdGhpcyB7XG4gICAgaWYgKG9wZXJhdGlvbnMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgaWYgKG9wZXJhdGlvbnMuTGlzdGVuQWRkcmVzcyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIG9wZXJhdGlvbnMgbGlzdGVuIGFkZHJlc3MgdG8gJHtvcGVyYXRpb25zLkxpc3RlbkFkZHJlc3N9YFxuICAgICAgICApO1xuICAgICAgICB0aGlzLmNvbmZpZy5PcGVyYXRpb25zIS5MaXN0ZW5BZGRyZXNzID0gb3BlcmF0aW9ucy5MaXN0ZW5BZGRyZXNzO1xuICAgICAgfVxuICAgICAgaWYgKG9wZXJhdGlvbnMuVExTICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgaWYgKG9wZXJhdGlvbnMuVExTLkVuYWJsZWQgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIFRMUyBlbmFibGVkIHRvICR7b3BlcmF0aW9ucy5UTFMuRW5hYmxlZH1gKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5PcGVyYXRpb25zIS5UTFMhLkVuYWJsZWQgPSBvcGVyYXRpb25zLlRMUy5FbmFibGVkO1xuICAgICAgICB9XG4gICAgICAgIGlmIChvcGVyYXRpb25zLlRMUy5DZXJ0aWZpY2F0ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBUTFMgY2VydGlmaWNhdGUgdG8gJHtvcGVyYXRpb25zLlRMUy5DZXJ0aWZpY2F0ZX1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5PcGVyYXRpb25zIS5UTFMhLkNlcnRpZmljYXRlID0gb3BlcmF0aW9ucy5UTFMuQ2VydGlmaWNhdGU7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKG9wZXJhdGlvbnMuVExTLlByaXZhdGVLZXkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgVExTIHByaXZhdGUga2V5IHRvICR7b3BlcmF0aW9ucy5UTFMuUHJpdmF0ZUtleX1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5PcGVyYXRpb25zIS5UTFMhLlByaXZhdGVLZXkgPSBvcGVyYXRpb25zLlRMUy5Qcml2YXRlS2V5O1xuICAgICAgICB9XG4gICAgICAgIGlmIChvcGVyYXRpb25zLlRMUy5DbGllbnRBdXRoUmVxdWlyZWQgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgVExTIGNsaWVudCBhdXRoZW50aWNhdGlvbiByZXF1aXJlZCB0byAke29wZXJhdGlvbnMuVExTLkNsaWVudEF1dGhSZXF1aXJlZH1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5PcGVyYXRpb25zIS5UTFMhLkNsaWVudEF1dGhSZXF1aXJlZCA9XG4gICAgICAgICAgICBvcGVyYXRpb25zLlRMUy5DbGllbnRBdXRoUmVxdWlyZWQ7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKG9wZXJhdGlvbnMuVExTLkNsaWVudFJvb3RDQXMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgVExTIGNsaWVudCByb290IENBcyB0byAke29wZXJhdGlvbnMuVExTLkNsaWVudFJvb3RDQXN9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuT3BlcmF0aW9ucyEuVExTIS5DbGllbnRSb290Q0FzID1cbiAgICAgICAgICAgIG9wZXJhdGlvbnMuVExTLkNsaWVudFJvb3RDQXM7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHNldE1ldHJpY3MobWV0cmljcz86IE1ldHJpY3NDb25maWcpOiB0aGlzIHtcbiAgICBpZiAobWV0cmljcyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAobWV0cmljcy5Qcm92aWRlciAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIG1ldHJpY3MgcHJvdmlkZXIgdG8gJHttZXRyaWNzLlByb3ZpZGVyfWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5NZXRyaWNzIS5Qcm92aWRlciA9IG1ldHJpY3MuUHJvdmlkZXI7XG4gICAgICB9XG4gICAgICBpZiAobWV0cmljcy5TdGF0c2QgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICBpZiAobWV0cmljcy5TdGF0c2QuTmV0d29yayAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgc3RhdHNkIG5ldHdvcmsgdG8gJHttZXRyaWNzLlN0YXRzZC5OZXR3b3JrfWApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLk1ldHJpY3MhLlN0YXRzZCEuTmV0d29yayA9IG1ldHJpY3MuU3RhdHNkLk5ldHdvcms7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKG1ldHJpY3MuU3RhdHNkLkFkZHJlc3MgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIHN0YXRzZCBhZGRyZXNzIHRvICR7bWV0cmljcy5TdGF0c2QuQWRkcmVzc31gKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5NZXRyaWNzIS5TdGF0c2QhLkFkZHJlc3MgPSBtZXRyaWNzLlN0YXRzZC5BZGRyZXNzO1xuICAgICAgICB9XG4gICAgICAgIGlmIChtZXRyaWNzLlN0YXRzZC5Xcml0ZUludGVydmFsICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICAgIGBTZXR0aW5nIHN0YXRzZCB3cml0ZSBpbnRlcnZhbCB0byAke21ldHJpY3MuU3RhdHNkLldyaXRlSW50ZXJ2YWx9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuTWV0cmljcyEuU3RhdHNkIS5Xcml0ZUludGVydmFsID1cbiAgICAgICAgICAgIG1ldHJpY3MuU3RhdHNkLldyaXRlSW50ZXJ2YWw7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKG1ldHJpY3MuU3RhdHNkLlByZWZpeCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgc3RhdHNkIHByZWZpeCB0byAke21ldHJpY3MuU3RhdHNkLlByZWZpeH1gKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5NZXRyaWNzIS5TdGF0c2QhLlByZWZpeCA9IG1ldHJpY3MuU3RhdHNkLlByZWZpeDtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHNldFByb2ZpbGUocHJvZmlsZT86IFByb2ZpbGVDb25maWcpOiB0aGlzIHtcbiAgICBpZiAocHJvZmlsZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAocHJvZmlsZS5FbmFibGVkICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgcHJvZmlsZSB0byAke3Byb2ZpbGUuRW5hYmxlZH1gKTtcbiAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuUHJvZmlsZSA9IHByb2ZpbGU7XG4gICAgICB9XG5cbiAgICAgIGlmIChwcm9maWxlLkFkZHJlc3MgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBwcm9maWxlIGFkZHJlc3MgdG8gJHtwcm9maWxlLkFkZHJlc3N9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLlByb2ZpbGUhLkFkZHJlc3MgPSBwcm9maWxlLkFkZHJlc3M7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXRMb2NhbE1TUChtc3A/OiBNU1BDb25maWcpOiB0aGlzIHtcbiAgICBpZiAobXNwICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmIChtc3AuTG9jYWxNU1BEaXIgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBsb2NhbCBNU1AgZGlyZWN0b3J5IHRvICR7bXNwLkxvY2FsTVNQRGlyfWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5Mb2NhbE1TUERpciA9IG1zcC5Mb2NhbE1TUERpcjtcbiAgICAgIH1cbiAgICAgIGlmIChtc3AuTG9jYWxNU1BJRCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIGxvY2FsIE1TUCBJRCB0byAke21zcC5Mb2NhbE1TUElEfWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5Mb2NhbE1TUElEID0gbXNwLkxvY2FsTVNQSUQ7XG4gICAgICB9XG4gICAgfVxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0Qm9vdHN0cmFwKGJvb3Q/OiBCb290c3RyYXBDb25maWcpOiB0aGlzIHtcbiAgICBpZiAoYm9vdCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBpZiAoYm9vdC5Cb290c3RyYXBGaWxlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgYm9vdHN0cmFwIGZpbGUgdG8gJHtib290LkJvb3RzdHJhcEZpbGV9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJvb3RzdHJhcEZpbGUgPSBib290LkJvb3RzdHJhcEZpbGU7XG4gICAgICB9XG5cbiAgICAgIGlmIChib290LkJvb3RzdHJhcE1ldGhvZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBib290c3RyYXAgbWV0aG9kIHRvICR7Ym9vdC5Cb290c3RyYXBNZXRob2R9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkJvb3RzdHJhcE1ldGhvZCA9IGJvb3QuQm9vdHN0cmFwTWV0aG9kO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0Q2x1c3RlcihjbHVzdGVyPzogQ2x1c3RlckNvbmZpZyk6IHRoaXMge1xuICAgIGlmIChjbHVzdGVyICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmIChjbHVzdGVyLlNlbmRCdWZmZXJTaXplICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgc2VuZCBidWZmZXIgc2l6ZSB0byAke2NsdXN0ZXIuU2VuZEJ1ZmZlclNpemV9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkNsdXN0ZXIhLlNlbmRCdWZmZXJTaXplID0gY2x1c3Rlci5TZW5kQnVmZmVyU2l6ZTtcbiAgICAgIH1cblxuICAgICAgaWYgKGNsdXN0ZXIuQ2xpZW50Q2VydGlmaWNhdGUgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICBgU2V0dGluZyBjbGllbnQgY2VydGlmaWNhdGUgdG8gJHtjbHVzdGVyLkNsaWVudENlcnRpZmljYXRlfWBcbiAgICAgICAgKTtcbiAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQ2x1c3RlciEuQ2xpZW50Q2VydGlmaWNhdGUgPVxuICAgICAgICAgIGNsdXN0ZXIuQ2xpZW50Q2VydGlmaWNhdGU7XG4gICAgICB9XG5cbiAgICAgIGlmIChjbHVzdGVyLkNsaWVudFByaXZhdGVLZXkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICBgU2V0dGluZyBjbGllbnQgcHJpdmF0ZSBrZXkgdG8gJHtjbHVzdGVyLkNsaWVudFByaXZhdGVLZXl9YFxuICAgICAgICApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5DbHVzdGVyIS5DbGllbnRQcml2YXRlS2V5ID1cbiAgICAgICAgICBjbHVzdGVyLkNsaWVudFByaXZhdGVLZXk7XG4gICAgICB9XG5cbiAgICAgIGlmIChjbHVzdGVyLkxpc3RlbkFkZHJlc3MgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBsaXN0ZW4gYWRkcmVzcyB0byAke2NsdXN0ZXIuTGlzdGVuQWRkcmVzc31gKTtcbiAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuQ2x1c3RlciEuTGlzdGVuQWRkcmVzcyA9IGNsdXN0ZXIuTGlzdGVuQWRkcmVzcztcbiAgICAgIH1cblxuICAgICAgaWYgKGNsdXN0ZXIuTGlzdGVuUG9ydCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIGxpc3RlbiBwb3J0IHRvICR7Y2x1c3Rlci5MaXN0ZW5Qb3J0fWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5DbHVzdGVyIS5MaXN0ZW5Qb3J0ID0gY2x1c3Rlci5MaXN0ZW5Qb3J0O1xuICAgICAgfVxuXG4gICAgICBpZiAoY2x1c3Rlci5TZXJ2ZXJDZXJ0aWZpY2F0ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIHNlcnZlciBjZXJ0aWZpY2F0ZSB0byAke2NsdXN0ZXIuU2VydmVyQ2VydGlmaWNhdGV9YFxuICAgICAgICApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5DbHVzdGVyIS5TZXJ2ZXJDZXJ0aWZpY2F0ZSA9XG4gICAgICAgICAgY2x1c3Rlci5TZXJ2ZXJDZXJ0aWZpY2F0ZTtcbiAgICAgIH1cblxuICAgICAgaWYgKGNsdXN0ZXIuU2VydmVyUHJpdmF0ZUtleSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIHNlcnZlciBwcml2YXRlIGtleSB0byAke2NsdXN0ZXIuU2VydmVyUHJpdmF0ZUtleX1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkNsdXN0ZXIhLlNlcnZlclByaXZhdGVLZXkgPVxuICAgICAgICAgIGNsdXN0ZXIuU2VydmVyUHJpdmF0ZUtleTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHNldE1TR1NpemUoY2ZnPzogTVNHU2l6ZUNvbmZpZyk6IHRoaXMge1xuICAgIGlmIChjZmcgIT09IHVuZGVmaW5lZCkge1xuICAgICAgaWYgKGNmZy5NYXhSZWN2TXNnU2l6ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIG1heCByZWNlaXZlIG1lc3NhZ2Ugc2l6ZSB0byAke2NmZy5NYXhSZWN2TXNnU2l6ZX1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLk1heFJlY3ZNc2dTaXplID0gY2ZnLk1heFJlY3ZNc2dTaXplO1xuICAgICAgfVxuICAgICAgaWYgKGNmZy5NYXhTZW5kTXNnU2l6ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIG1heCBzZW5kIG1lc3NhZ2Ugc2l6ZSB0byAke2NmZy5NYXhTZW5kTXNnU2l6ZX1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLk1heFNlbmRNc2dTaXplID0gY2ZnLk1heFNlbmRNc2dTaXplO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0S2VlcEFsaXZlKGtlZXBBbGl2ZT86IEtlZXBBbGl2ZUNvbmZpZyk6IHRoaXMge1xuICAgIGlmIChrZWVwQWxpdmUgIT09IHVuZGVmaW5lZCkge1xuICAgICAgaWYgKGtlZXBBbGl2ZS5TZXJ2ZXJJbnRlcnZhbCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIHNlcnZlciBpbnRlcnZhbCB0byAke2tlZXBBbGl2ZS5TZXJ2ZXJJbnRlcnZhbH1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLktlZXBhbGl2ZSEuU2VydmVySW50ZXJ2YWwgPVxuICAgICAgICAgIGtlZXBBbGl2ZS5TZXJ2ZXJJbnRlcnZhbDtcbiAgICAgIH1cbiAgICAgIGlmIChrZWVwQWxpdmUuU2VydmVyTWluSW50ZXJ2YWwgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICB0aGlzLmxvZy5kZWJ1ZyhcbiAgICAgICAgICBgU2V0dGluZyBzZXJ2ZXIgbWluaW11bSBpbnRlcnZhbCB0byAke2tlZXBBbGl2ZS5TZXJ2ZXJNaW5JbnRlcnZhbH1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLktlZXBhbGl2ZSEuU2VydmVyTWluSW50ZXJ2YWwgPVxuICAgICAgICAgIGtlZXBBbGl2ZS5TZXJ2ZXJNaW5JbnRlcnZhbDtcbiAgICAgIH1cbiAgICAgIGlmIChrZWVwQWxpdmUuU2VydmVyVGltZW91dCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKGBTZXR0aW5nIHNlcnZlciB0aW1lb3V0IHRvICR7a2VlcEFsaXZlLlNlcnZlclRpbWVvdXR9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLktlZXBhbGl2ZSEuU2VydmVyVGltZW91dCA9IGtlZXBBbGl2ZS5TZXJ2ZXJUaW1lb3V0O1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0TGlzdGVuQWRkcmVzcyhhZGRyZXNzPzogc3RyaW5nKTogdGhpcyB7XG4gICAgaWYgKGFkZHJlc3MgIT09IHVuZGVmaW5lZCkge1xuICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgbGlzdGVuIGFkZHJlc3MgdG8gJHthZGRyZXNzfWApO1xuICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuTGlzdGVuQWRkcmVzcyA9IGFkZHJlc3M7XG4gICAgfVxuXG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXRQb3J0KHBvcnQ/OiBudW1iZXIpOiB0aGlzIHtcbiAgICBpZiAocG9ydCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICB0aGlzLmxvZy5kZWJ1ZyhgU2V0dGluZyBwb3J0IHRvICR7cG9ydH1gKTtcbiAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLkxpc3RlblBvcnQgPSBwb3J0O1xuICAgIH1cblxuICAgIHJldHVybiB0aGlzO1xuICB9XG5cbiAgc2V0VExTKHRscz86IFRMU0NvbmZpZyk6IHRoaXMge1xuICAgIGlmICh0bHMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgaWYgKHRscy5FbmFibGVkICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgVExTIGVuYWJsZWQgdG8gJHt0bHMuRW5hYmxlZH1gKTtcbiAgICAgICAgdGhpcy5jb25maWcuR2VuZXJhbCEuVExTIS5FbmFibGVkID0gdGxzLkVuYWJsZWQ7XG4gICAgICB9XG4gICAgICBpZiAodGxzLkNlcnRpZmljYXRlICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgVExTIGNlcnRpZmljYXRlIHRvICR7dGxzLkNlcnRpZmljYXRlfWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5UTFMhLkNlcnRpZmljYXRlID0gdGxzLkNlcnRpZmljYXRlO1xuICAgICAgfVxuICAgICAgaWYgKHRscy5Qcml2YXRlS2V5ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgVExTIHByaXZhdGUga2V5IHRvICR7dGxzLlByaXZhdGVLZXl9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLlRMUyEuUHJpdmF0ZUtleSA9IHRscy5Qcml2YXRlS2V5O1xuICAgICAgfVxuICAgICAgaWYgKHRscy5Sb290Q0FzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgVExTIHJvb3QgQ0FzIHRvICR7dGxzLlJvb3RDQXMuam9pbihcIiwgXCIpfWApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5UTFMhLlJvb3RDQXMgPSB0bHMuUm9vdENBcztcbiAgICAgIH1cbiAgICAgIGlmICh0bHMuQ2xpZW50QXV0aFJlcXVpcmVkICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgYFNldHRpbmcgVExTIGNsaWVudCBhdXRoIHJlcXVpcmVkIHRvICR7dGxzLkNsaWVudEF1dGhSZXF1aXJlZH1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkdlbmVyYWwhLlRMUyEuQ2xpZW50QXV0aFJlcXVpcmVkID0gdGxzLkNsaWVudEF1dGhSZXF1aXJlZDtcbiAgICAgIH1cbiAgICAgIGlmICh0bHMuQ2xpZW50Um9vdENBcyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgIGBTZXR0aW5nIFRMUyBjbGllbnQgcm9vdCBDQXMgdG8gJHt0bHMuQ2xpZW50Um9vdENBcy5qb2luKFwiLCBcIil9YFxuICAgICAgICApO1xuICAgICAgICB0aGlzLmNvbmZpZy5HZW5lcmFsIS5UTFMhLkNsaWVudFJvb3RDQXMgPSB0bHMuQ2xpZW50Um9vdENBcztcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIHRoaXM7XG4gIH1cblxuICBzZXRBZG1pbihjZmc/OiBBZG1pbkNvbmZpZyk6IHRoaXMge1xuICAgIGlmIChjZmcgIT09IHVuZGVmaW5lZCkge1xuICAgICAgaWYgKGNmZy5MaXN0ZW5BZGRyZXNzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgYWRtaW4gbGlzdGVuIGFkZHJlc3MgdG8gJHtjZmcuTGlzdGVuQWRkcmVzc31gKTtcbiAgICAgICAgdGhpcy5jb25maWcuQWRtaW4hLkxpc3RlbkFkZHJlc3MgPSBjZmcuTGlzdGVuQWRkcmVzcztcbiAgICAgIH1cbiAgICAgIGlmIChjZmcuVExTICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgaWYgKGNmZy5UTFMuRW5hYmxlZCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgYWRtaW4gVExTIGVuYWJsZWQgdG8gJHtjZmcuVExTLkVuYWJsZWR9YCk7XG4gICAgICAgICAgdGhpcy5jb25maWcuQWRtaW4hLlRMUyEuRW5hYmxlZCA9IGNmZy5UTFMuRW5hYmxlZDtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChjZmcuVExTLlByaXZhdGVLZXkgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgYWRtaW4gVExTIHByaXZhdGUga2V5IHRvICR7Y2ZnLlRMUy5Qcml2YXRlS2V5fWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkFkbWluIS5UTFMhLlByaXZhdGVLZXkgPSBjZmcuVExTLlByaXZhdGVLZXk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoY2ZnLlRMUy5DZXJ0aWZpY2F0ZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBhZG1pbiBUTFMgY2VydGlmaWNhdGUgdG8gJHtjZmcuVExTLkNlcnRpZmljYXRlfWBcbiAgICAgICAgICApO1xuICAgICAgICAgIHRoaXMuY29uZmlnLkFkbWluIS5UTFMhLkNlcnRpZmljYXRlID0gY2ZnLlRMUy5DZXJ0aWZpY2F0ZTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChjZmcuVExTLlJvb3RDQXMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgYFNldHRpbmcgYWRtaW4gVExTIHJvb3QgQ0FzIGZpbGVzOiAke2NmZy5UTFMuUm9vdENBcy5qb2luKFwiLCBcIil9YFxuICAgICAgICAgICk7XG4gICAgICAgICAgdGhpcy5jb25maWcuQWRtaW4hLlRMUyEuUm9vdENBcyA9IGNmZy5UTFMuUm9vdENBcztcbiAgICAgICAgfVxuXG4gICAgICAgIGlmIChjZmcuVExTLkNsaWVudEF1dGhSZXF1aXJlZCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgICBgU2V0dGluZyBhZG1pbiBUTFMgY2xpZW50IGF1dGggcmVxdWlyZWQgdG8gJHtjZmcuVExTLkNsaWVudEF1dGhSZXF1aXJlZH1gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aGlzLmNvbmZpZy5BZG1pbiEuVExTIS5DbGllbnRBdXRoUmVxdWlyZWQgPVxuICAgICAgICAgICAgY2ZnLlRMUy5DbGllbnRBdXRoUmVxdWlyZWQ7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoY2ZnLlRMUy5DbGllbnRSb290Q0FzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICBpZiAoY2ZnLlRMUy5DbGllbnRSb290Q0FzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIHRoaXMubG9nLmRlYnVnKFxuICAgICAgICAgICAgICBgU2V0dGluZyBhZG1pbiBUTFMgY2xpZW50IHJvb3QgQ0FzIGZpbGVzOiAke2NmZy5UTFMuQ2xpZW50Um9vdENBcy5qb2luKFxuICAgICAgICAgICAgICAgIFwiLCBcIlxuICAgICAgICAgICAgICApfWBcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICB0aGlzLmNvbmZpZy5BZG1pbiEuVExTIS5DbGllbnRSb290Q0FzID0gY2ZnLlRMUy5DbGllbnRSb290Q0FzO1xuICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHNldENoYW5uZWxQYXJ0aWNpcGF0aW9uKFxuICAgIGNoYW5uZWxQYXJ0aWNpcGF0aW9uPzogQ2hhbm5lbFBhcnRpY2lwYXRpb25Db25maWdcbiAgKTogdGhpcyB7XG4gICAgaWYgKGNoYW5uZWxQYXJ0aWNpcGF0aW9uICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmIChjaGFubmVsUGFydGljaXBhdGlvbi5FbmFibGVkICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgYFNldHRpbmcgY2hhbm5lbCBwYXJ0aWNpcGF0aW9uIHRvICR7Y2hhbm5lbFBhcnRpY2lwYXRpb24uRW5hYmxlZH1gXG4gICAgICAgICk7XG4gICAgICAgIHRoaXMuY29uZmlnLkNoYW5uZWxQYXJ0aWNpcGF0aW9uIS5FbmFibGVkID1cbiAgICAgICAgICBjaGFubmVsUGFydGljaXBhdGlvbi5FbmFibGVkO1xuICAgICAgfVxuXG4gICAgICBpZiAoY2hhbm5lbFBhcnRpY2lwYXRpb24uTWF4UmVxdWVzdEJvZHlTaXplICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoXG4gICAgICAgICAgYFNldHRpbmcgbWF4IHJlcXVlc3QgYm9keSBzaXplIHRvICR7Y2hhbm5lbFBhcnRpY2lwYXRpb24uTWF4UmVxdWVzdEJvZHlTaXplfWBcbiAgICAgICAgKTtcbiAgICAgICAgdGhpcy5jb25maWcuQ2hhbm5lbFBhcnRpY2lwYXRpb24hLk1heFJlcXVlc3RCb2R5U2l6ZSA9XG4gICAgICAgICAgY2hhbm5lbFBhcnRpY2lwYXRpb24uTWF4UmVxdWVzdEJvZHlTaXplO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIHNldENvbnNlbnN1cyhjb25zZW5zdXM/OiBDb25zZW5zdXNDb25maWcpOiB0aGlzIHtcbiAgICBpZiAoY29uc2Vuc3VzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGlmIChjb25zZW5zdXMuV0FMRGlyICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgV0FMIGRpcmVjdG9yeSB0byAke2NvbnNlbnN1cy5XQUxEaXJ9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkNvbnNlbnN1cyEuV0FMRGlyID0gY29uc2Vuc3VzLldBTERpcjtcbiAgICAgIH1cblxuICAgICAgaWYgKGNvbnNlbnN1cy5TbmFwRGlyICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgdGhpcy5sb2cuZGVidWcoYFNldHRpbmcgc25hcHNob3QgZGlyZWN0b3J5IHRvICR7Y29uc2Vuc3VzLlNuYXBEaXJ9YCk7XG4gICAgICAgIHRoaXMuY29uZmlnLkNvbnNlbnN1cyEuU25hcERpciA9IGNvbnNlbnN1cy5TbmFwRGlyO1xuICAgICAgfVxuICAgIH1cbiAgICByZXR1cm4gdGhpcztcbiAgfVxuXG4gIC8qKlxuICAgKiBAZGVzY3JpcHRpb24gU2F2ZXMgdGhlIGN1cnJlbnQgY29uZmlndXJhdGlvbiB0byBhIGZpbGUuXG4gICAqIEBzdW1tYXJ5IFdyaXRlcyB0aGUgY3VycmVudCBGYWJyaWMgQ0EgU2VydmVyIGNvbmZpZ3VyYXRpb24gdG8gYSBZQU1MIGZpbGUgYXQgdGhlIHNwZWNpZmllZCBwYXRoLiBJZiB0aGUgZGlyZWN0b3J5IGRvZXNuJ3QgZXhpc3QsIGl0IHdpbGwgYmUgY3JlYXRlZC5cbiAgICogQHBhcmFtIHtzdHJpbmd9IGNwYXRoIC0gVGhlIHBhdGggd2hlcmUgdGhlIGNvbmZpZ3VyYXRpb24gZmlsZSBzaG91bGQgYmUgc2F2ZWQuXG4gICAqIEByZXR1cm4ge3RoaXN9IFRoZSBjdXJyZW50IGluc3RhbmNlIG9mIHRoZSBidWlsZGVyIGZvciBtZXRob2QgY2hhaW5pbmcuXG4gICAqIEBleGFtcGxlXG4gICAqIGNvbnN0IGJ1aWxkZXIgPSBuZXcgRmFicmljQ0FTZXJ2ZXJDb21tYW5kQnVpbGRlcigpO1xuICAgKiBidWlsZGVyLnNhdmUoJy9wYXRoL3RvL2NvbmZpZy9mYWJyaWMtY2Etc2VydmVyLnlhbWwnKTtcbiAgICpcbiAgICogQG1lcm1haWRcbiAgICogc2VxdWVuY2VEaWFncmFtXG4gICAqICAgcGFydGljaXBhbnQgQ2xpZW50XG4gICAqICAgcGFydGljaXBhbnQgQnVpbGRlciBhcyBGYWJyaWNDQVNlcnZlckNvbW1hbmRCdWlsZGVyXG4gICAqICAgcGFydGljaXBhbnQgRmlsZVN5c3RlbSBhcyBGaWxlIFN5c3RlbVxuICAgKiAgIENsaWVudC0+PkJ1aWxkZXI6IHNhdmVDb25maWcoJy9wYXRoL3RvL2NvbmZpZy9mYWJyaWMtY2Etc2VydmVyLnlhbWwnKVxuICAgKiAgIEJ1aWxkZXItPj5CdWlsZGVyOiBDaGVjayBpZiBjcGF0aCBpcyBkZWZpbmVkXG4gICAqICAgYWx0IGNwYXRoIGlzIGRlZmluZWRcbiAgICogICAgIEJ1aWxkZXItPj5GaWxlU3lzdGVtOiBDaGVjayBpZiBkaXJlY3RvcnkgZXhpc3RzXG4gICAqICAgICBhbHQgRGlyZWN0b3J5IGRvZXNuJ3QgZXhpc3RcbiAgICogICAgICAgQnVpbGRlci0+PkZpbGVTeXN0ZW06IENyZWF0ZSBkaXJlY3RvcnlcbiAgICogICAgIGVuZFxuICAgKiAgICAgQnVpbGRlci0+PkJ1aWxkZXI6IExvZyBkZWJ1ZyBtZXNzYWdlXG4gICAqICAgICBCdWlsZGVyLT4+RmlsZVN5c3RlbTogV3JpdGUgWUFNTCBjb25maWd1cmF0aW9uIHRvIGZpbGVcbiAgICogICBlbmRcbiAgICogICBCdWlsZGVyLS0+PkNsaWVudDogUmV0dXJuIHRoaXNcbiAgICovXG4gIHNhdmUoY3BhdGg/OiBzdHJpbmcpOiB0aGlzIHtcbiAgICBpZiAoY3BhdGggPT09IHVuZGVmaW5lZCkgcmV0dXJuIHRoaXM7XG5cbiAgICBpZiAoIWZzLmV4aXN0c1N5bmMocGF0aC5qb2luKGNwYXRoKSkpXG4gICAgICBmcy5ta2RpclN5bmMocGF0aC5qb2luKGNwYXRoKSwgeyByZWN1cnNpdmU6IHRydWUgfSk7XG5cbiAgICBpZiAoIWNwYXRoLmVuZHNXaXRoKFwiLnlhbWxcIikpIGNwYXRoID0gcGF0aC5qb2luKGNwYXRoLCBcIm9yZGVyZXIueWFtbFwiKTtcblxuICAgIHRoaXMubG9nLmRlYnVnKGBXcml0aW5nIGNvbmZpZ3VyYXRpb24gdG8gJHtjcGF0aH1gKTtcbiAgICB0aGlzLmxvZy5kZWJ1ZyhgQ29uZmlnIGZpbGU6ICR7SlNPTi5zdHJpbmdpZnkodGhpcy5jb25maWcsIG51bGwsIDIpfWApO1xuICAgIHdyaXRlRmlsZVlhbWwoY3BhdGgsIHRoaXMuY29uZmlnKTtcblxuICAgIHJldHVybiB0aGlzO1xuICB9XG59XG4iXX0=