@aws-cdk/core
Version:
AWS Cloud Development Kit Core Library
164 lines • 17.9 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
const token_1 = require("../token");
const encoding_1 = require("./encoding");
const glob = global;
const STRING_SYMBOL = Symbol.for('@aws-cdk/core.TokenMap.STRING');
const LIST_SYMBOL = Symbol.for('@aws-cdk/core.TokenMap.LIST');
const NUMBER_SYMBOL = Symbol.for('@aws-cdk/core.TokenMap.NUMBER');
/**
* Central place where we keep a mapping from Tokens to their String representation
*
* The string representation is used to embed token into strings,
* and stored to be able to reverse that mapping.
*
* All instances of TokenStringMap share the same storage, so that this process
* works even when different copies of the library are loaded.
*/
class TokenMap {
constructor() {
this.stringTokenMap = new Map();
this.numberTokenMap = new Map();
this.tokenCounter = 0;
}
/**
* Singleton instance of the token string map
*/
static instance() {
if (!glob.__cdkTokenMap) {
glob.__cdkTokenMap = new TokenMap();
}
return glob.__cdkTokenMap;
}
/**
* Generate a unique string for this Token, returning a key
*
* Every call for the same Token will produce a new unique string, no
* attempt is made to deduplicate. Token objects should cache the
* value themselves, if required.
*
* The token can choose (part of) its own representation string with a
* hint. This may be used to produce aesthetically pleasing and
* recognizable token representations for humans.
*/
registerString(token, displayHint) {
return cachedValue(token, STRING_SYMBOL, () => {
const key = this.registerStringKey(token, displayHint);
return `${encoding_1.BEGIN_STRING_TOKEN_MARKER}${key}${encoding_1.END_TOKEN_MARKER}`;
});
}
/**
* Generate a unique string for this Token, returning a key
*/
registerList(token, displayHint) {
return cachedValue(token, LIST_SYMBOL, () => {
const key = this.registerStringKey(token, displayHint);
return [`${encoding_1.BEGIN_LIST_TOKEN_MARKER}${key}${encoding_1.END_TOKEN_MARKER}`];
});
}
/**
* Create a unique number representation for this Token and return it
*/
registerNumber(token) {
return cachedValue(token, NUMBER_SYMBOL, () => {
return this.registerNumberKey(token);
});
}
/**
* Lookup a token from an encoded value
*/
tokenFromEncoding(x) {
if (typeof x === 'string') {
return this.lookupString(x);
}
if (Array.isArray(x)) {
return this.lookupList(x);
}
if (token_1.Token.isUnresolved(x)) {
return x;
}
return undefined;
}
/**
* Reverse a string representation into a Token object
*/
lookupString(s) {
const fragments = this.splitString(s);
if (fragments.tokens.length > 0 && fragments.length === 1) {
return fragments.firstToken;
}
return undefined;
}
/**
* Reverse a string representation into a Token object
*/
lookupList(xs) {
if (xs.length !== 1) {
return undefined;
}
const str = encoding_1.TokenString.forListToken(xs[0]);
const fragments = str.split(this.lookupToken.bind(this));
if (fragments.length === 1) {
return fragments.firstToken;
}
return undefined;
}
/**
* Split a string into literals and Tokens
*/
splitString(s) {
const str = encoding_1.TokenString.forString(s);
return str.split(this.lookupToken.bind(this));
}
/**
* Reverse a number encoding into a Token, or undefined if the number wasn't a Token
*/
lookupNumberToken(x) {
const tokenIndex = encoding_1.extractTokenDouble(x);
if (tokenIndex === undefined) {
return undefined;
}
const t = this.numberTokenMap.get(tokenIndex);
if (t === undefined) {
throw new Error('Encoded representation of unknown number Token found');
}
return t;
}
/**
* Find a Token by key.
*
* This excludes the token markers.
*/
lookupToken(key) {
const token = this.stringTokenMap.get(key);
if (!token) {
throw new Error(`Unrecognized token key: ${key}`);
}
return token;
}
registerStringKey(token, displayHint) {
const counter = this.tokenCounter++;
const representation = (displayHint || 'TOKEN').replace(new RegExp(`[^${encoding_1.VALID_KEY_CHARS}]`, 'g'), '.');
const key = `${representation}.${counter}`;
this.stringTokenMap.set(key, token);
return key;
}
registerNumberKey(token) {
const counter = this.tokenCounter++;
this.numberTokenMap.set(counter, token);
return encoding_1.createTokenDouble(counter);
}
}
exports.TokenMap = TokenMap;
/**
* Get a cached value for an object, storing it on the object in a symbol
*/
function cachedValue(x, sym, prod) {
let cached = x[sym];
if (cached === undefined) {
cached = prod();
Object.defineProperty(x, sym, { value: cached });
}
return cached;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidG9rZW4tbWFwLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsidG9rZW4tbWFwLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7O0FBRUEsb0NBQWlDO0FBQ2pDLHlDQUN5RjtBQUV6RixNQUFNLElBQUksR0FBRyxNQUFhLENBQUM7QUFFM0IsTUFBTSxhQUFhLEdBQUcsTUFBTSxDQUFDLEdBQUcsQ0FBQywrQkFBK0IsQ0FBQyxDQUFDO0FBQ2xFLE1BQU0sV0FBVyxHQUFHLE1BQU0sQ0FBQyxHQUFHLENBQUMsNkJBQTZCLENBQUMsQ0FBQztBQUM5RCxNQUFNLGFBQWEsR0FBRyxNQUFNLENBQUMsR0FBRyxDQUFDLCtCQUErQixDQUFDLENBQUM7QUFFbEU7Ozs7Ozs7O0dBUUc7QUFDSCxNQUFhLFFBQVE7SUFBckI7UUFXbUIsbUJBQWMsR0FBRyxJQUFJLEdBQUcsRUFBdUIsQ0FBQztRQUNoRCxtQkFBYyxHQUFHLElBQUksR0FBRyxFQUF1QixDQUFDO1FBQ3pELGlCQUFZLEdBQUcsQ0FBQyxDQUFDO0lBc0gzQixDQUFDO0lBbElDOztPQUVHO0lBQ0ksTUFBTSxDQUFDLFFBQVE7UUFDcEIsSUFBSSxDQUFDLElBQUksQ0FBQyxhQUFhLEVBQUU7WUFDdkIsSUFBSSxDQUFDLGFBQWEsR0FBRyxJQUFJLFFBQVEsRUFBRSxDQUFDO1NBQ3JDO1FBQ0QsT0FBTyxJQUFJLENBQUMsYUFBYSxDQUFDO0lBQzVCLENBQUM7SUFNRDs7Ozs7Ozs7OztPQVVHO0lBQ0ksY0FBYyxDQUFDLEtBQWtCLEVBQUUsV0FBb0I7UUFDNUQsT0FBTyxXQUFXLENBQUMsS0FBSyxFQUFFLGFBQWEsRUFBRSxHQUFHLEVBQUU7WUFDNUMsTUFBTSxHQUFHLEdBQUcsSUFBSSxDQUFDLGlCQUFpQixDQUFDLEtBQUssRUFBRSxXQUFXLENBQUMsQ0FBQztZQUN2RCxPQUFPLEdBQUcsb0NBQXlCLEdBQUcsR0FBRyxHQUFHLDJCQUFnQixFQUFFLENBQUM7UUFDakUsQ0FBQyxDQUFDLENBQUM7SUFDTCxD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QztJQUNwQyxJQUFJLE1BQU0sS0FBSyxTQUFTLEVBQUU7UUFDeEIsTUFBTSxHQUFHLElBQUksRUFBRSxDQUFDO1FBQ2hCLE1BQU0sQ0FBQyxjQUFjLENBQUMsQ0FBQyxFQUFFLEdBQUcsRUFBRSxFQUFFLEtBQUssRUFBRSxNQUFNLEVBQUUsQ0FBQyxDQUFDO0tBQ2xEO0lBQ0QsT0FBTyxNQUFNLENBQUM7QUFDaEIsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IElSZXNvbHZhYmxlIH0gZnJvbSAnLi4vcmVzb2x2YWJsZSc7XG5pbXBvcnQgeyBUb2tlbml6ZWRTdHJpbmdGcmFnbWVudHMgfSBmcm9tICcuLi9zdHJpbmctZnJhZ21lbnRzJztcbmltcG9ydCB7IFRva2VuIH0gZnJvbSAnLi4vdG9rZW4nO1xuaW1wb3J0IHsgQkVHSU5fTElTVF9UT0tFTl9NQVJLRVIsIEJFR0lOX1NUUklOR19UT0tFTl9NQVJLRVIsIGNyZWF0ZVRva2VuRG91YmxlLFxuICBFTkRfVE9LRU5fTUFSS0VSLCBleHRyYWN0VG9rZW5Eb3VibGUsIFRva2VuU3RyaW5nLCBWQUxJRF9LRVlfQ0hBUlMgfSBmcm9tICcuL2VuY29kaW5nJztcblxuY29uc3QgZ2xvYiA9IGdsb2JhbCBhcyBhbnk7XG5cbmNvbnN0IFNUUklOR19TWU1CT0wgPSBTeW1ib2wuZm9yKCdAYXdzLWNkay9jb3JlLlRva2VuTWFwLlNUUklORycpO1xuY29uc3QgTElTVF9TWU1CT0wgPSBTeW1ib2wuZm9yKCdAYXdzLWNkay9jb3JlLlRva2VuTWFwLkxJU1QnKTtcbmNvbnN0IE5VTUJFUl9TWU1CT0wgPSBTeW1ib2wuZm9yKCdAYXdzLWNkay9jb3JlLlRva2VuTWFwLk5VTUJFUicpO1xuXG4vKipcbiAqIENlbnRyYWwgcGxhY2Ugd2hlcmUgd2Uga2VlcCBhIG1hcHBpbmcgZnJvbSBUb2tlbnMgdG8gdGhlaXIgU3RyaW5nIHJlcHJlc2VudGF0aW9uXG4gKlxuICogVGhlIHN0cmluZyByZXByZXNlbnRhdGlvbiBpcyB1c2VkIHRvIGVtYmVkIHRva2VuIGludG8gc3RyaW5ncyxcbiAqIGFuZCBzdG9yZWQgdG8gYmUgYWJsZSB0byByZXZlcnNlIHRoYXQgbWFwcGluZy5cbiAqXG4gKiBBbGwgaW5zdGFuY2VzIG9mIFRva2VuU3RyaW5nTWFwIHNoYXJlIHRoZSBzYW1lIHN0b3JhZ2UsIHNvIHRoYXQgdGhpcyBwcm9jZXNzXG4gKiB3b3JrcyBldmVuIHdoZW4gZGlmZmVyZW50IGNvcGllcyBvZiB0aGUgbGlicmFyeSBhcmUgbG9hZGVkLlxuICovXG5leHBvcnQgY2xhc3MgVG9rZW5NYXAge1xuICAvKipcbiAgICogU2luZ2xldG9uIGluc3RhbmNlIG9mIHRoZSB0b2tlbiBzdHJpbmcgbWFwXG4gICAqL1xuICBwdWJsaWMgc3RhdGljIGluc3RhbmNlKCk6IFRva2VuTWFwIHtcbiAgICBpZiAoIWdsb2IuX19jZGtUb2tlbk1hcCkge1xuICAgICAgZ2xvYi5fX2Nka1Rva2VuTWFwID0gbmV3IFRva2VuTWFwKCk7XG4gICAgfVxuICAgIHJldHVybiBnbG9iLl9fY2RrVG9rZW5NYXA7XG4gIH1cblxuICBwcml2YXRlIHJlYWRvbmx5IHN0cmluZ1Rva2VuTWFwID0gbmV3IE1hcDxzdHJpbmcsIElSZXNvbHZhYmxlPigpO1xuICBwcml2YXRlIHJlYWRvbmx5IG51bWJlclRva2VuTWFwID0gbmV3IE1hcDxudW1iZXIsIElSZXNvbHZhYmxlPigpO1xuICBwcml2YXRlIHRva2VuQ291bnRlciA9IDA7XG5cbiAgLyoqXG4gICAqIEdlbmVyYXRlIGEgdW5pcXVlIHN0cmluZyBmb3IgdGhpcyBUb2tlbiwgcmV0dXJuaW5nIGEga2V5XG4gICAqXG4gICAqIEV2ZXJ5IGNhbGwgZm9yIHRoZSBzYW1lIFRva2VuIHdpbGwgcHJvZHVjZSBhIG5ldyB1bmlxdWUgc3RyaW5nLCBub1xuICAgKiBhdHRlbXB0IGlzIG1hZGUgdG8gZGVkdXBsaWNhdGUuIFRva2VuIG9iamVjdHMgc2hvdWxkIGNhY2hlIHRoZVxuICAgKiB2YWx1ZSB0aGVtc2VsdmVzLCBpZiByZXF1aXJlZC5cbiAgICpcbiAgICogVGhlIHRva2VuIGNhbiBjaG9vc2UgKHBhcnQgb2YpIGl0cyBvd24gcmVwcmVzZW50YXRpb24gc3RyaW5nIHdpdGggYVxuICAgKiBoaW50LiBUaGlzIG1heSBiZSB1c2VkIHRvIHByb2R1Y2UgYWVzdGhldGljYWxseSBwbGVhc2luZyBhbmRcbiAgICogcmVjb2duaXphYmxlIHRva2VuIHJlcHJlc2VudGF0aW9ucyBmb3IgaHVtYW5zLlxuICAgKi9cbiAgcHVibGljIHJlZ2lzdGVyU3RyaW5nKHRva2VuOiBJUmVzb2x2YWJsZSwgZGlzcGxheUhpbnQ/OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgIHJldHVybiBjYWNoZWRWYWx1ZSh0b2tlbiwgU1RSSU5HX1NZTUJPTCwgKCkgPT4ge1xuICAgICAgY29uc3Qga2V5ID0gdGhpcy5yZWdpc3RlclN0cmluZ0tleSh0b2tlbiwgZGlzcGxheUhpbnQpO1xuICAgICAgcmV0dXJuIGAke0JFR0lOX1NUUklOR19UT0tFTl9NQVJLRVJ9JHtrZXl9JHtFTkRfVE9LRU5fTUFSS0VSfWA7XG4gICAgfSk7XG4gIH1cblxuICAvKipcbiAgICogR2VuZXJhdGUgYSB1bmlxdWUgc3RyaW5nIGZvciB0aGlzIFRva2VuLCByZXR1cm5pbmcgYSBrZXlcbiAgICovXG4gIHB1YmxpYyByZWdpc3Rlckxpc3QodG9rZW46IElSZXNvbHZhYmxlLCBkaXNwbGF5SGludD86IHN0cmluZyk6IHN0cmluZ1tdIHtcbiAgICByZXR1cm4gY2FjaGVkVmFsdWUodG9rZW4sIExJU1RfU1lNQk9MLCAoKSA9PiB7XG4gICAgICBjb25zdCBrZXkgPSB0aGlzLnJlZ2lzdGVyU3RyaW5nS2V5KHRva2VuLCBkaXNwbGF5SGludCk7XG4gICAgICByZXR1cm4gW2Ake0JFR0lOX0xJU1RfVE9LRU5fTUFSS0VSfSR7a2V5fSR7RU5EX1RPS0VOX01BUktFUn1gXTtcbiAgICB9KTtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGUgYSB1bmlxdWUgbnVtYmVyIHJlcHJlc2VudGF0aW9uIGZvciB0aGlzIFRva2VuIGFuZCByZXR1cm4gaXRcbiAgICovXG4gIHB1YmxpYyByZWdpc3Rlck51bWJlcih0b2tlbjogSVJlc29sdmFibGUpOiBudW1iZXIge1xuICAgIHJldHVybiBjYWNoZWRWYWx1ZSh0b2tlbiwgTlVNQkVSX1NZTUJPTCwgKCkgPT4ge1xuICAgICAgcmV0dXJuIHRoaXMucmVnaXN0ZXJOdW1iZXJLZXkodG9rZW4pO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIExvb2t1cCBhIHRva2VuIGZyb20gYW4gZW5jb2RlZCB2YWx1ZVxuICAgKi9cbiAgcHVibGljIHRva2VuRnJvbUVuY29kaW5nKHg6IGFueSk6IElSZXNvbHZhYmxlIHwgdW5kZWZpbmVkIHtcbiAgICBpZiAodHlwZW9mIHggPT09ICdzdHJpbmcnKSB7IHJldHVybiB0aGlzLmxvb2t1cFN0cmluZyh4KTsgfVxuICAgIGlmIChBcnJheS5pc0FycmF5KHgpKSB7IHJldHVybiB0aGlzLmxvb2t1cExpc3QoeCk7IH1cbiAgICBpZiAoVG9rZW4uaXNVbnJlc29sdmVkKHgpKSB7IHJldHVybiB4OyB9XG4gICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXZlcnNlIGEgc3RyaW5nIHJlcHJlc2VudGF0aW9uIGludG8gYSBUb2tlbiBvYmplY3RcbiAgICovXG4gIHB1YmxpYyBsb29rdXBTdHJpbmcoczogc3RyaW5nKTogSVJlc29sdmFibGUgfCB1bmRlZmluZWQge1xuICAgIGNvbnN0IGZyYWdtZW50cyA9IHRoaXMuc3BsaXRTdHJpbmcocyk7XG4gICAgaWYgKGZyYWdtZW50cy50b2tlbnMubGVuZ3RoID4gMCAmJiBmcmFnbWVudHMubGVuZ3RoID09PSAxKSB7XG4gICAgICByZXR1cm4gZnJhZ21lbnRzLmZpcnN0VG9rZW47XG4gICAgfVxuICAgIHJldHVybiB1bmRlZmluZWQ7XG4gIH1cblxuICAvKipcbiAgICogUmV2ZXJzZSBhIHN0cmluZyByZXByZXNlbnRhdGlvbiBpbnRvIGEgVG9rZW4gb2JqZWN0XG4gICAqL1xuICBwdWJsaWMgbG9va3VwTGlzdCh4czogc3RyaW5nW10pOiBJUmVzb2x2YWJsZSB8IHVuZGVmaW5lZCB7XG4gICAgaWYgKHhzLmxlbmd0aCAhPT0gMSkgeyByZXR1cm4gdW5kZWZpbmVkOyB9XG4gICAgY29uc3Qgc3RyID0gVG9rZW5TdHJpbmcuZm9yTGlzdFRva2VuKHhzWzBdKTtcbiAgICBjb25zdCBmcmFnbWVudHMgPSBzdHIuc3BsaXQodGhpcy5sb29rdXBUb2tlbi5iaW5kKHRoaXMpKTtcbiAgICBpZiAoZnJhZ21lbnRzLmxlbmd0aCA9PT0gMSkge1xuICAgICAgcmV0dXJuIGZyYWdtZW50cy5maXJzdFRva2VuO1xuICAgIH1cbiAgICByZXR1cm4gdW5kZWZpbmVkO1xuICB9XG5cbiAgLyoqXG4gICAqIFNwbGl0IGEgc3RyaW5nIGludG8gbGl0ZXJhbHMgYW5kIFRva2Vuc1xuICAgKi9cbiAgcHVibGljIHNwbGl0U3RyaW5nKHM6IHN0cmluZyk6IFRva2VuaXplZFN0cmluZ0ZyYWdtZW50cyB7XG4gICAgY29uc3Qgc3RyID0gVG9rZW5TdHJpbmcuZm9yU3RyaW5nKHMpO1xuICAgIHJldHVybiBzdHIuc3BsaXQodGhpcy5sb29rdXBUb2tlbi5iaW5kKHRoaXMpKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXZlcnNlIGEgbnVtYmVyIGVuY29kaW5nIGludG8gYSBUb2tlbiwgb3IgdW5kZWZpbmVkIGlmIHRoZSBudW1iZXIgd2Fzbid0IGEgVG9rZW5cbiAgICovXG4gIHB1YmxpYyBsb29rdXBOdW1iZXJUb2tlbih4OiBudW1iZXIpOiBJUmVzb2x2YWJsZSB8IHVuZGVmaW5lZCB7XG4gICAgY29uc3QgdG9rZW5JbmRleCA9IGV4dHJhY3RUb2tlbkRvdWJsZSh4KTtcbiAgICBpZiAodG9rZW5JbmRleCA9PT0gdW5kZWZpbmVkKSB7IHJldHVybiB1bmRlZmluZWQ7IH1cbiAgICBjb25zdCB0ID0gdGhpcy5udW1iZXJUb2tlbk1hcC5nZXQodG9rZW5JbmRleCk7XG4gICAgaWYgKHQgPT09IHVuZGVmaW5lZCkgeyB0aHJvdyBuZXcgRXJyb3IoJ0VuY29kZWQgcmVwcmVzZW50YXRpb24gb2YgdW5rbm93biBudW1iZXIgVG9rZW4gZm91bmQnKTsgfVxuICAgIHJldHVybiB0O1xuICB9XG5cbiAgLyoqXG4gICAqIEZpbmQgYSBUb2tlbiBieSBrZXkuXG4gICAqXG4gICAqIFRoaXMgZXhjbHVkZXMgdGhlIHRva2VuIG1hcmtlcnMuXG4gICAqL1xuICBwdWJsaWMgbG9va3VwVG9rZW4oa2V5OiBzdHJpbmcpOiBJUmVzb2x2YWJsZSB7XG4gICAgY29uc3QgdG9rZW4gPSB0aGlzLnN0cmluZ1Rva2VuTWFwLmdldChrZXkpO1xuICAgIGlmICghdG9rZW4pIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgVW5yZWNvZ25pemVkIHRva2VuIGtleTogJHtrZXl9YCk7XG4gICAgfVxuICAgIHJldHVybiB0b2tlbjtcbiAgfVxuXG4gIHByaXZhdGUgcmVnaXN0ZXJTdHJpbmdLZXkodG9rZW46IElSZXNvbHZhYmxlLCBkaXNwbGF5SGludD86IHN0cmluZyk6IHN0cmluZyB7XG4gICAgY29uc3QgY291bnRlciA9IHRoaXMudG9rZW5Db3VudGVyKys7XG4gICAgY29uc3QgcmVwcmVzZW50YXRpb24gPSAoZGlzcGxheUhpbnQgfHwgJ1RPS0VOJykucmVwbGFjZShuZXcgUmVnRXhwKGBbXiR7VkFMSURfS0VZX0NIQVJTfV1gLCAnZycpLCAnLicpO1xuICAgIGNvbnN0IGtleSA9IGAke3JlcHJlc2VudGF0aW9ufS4ke2NvdW50ZXJ9YDtcbiAgICB0aGlzLnN0cmluZ1Rva2VuTWFwLnNldChrZXksIHRva2VuKTtcbiAgICByZXR1cm4ga2V5O1xuICB9XG5cbiAgcHJpdmF0ZSByZWdpc3Rlck51bWJlcktleSh0b2tlbjogSVJlc29sdmFibGUpOiBudW1iZXIge1xuICAgIGNvbnN0IGNvdW50ZXIgPSB0aGlzLnRva2VuQ291bnRlcisrO1xuICAgIHRoaXMubnVtYmVyVG9rZW5NYXAuc2V0KGNvdW50ZXIsIHRva2VuKTtcbiAgICByZXR1cm4gY3JlYXRlVG9rZW5Eb3VibGUoY291bnRlcik7XG4gIH1cbn1cblxuLyoqXG4gKiBHZXQgYSBjYWNoZWQgdmFsdWUgZm9yIGFuIG9iamVjdCwgc3RvcmluZyBpdCBvbiB0aGUgb2JqZWN0IGluIGEgc3ltYm9sXG4gKi9cbmZ1bmN0aW9uIGNhY2hlZFZhbHVlPEEgZXh0ZW5kcyBvYmplY3QsIEI+KHg6IEEsIHN5bTogc3ltYm9sLCBwcm9kOiAoKSA9PiBCKSB7XG4gIGxldCBjYWNoZWQgPSAoeCBhcyBhbnkpW3N5bSBhcyBhbnldO1xuICBpZiAoY2FjaGVkID09PSB1bmRlZmluZWQpIHtcbiAgICBjYWNoZWQgPSBwcm9kKCk7XG4gICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHgsIHN5bSwgeyB2YWx1ZTogY2FjaGVkIH0pO1xuICB9XG4gIHJldHVybiBjYWNoZWQ7XG59XG4iXX0=