com.phloxui
Version:
PhloxUI Ng2+ Framework
264 lines (263 loc) • 26.3 kB
JavaScript
/**
* @fileoverview added by tsickle
* @suppress {checkTypes} checked by tsc
*/
import { Injectable } from '@angular/core';
import { Subject } from 'rxjs/Subject';
/**
* <p style="text-indent: 2em;">
* A <code>ng</code> service which is mainly responsible for providing publish/subscribe <code>Messaging API</code>. You can easily create/publish/subscribe a
* <code>message topic</code> by using this service. This service uses <code>RxJS</code>'s <code>Observable / Subject API</code> as a core engine. Neverthelss, it does not
* require you to have any background on <code>RxJS</code> since it simplifies the <code>RxJS</code>'s API by providing a new way to use it. For example, in
* <code>RxJS</code>'s normal way, you may need to keep a reference to an <code>Subject</code> object all the time in which that the <code>message topic</code>
* is still active. Moreover, if you have more <code>message topic</code>s to handle, you must keep more <code>Subject</code> instance references separately.
* In spite of that, this service diminishes those struggles by mapping each <code>Subject</code> object instance to a <code>topic name</code>. When you want
* to interact with those topics, you could simply supply the <code>topic name</code> to this service. For more information, please see methods of this class
* below.
* </p>
* <p style="text-indent: 2em;">
* If you only want to publish/subscribe to a topic. Please see [[publish]] and [[subscribe]] method below.
* </p>
*
* @author shiorin, tee4cute
*/
var ObservableManager = /** @class */ (function () {
function ObservableManager() {
this.subjects = {};
}
/**
* <p style="text-indent: 1em;">
* Get the <code>RxJS</code>'s <code>Subject</code> object bound to the given topic <code><b>name</b></code>.
* </p>
*
* @param {?} name A message topic name to get.
*
* @return {?} Returns <code>null</code> if the given topic <code><b>name</b></code> is not created yet.
*/
ObservableManager.prototype.getSubject = /**
* <p style="text-indent: 1em;">
* Get the <code>RxJS</code>'s <code>Subject</code> object bound to the given topic <code><b>name</b></code>.
* </p>
*
* @param {?} name A message topic name to get.
*
* @return {?} Returns <code>null</code> if the given topic <code><b>name</b></code> is not created yet.
*/
function (name) {
if (name === null || typeof name !== 'string') {
return null;
}
var /** @type {?} */ re = this.subjects[name];
if (typeof re === 'undefined') {
re = null;
}
return re;
};
/**
* <p style="text-indent: 1em;">
* To check that there already is <code>RxJS</code>'s <code>Subject</code> object bound to the given topic
* <code><b>name</b></code> or not.
* </p>
*
* @param {?} name A message topic name to check.
* @return {?}
*/
ObservableManager.prototype.containsSubject = /**
* <p style="text-indent: 1em;">
* To check that there already is <code>RxJS</code>'s <code>Subject</code> object bound to the given topic
* <code><b>name</b></code> or not.
* </p>
*
* @param {?} name A message topic name to check.
* @return {?}
*/
function (name) {
if (name === null || typeof name !== 'string') {
return false;
}
var /** @type {?} */ subj = this.getSubject(name);
return subj !== null && typeof subj !== 'undefined';
};
/**
* <p style="text-indent: 1em;">
* Create a new <code>Subject</code> (or topic) and map it to the given topic <code><b>name</b></code>. This method will return
* the old object instance if the given <code><b>"name"</b></code> already exists.
* </p>
*
* @param {?} name A message topic name to create <code>Subject</code>.
* @return {?}
*/
ObservableManager.prototype.createSubject = /**
* <p style="text-indent: 1em;">
* Create a new <code>Subject</code> (or topic) and map it to the given topic <code><b>name</b></code>. This method will return
* the old object instance if the given <code><b>"name"</b></code> already exists.
* </p>
*
* @param {?} name A message topic name to create <code>Subject</code>.
* @return {?}
*/
function (name) {
if (name === null || typeof name !== 'string') {
return null;
}
if (this.containsSubject(name)) {
// If the given name already exists, return the old one.
return this.getSubject(name);
}
console.debug('Obsv Mgr: Creating subject for topic "' + name + '".');
this.subjects[name] = new Subject();
return this.subjects[name];
};
/**
* <p style="text-indent: 1em;">
* Subscribe message to the given topic <code><b>name</b></code>. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name A message topic name to subscribe.
* @param {?} handler A message <code>handler function</code> which will be triggered when message arrives.
* @param {?=} errorHandler An error <code>handler function</code> which will be triggered when any error occurs on the [[Observer]].
* @param {?=} completeHandler A <code>handler function</code> which will be triggered when the topic is closed and not publishes any messages anymore.
*
* @return {?} A <code>RxJS</code>'s <code>Subscription</code> object returning from <code>Subject.subscribe()</code> method.
*/
ObservableManager.prototype.subscribe = /**
* <p style="text-indent: 1em;">
* Subscribe message to the given topic <code><b>name</b></code>. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name A message topic name to subscribe.
* @param {?} handler A message <code>handler function</code> which will be triggered when message arrives.
* @param {?=} errorHandler An error <code>handler function</code> which will be triggered when any error occurs on the [[Observer]].
* @param {?=} completeHandler A <code>handler function</code> which will be triggered when the topic is closed and not publishes any messages anymore.
*
* @return {?} A <code>RxJS</code>'s <code>Subscription</code> object returning from <code>Subject.subscribe()</code> method.
*/
function (name, handler, errorHandler, completeHandler) {
if (name === null || typeof name !== 'string') {
return null;
}
if (!this.containsSubject(name)) {
// Auto create topic if does not exist.
this.createSubject(name);
}
console.debug('Obsv Mgr: Subscribing topic "' + name + '".');
return this.subjects[name].subscribe(handler, errorHandler, completeHandler);
};
/**
* <p style="text-indent: 1em;">
* Publish a message (<code><b>data</b></code>) to the given topic <code><b>name</b></code>. The subscriber's <code>handler function</code> will be
* triggered with the given <code><b>data</b></code> passed as a parameter. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name The message topic name to publish.
* @param {?} data The message data to publish.
* @return {?}
*/
ObservableManager.prototype.publish = /**
* <p style="text-indent: 1em;">
* Publish a message (<code><b>data</b></code>) to the given topic <code><b>name</b></code>. The subscriber's <code>handler function</code> will be
* triggered with the given <code><b>data</b></code> passed as a parameter. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name The message topic name to publish.
* @param {?} data The message data to publish.
* @return {?}
*/
function (name, data) {
if (name === null || typeof name !== 'string') {
return;
}
if (!this.containsSubject(name)) {
// Auto create topic if does not exist.
this.createSubject(name);
}
console.debug('Obsv Mgr: Publishing to topic "' + name + '" [data=' + JSON.stringify(data) + '].');
this.getSubject(name).next(data);
};
/**
* <p style="text-indent: 1em;">
* Signal error message to the given topic <code><b>name</b></code>. The subscriber's <code>error function</code> will be
* triggered with the given <code><b>error</b></code> passed as a parameter. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name The message topic name to signal.
* @param {?} error The error message to signal.
* @return {?}
*/
ObservableManager.prototype.error = /**
* <p style="text-indent: 1em;">
* Signal error message to the given topic <code><b>name</b></code>. The subscriber's <code>error function</code> will be
* triggered with the given <code><b>error</b></code> passed as a parameter. This method will automatically create the topic if the given
* topic name is not created yet.
* </p>
*
* @param {?} name The message topic name to signal.
* @param {?} error The error message to signal.
* @return {?}
*/
function (name, error) {
if (name === null || typeof name !== 'string') {
return;
}
if (!this.containsSubject(name)) {
// Auto create topic if does not exist.
this.createSubject(name);
}
console.debug('Obsv Mgr: Signal error to topic "' + name + '" [error=' + JSON.stringify(error) + '].');
this.getSubject(name).error(error);
};
/**
* <p style="text-indent: 1em;">
* Close the specified topic <code><b>name</b></code>. If there is currently no <code>message topic</code> created or no one subsribing to this topic, this
* method will do nothing. Otherwise, the subscriber's <code>complete handler function</code> will be triggered. Note that, we use the method name <code>
* complete</code> instead of <code>close</code> since we try to use the same naming as <code>RxJS</code> does as much as possible.
* </p>
*
* @param {?} name The message topic name to close.
* @return {?}
*/
ObservableManager.prototype.complete = /**
* <p style="text-indent: 1em;">
* Close the specified topic <code><b>name</b></code>. If there is currently no <code>message topic</code> created or no one subsribing to this topic, this
* method will do nothing. Otherwise, the subscriber's <code>complete handler function</code> will be triggered. Note that, we use the method name <code>
* complete</code> instead of <code>close</code> since we try to use the same naming as <code>RxJS</code> does as much as possible.
* </p>
*
* @param {?} name The message topic name to close.
* @return {?}
*/
function (name) {
if (name === null || typeof name !== 'string') {
return;
}
if (!this.containsSubject(name)) {
return;
}
this.getSubject(name).complete();
delete this.subjects[name];
};
ObservableManager.decorators = [
{ type: Injectable },
];
/** @nocollapse */
ObservableManager.ctorParameters = function () { return []; };
return ObservableManager;
}());
export { ObservableManager };
function ObservableManager_tsickle_Closure_declarations() {
/** @type {!Array<{type: !Function, args: (undefined|!Array<?>)}>} */
ObservableManager.decorators;
/**
* @nocollapse
* @type {function(): !Array<(null|{type: ?, decorators: (undefined|!Array<{type: !Function, args: (undefined|!Array<?>)}>)})>}
*/
ObservableManager.ctorParameters;
/** @type {?} */
ObservableManager.prototype.subjects;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiT2JzZXJ2YWJsZU1hbmFnZXIuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiJuZzovL2NvbS5waGxveHVpLyIsInNvdXJjZXMiOlsibGliL3NlcnZpY2UvT2JzZXJ2YWJsZU1hbmFnZXIuc2VydmljZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7O0FBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUMzQyxPQUFPLEVBQUUsT0FBTyxFQUFFLE1BQU0sY0FBYyxDQUFDOzs7Ozs7Ozs7Ozs7Ozs7Ozs7O0lBeUJyQztRQUNFLElBQUksQ0FBQyxRQUFRLEdBQUcsRUFBRSxDQUFDO0tBQ3BCOzs7Ozs7Ozs7O0lBV00sc0NBQVU7Ozs7Ozs7OztjQUFDLElBQVk7UUFDNUIsRUFBRSxDQUFDLENBQUMsSUFBSSxLQUFLLElBQUksSUFBSSxPQUFPLElBQUksS0FBSyxRQUFRLENBQUMsQ0FBQyxDQUFDO1lBQzlDLE1BQU0sQ0FBQyxJQUFJLENBQUM7U0FDYjtRQUVELHFCQUFJLEVBQUUsR0FBUSxJQUFJLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxDQUFDO1FBRWxDLEVBQUUsQ0FBQyxDQUFDLE9BQU8sRUFBRSxLQUFLLFdBQVcsQ0FBQyxDQUFDLENBQUM7WUFDOUIsRUFBRSxHQUFHLElBQUksQ0FBQztTQUNYO1FBRUQsTUFBTSxDQUFDLEVBQUUsQ0FBQzs7Ozs7Ozs7Ozs7SUFXTCwyQ0FBZTs7Ozs7Ozs7O2NBQUMsSUFBWTtRQUNqQyxFQUFFLENBQUMsQ0FBQyxJQUFJLEtBQUssSUFBSSxJQUFJLE9BQU8sSUFBSSxLQUFLLFFBQVEsQ0FBQyxDQUFDLENBQUM7WUFDOUMsTUFBTSxDQUFDLEtBQUssQ0FBQztTQUNkO1FBRUQscUJBQUksSUFBSSxHQUFpQixJQUFJLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxDQUFDO1FBRS9DLE1BQU0sQ0FBQyxJQUFJLEtBQUssSUFBSSxJQUFJLE9BQU8sSUFBSSxLQUFLLFdBQVcsQ0FBQzs7Ozs7Ozs7Ozs7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Q0FBUTs7Ozs7Ozs7OztjQUFDLElBQVk7UUFDMUIsRUFBRSxDQUFDLENBQUMsSUFBSSxLQUFLLElBQUksSUFBSSxPQUFPLElBQUksS0FBSyxRQUFRLENBQUMsQ0FBQyxDQUFDO1lBQzlDLE1BQU0sQ0FBQztTQUNSO1FBRUQsRUFBRSxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsZUFBZSxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQztZQUNoQyxNQUFNLENBQUM7U0FDUjtRQUVELElBQUksQ0FBQyxVQUFVLENBQUMsSUFBSSxDQUFDLENBQUMsUUFBUSxFQUFFLENBQUM7UUFFakMsT0FBTyxJQUFJLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxDQUFDOzs7Z0JBN0s5QixVQUFVOzs7OzRCQXJCWDs7U0FzQmEsaUJBQWlCIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgU3ViamVjdCB9IGZyb20gJ3J4anMvU3ViamVjdCc7XG5pbXBvcnQgeyBTdWJzY3JpcHRpb24gfSBmcm9tICdyeGpzL1N1YnNjcmlwdGlvbic7XG5cbi8qKlxuICogPHAgc3R5bGU9XCJ0ZXh0LWluZGVudDogMmVtO1wiPlxuICogQSA8Y29kZT5uZzwvY29kZT4gc2VydmljZSB3aGljaCBpcyBtYWlubHkgcmVzcG9uc2libGUgZm9yIHByb3ZpZGluZyBwdWJsaXNoL3N1YnNjcmliZSA8Y29kZT5NZXNzYWdpbmcgQVBJPC9jb2RlPi4gWW91IGNhbiBlYXNpbHkgY3JlYXRlL3B1Ymxpc2gvc3Vic2NyaWJlIGFcbiAqIDxjb2RlPm1lc3NhZ2UgdG9waWM8L2NvZGU+IGJ5IHVzaW5nIHRoaXMgc2VydmljZS4gVGhpcyBzZXJ2aWNlIHVzZXMgPGNvZGU+UnhKUzwvY29kZT4ncyA8Y29kZT5PYnNlcnZhYmxlIC8gU3ViamVjdCBBUEk8L2NvZGU+IGFzIGEgY29yZSBlbmdpbmUuIE5ldmVydGhlbHNzLCBpdCBkb2VzIG5vdFxuICogcmVxdWlyZSB5b3UgdG8gaGF2ZSBhbnkgYmFja2dyb3VuZCBvbiA8Y29kZT5SeEpTPC9jb2RlPiBzaW5jZSBpdCBzaW1wbGlmaWVzIHRoZSA8Y29kZT5SeEpTPC9jb2RlPidzIEFQSSBieSBwcm92aWRpbmcgYSBuZXcgd2F5IHRvIHVzZSBpdC4gRm9yIGV4YW1wbGUsIGluXG4gKiA8Y29kZT5SeEpTPC9jb2RlPidzIG5vcm1hbCB3YXksIHlvdSBtYXkgbmVlZCB0byBrZWVwIGEgcmVmZXJlbmNlIHRvIGFuIDxjb2RlPlN1YmplY3Q8L2NvZGU+IG9iamVjdCBhbGwgdGhlIHRpbWUgaW4gd2hpY2ggdGhhdCB0aGUgPGNvZGU+bWVzc2FnZSB0b3BpYzwvY29kZT5cbiAqIGlzIHN0aWxsIGFjdGl2ZS4gTW9yZW92ZXIsIGlmIHlvdSBoYXZlIG1vcmUgPGNvZGU+bWVzc2FnZSB0b3BpYzwvY29kZT5zIHRvIGhhbmRsZSwgeW91IG11c3Qga2VlcCBtb3JlIDxjb2RlPlN1YmplY3Q8L2NvZGU+IGluc3RhbmNlIHJlZmVyZW5jZXMgc2VwYXJhdGVseS5cbiAqIEluIHNwaXRlIG9mIHRoYXQsIHRoaXMgc2VydmljZSBkaW1pbmlzaGVzIHRob3NlIHN0cnVnZ2xlcyBieSBtYXBwaW5nIGVhY2ggPGNvZGU+U3ViamVjdDwvY29kZT4gb2JqZWN0IGluc3RhbmNlIHRvIGEgPGNvZGU+dG9waWMgbmFtZTwvY29kZT4uIFdoZW4geW91IHdhbnRcbiAqIHRvIGludGVyYWN0IHdpdGggdGhvc2UgdG9waWNzLCB5b3UgY291bGQgc2ltcGx5IHN1cHBseSB0aGUgPGNvZGU+dG9waWMgbmFtZTwvY29kZT4gdG8gdGhpcyBzZXJ2aWNlLiBGb3IgbW9yZSBpbmZvcm1hdGlvbiwgcGxlYXNlIHNlZSBtZXRob2RzIG9mIHRoaXMgY2xhc3NcbiAqIGJlbG93LlxuICogPC9wPlxuICogPHAgc3R5bGU9XCJ0ZXh0LWluZGVudDogMmVtO1wiPlxuICogSWYgeW91IG9ubHkgd2FudCB0byBwdWJsaXNoL3N1YnNjcmliZSB0byBhIHRvcGljLiBQbGVhc2Ugc2VlIFtbcHVibGlzaF1dIGFuZCBbW3N1YnNjcmliZV1dIG1ldGhvZCBiZWxvdy5cbiAqIDwvcD5cbiAqXG4gKiBAYXV0aG9yIHNoaW9yaW4sIHRlZTRjdXRlXG4gKi9cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBPYnNlcnZhYmxlTWFuYWdlciB7XG5cbiAgcHJpdmF0ZSBzdWJqZWN0czogYW55O1xuXG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIHRoaXMuc3ViamVjdHMgPSB7fTtcbiAgfVxuXG4gIC8qKlxuICAgKiA8cCBzdHlsZT1cInRleHQtaW5kZW50OiAxZW07XCI+XG4gICAqIEdldCB0aGUgPGNvZGU+UnhKUzwvY29kZT4ncyA8Y29kZT5TdWJqZWN0PC9jb2RlPiBvYmplY3QgYm91bmQgdG8gdGhlIGdpdmVuIHRvcGljIDxjb2RlPjxiPm5hbWU8L2I+PC9jb2RlPi5cbiAgICogPC9wPlxuICAgKlxuICAgKiBAcGFyYW0gbmFtZSBBIG1lc3NhZ2UgdG9waWMgbmFtZSB0byBnZXQuXG4gICAqXG4gICAqIEByZXR1cm4gUmV0dXJucyA8Y29kZT5udWxsPC9jb2RlPiBpZiB0aGUgZ2l2ZW4gdG9waWMgPGNvZGU+PGI+bmFtZTwvYj48L2NvZGU+IGlzIG5vdCBjcmVhdGVkIHlldC5cbiAgICovXG4gIHB1YmxpYyBnZXRTdWJqZWN0KG5hbWU6IHN0cmluZyk6IFN1YmplY3Q8YW55PiB7XG4gICAgaWYgKG5hbWUgPT09IG51bGwgfHwgdHlwZW9mIG5hbWUgIT09ICdzdHJpbmcnKSB7XG4gICAgICByZXR1cm4gbnVsbDtcbiAgICB9XG5cbiAgICBsZXQgcmU6IGFueSA9IHRoaXMuc3ViamVjdHNbbmFtZV07XG5cbiAgICBpZiAodHlwZW9mIHJlID09PSAndW5kZWZpbmVkJykge1xuICAgICAgcmUgPSBudWxsO1xuICAgIH1cblxuICAgIHJldHVybiByZTtcbiAgfVxuXG4gIC8qKlxuICAgKiA8cCBzdHlsZT1cInRleHQtaW5kZW50OiAxZW07XCI+XG4gICAqIFRvIGNoZWNrIHRoYXQgdGhlcmUgYWxyZWFkeSBpcyA8Y29kZT5SeEpTPC9jb2RlPidzIDxjb2RlPlN1YmplY3Q8L2NvZGU+IG9iamVjdCBib3VuZCB0byB0aGUgZ2l2ZW4gdG9waWNcbiAgICogPGNvZGU+PGI+bmFtZTwvYj48L2NvZGU+IG9yIG5vdC5cbiAgICogPC9wPlxuICAgKlxuICAgKiBAcGFyYW0gbmFtZSBBIG1lc3NhZ2UgdG9waWMgbmFtZSB0byBjaGVjay5cbiAgICovXG4gIHB1YmxpYyBjb250YWluc1N1YmplY3QobmFtZTogc3RyaW5nKTogYm9vbGVhbiB7XG4gICAgaWYgKG5hbWUgPT09IG51bGwgfHwgdHlwZW9mIG5hbWUgIT09ICdzdHJpbmcnKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgbGV0IHN1Ymo6IFN1YmplY3Q8YW55PiA9IHRoaXMuZ2V0U3ViamVjdChuYW1lKTtcblxuICAgIHJldHVybiBzdWJqICE9PSBudWxsICYmIHR5cGVvZiBzdWJqICE9PSAndW5kZWZpbmVkJztcbiAgfVxuXG4gIC8qKlxuICAgKiA8cCBzdHlsZT1cInRleHQtaW5kZW50OiAxZW07XCI+XG4gICAqIENyZWF0ZSBhIG5ldyA8Y29kZT5TdWJqZWN0PC9jb2RlPiAob3IgdG9waWMpIGFuZCBtYXAgaXQgdG8gdGhlIGdpdmVuIHRvcGljIDxjb2RlPjxiPm5hbWU8L2I+PC9jb2RlPi4gVGhpcyBtZXRob2Qgd2lsbCByZXR1cm5cbiAgICogdGhlIG9sZCBvYmplY3QgaW5zdGFuY2UgaWYgdGhlIGdpdmVuIDxjb2RlPjxiPlwibmFtZVwiPC9iPjwvY29kZT4gYWxyZWFkeSBleGlzdHMuXG4gICAqIDwvcD5cbiAgICpcbiAgICogQHBhcmFtIG5hbWUgQSBtZXNzYWdlIHRvcGljIG5hbWUgdG8gY3JlYXRlIDxjb2RlPlN1YmplY3Q8L2NvZGU+LlxuICAgKi9cbiAgcHVibGljIGNyZWF0ZVN1YmplY3QobmFtZTogc3RyaW5nKTogU3ViamVjdDxhbnk+IHtcbiAgICBpZiAobmFtZSA9PT0gbnVsbCB8fCB0eXBlb2YgbmFtZSAhPT0gJ3N0cmluZycpIHtcbiAgICAgIHJldHVybiBudWxsO1xuICAgIH1cblxuICAgIGlmICh0aGlzLmNvbnRhaW5zU3ViamVjdChuYW1lKSkge1xuICAgICAgLy8gSWYgdGhlIGdpdmVuIG5hbWUgYWxyZWFkeSBleGlzdHMsIHJldHVybiB0aGUgb2xkIG9uZS5cbiAgICAgIHJldHVybiB0aGlzLmdldFN1YmplY3QobmFtZSk7XG4gICAgfVxuXG4gICAgY29uc29sZS5kZWJ1ZygnT2JzdiBNZ3I6IENyZWF0aW5nIHN1YmplY3QgZm9yIHRvcGljIFwiJyArIG5hbWUgKyAnXCIuJyk7XG5cbiAgICB0aGlzLnN1YmplY3RzW25hbWVdID0gbmV3IFN1YmplY3Q8YW55PigpO1xuXG4gICAgcmV0dXJuIHRoaXMuc3ViamVjdHNbbmFtZV07XG4gIH1cblxuICAvKipcbiAgICogPHAgc3R5bGU9XCJ0ZXh0LWluZGVudDogMWVtO1wiPlxuICAgKiBTdWJzY3JpYmUgbWVzc2FnZSB0byB0aGUgZ2l2ZW4gdG9waWMgPGNvZGU+PGI+bmFtZTwvYj48L2NvZGU+LiBUaGlzIG1ldGhvZCB3aWxsIGF1dG9tYXRpY2FsbHkgY3JlYXRlIHRoZSB0b3BpYyBpZiB0aGUgZ2l2ZW5cbiAgICogdG9waWMgbmFtZSBpcyBub3QgY3JlYXRlZCB5ZXQuXG4gICAqIDwvcD5cbiAgICpcbiAgICogQHBhcmFtIG5hbWUgQSBtZXNzYWdlIHRvcGljIG5hbWUgdG8gc3Vic2NyaWJlLlxuICAgKiBAcGFyYW0gaGFuZGxlciBBIG1lc3NhZ2UgPGNvZGU+aGFuZGxlciBmdW5jdGlvbjwvY29kZT4gd2hpY2ggd2lsbCBiZSB0cmlnZ2VyZWQgd2hlbiBtZXNzYWdlIGFycml2ZXMuXG4gICAqIEBwYXJhbSBlcnJvckhhbmRsZXIgQW4gZXJyb3IgPGNvZGU+aGFuZGxlciBmdW5jdGlvbjwvY29kZT4gd2hpY2ggd2lsbCBiZSB0cmlnZ2VyZWQgd2hlbiBhbnkgZXJyb3Igb2NjdXJzIG9uIHRoZSBbW09ic2VydmVyXV0uXG4gICAqIEBwYXJhbSBjb21wbGV0ZUhhbmRsZXIgQSA8Y29kZT5oYW5kbGVyIGZ1bmN0aW9uPC9jb2RlPiB3aGljaCB3aWxsIGJlIHRyaWdnZXJlZCB3aGVuIHRoZSB0b3BpYyBpcyBjbG9zZWQgYW5kIG5vdCBwdWJsaXNoZXMgYW55IG1lc3NhZ2VzIGFueW1vcmUuXG4gICAqXG4gICAqIEByZXR1cm4gQSA8Y29kZT5SeEpTPC9jb2RlPidzIDxjb2RlPlN1YnNjcmlwdGlvbjwvY29kZT4gb2JqZWN0IHJldHVybmluZyBmcm9tIDxjb2RlPlN1YmplY3Quc3Vic2NyaWJlKCk8L2NvZGU+IG1ldGhvZC5cbiAgICovXG4gIHB1YmxpYyBzdWJzY3JpYmUobmFtZTogc3RyaW5nLCBoYW5kbGVyOiBhbnksIGVycm9ySGFuZGxlcj86IGFueSwgY29tcGxldGVIYW5kbGVyPzogYW55KTogU3Vic2NyaXB0aW9uIHtcbiAgICBpZiAobmFtZSA9PT0gbnVsbCB8fCB0eXBlb2YgbmFtZSAhPT0gJ3N0cmluZycpIHtcbiAgICAgIHJldHVybiBudWxsO1xuICAgIH1cblxuICAgIGlmICghdGhpcy5jb250YWluc1N1YmplY3QobmFtZSkpIHtcbiAgICAgIC8vIEF1dG8gY3JlYXRlIHRvcGljIGlmIGRvZXMgbm90IGV4aXN0LlxuICAgICAgdGhpcy5jcmVhdGVTdWJqZWN0KG5hbWUpO1xuICAgIH1cblxuICAgIGNvbnNvbGUuZGVidWcoJ09ic3YgTWdyOiBTdWJzY3JpYmluZyB0b3BpYyBcIicgKyBuYW1lICsgJ1wiLicpO1xuXG4gICAgcmV0dXJuIHRoaXMuc3ViamVjdHNbbmFtZV0uc3Vic2NyaWJlKGhhbmRsZXIsIGVycm9ySGFuZGxlciwgY29tcGxldGVIYW5kbGVyKTtcbiAgfVxuXG4gIC8qKlxuICAgKiA8cCBzdHlsZT1cInRleHQtaW5kZW50OiAxZW07XCI+XG4gICAqIFB1Ymxpc2ggYSBtZXNzYWdlICg8Y29kZT48Yj5kYXRhPC9iPjwvY29kZT4pIHRvIHRoZSBnaXZlbiB0b3BpYyA8Y29kZT48Yj5uYW1lPC9iPjwvY29kZT4uIFRoZSBzdWJzY3JpYmVyJ3MgPGNvZGU+aGFuZGxlciBmdW5jdGlvbjwvY29kZT4gd2lsbCBiZVxuICAgKiB0cmlnZ2VyZWQgd2l0aCB0aGUgZ2l2ZW4gPGNvZGU+PGI+ZGF0YTwvYj48L2NvZGU+IHBhc3NlZCBhcyBhIHBhcmFtZXRlci4gVGhpcyBtZXRob2Qgd2lsbCBhdXRvbWF0aWNhbGx5IGNyZWF0ZSB0aGUgdG9waWMgaWYgdGhlIGdpdmVuXG4gICAqIHRvcGljIG5hbWUgaXMgbm90IGNyZWF0ZWQgeWV0LlxuICAgKiA8L3A+XG4gICAqXG4gICAqIEBwYXJhbSBuYW1lIFRoZSBtZXNzYWdlIHRvcGljIG5hbWUgdG8gcHVibGlzaC5cbiAgICogQHBhcmFtIGRhdGEgVGhlIG1lc3NhZ2UgZGF0YSB0byBwdWJsaXNoLlxuICAgKi9cbiAgcHVibGljIHB1Ymxpc2gobmFtZTogc3RyaW5nLCBkYXRhOiBhbnkpOiB2b2lkIHtcbiAgICBpZiAobmFtZSA9PT0gbnVsbCB8fCB0eXBlb2YgbmFtZSAhPT0gJ3N0cmluZycpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAoIXRoaXMuY29udGFpbnNTdWJqZWN0KG5hbWUpKSB7XG4gICAgICAvLyBBdXRvIGNyZWF0ZSB0b3BpYyBpZiBkb2VzIG5vdCBleGlzdC5cbiAgICAgIHRoaXMuY3JlYXRlU3ViamVjdChuYW1lKTtcbiAgICB9XG5cbiAgICBjb25zb2xlLmRlYnVnKCdPYnN2IE1ncjogUHVibGlzaGluZyB0byB0b3BpYyBcIicgKyBuYW1lICsgJ1wiIFtkYXRhPScgKyBKU09OLnN0cmluZ2lmeShkYXRhKSArICddLicpO1xuXG4gICAgdGhpcy5nZXRTdWJqZWN0KG5hbWUpLm5leHQoZGF0YSk7XG4gIH1cblxuICAvKipcbiAgICogPHAgc3R5bGU9XCJ0ZXh0LWluZGVudDogMWVtO1wiPlxuICAgKiBTaWduYWwgZXJyb3IgbWVzc2FnZSB0byB0aGUgZ2l2ZW4gdG9waWMgPGNvZGU+PGI+bmFtZTwvYj48L2NvZGU+LiBUaGUgc3Vic2NyaWJlcidzIDxjb2RlPmVycm9yIGZ1bmN0aW9uPC9jb2RlPiB3aWxsIGJlXG4gICAqIHRyaWdnZXJlZCB3aXRoIHRoZSBnaXZlbiA8Y29kZT48Yj5lcnJvcjwvYj48L2NvZGU+IHBhc3NlZCBhcyBhIHBhcmFtZXRlci4gVGhpcyBtZXRob2Qgd2lsbCBhdXRvbWF0aWNhbGx5IGNyZWF0ZSB0aGUgdG9waWMgaWYgdGhlIGdpdmVuXG4gICAqIHRvcGljIG5hbWUgaXMgbm90IGNyZWF0ZWQgeWV0LlxuICAgKiA8L3A+XG4gICAqXG4gICAqIEBwYXJhbSBuYW1lIFRoZSBtZXNzYWdlIHRvcGljIG5hbWUgdG8gc2lnbmFsLlxuICAgKiBAcGFyYW0gZXJyb3IgVGhlIGVycm9yIG1lc3NhZ2UgdG8gc2lnbmFsLlxuICAgKi9cbiAgcHVibGljIGVycm9yKG5hbWU6IHN0cmluZywgZXJyb3I6IGFueSk6IHZvaWQge1xuICAgIGlmIChuYW1lID09PSBudWxsIHx8IHR5cGVvZiBuYW1lICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGlmICghdGhpcy5jb250YWluc1N1YmplY3QobmFtZSkpIHtcbiAgICAgIC8vIEF1dG8gY3JlYXRlIHRvcGljIGlmIGRvZXMgbm90IGV4aXN0LlxuICAgICAgdGhpcy5jcmVhdGVTdWJqZWN0KG5hbWUpO1xuICAgIH1cblxuICAgIGNvbnNvbGUuZGVidWcoJ09ic3YgTWdyOiBTaWduYWwgZXJyb3IgdG8gdG9waWMgXCInICsgbmFtZSArICdcIiBbZXJyb3I9JyArIEpTT04uc3RyaW5naWZ5KGVycm9yKSArICddLicpO1xuXG4gICAgdGhpcy5nZXRTdWJqZWN0KG5hbWUpLmVycm9yKGVycm9yKTtcbiAgfVxuXG4gIC8qKlxuICAgKiA8cCBzdHlsZT1cInRleHQtaW5kZW50OiAxZW07XCI+XG4gICAqIENsb3NlIHRoZSBzcGVjaWZpZWQgdG9waWMgPGNvZGU+PGI+bmFtZTwvYj48L2NvZGU+LiBJZiB0aGVyZSBpcyBjdXJyZW50bHkgbm8gPGNvZGU+bWVzc2FnZSB0b3BpYzwvY29kZT4gY3JlYXRlZCBvciBubyBvbmUgc3Vic3JpYmluZyB0byB0aGlzIHRvcGljLCB0aGlzXG4gICAqIG1ldGhvZCB3aWxsIGRvIG5vdGhpbmcuIE90aGVyd2lzZSwgdGhlIHN1YnNjcmliZXIncyA8Y29kZT5jb21wbGV0ZSBoYW5kbGVyIGZ1bmN0aW9uPC9jb2RlPiB3aWxsIGJlIHRyaWdnZXJlZC4gTm90ZSB0aGF0LCB3ZSB1c2UgdGhlIG1ldGhvZCBuYW1lIDxjb2RlPlxuICAgKiBjb21wbGV0ZTwvY29kZT4gaW5zdGVhZCBvZiA8Y29kZT5jbG9zZTwvY29kZT4gc2luY2Ugd2UgdHJ5IHRvIHVzZSB0aGUgc2FtZSBuYW1pbmcgYXMgPGNvZGU+UnhKUzwvY29kZT4gZG9lcyBhcyBtdWNoIGFzIHBvc3NpYmxlLlxuICAgKiA8L3A+XG4gICAqXG4gICAqIEBwYXJhbSBuYW1lIFRoZSBtZXNzYWdlIHRvcGljIG5hbWUgdG8gY2xvc2UuXG4gICAqL1xuICBwdWJsaWMgY29tcGxldGUobmFtZTogc3RyaW5nKTogdm9pZCB7XG4gICAgaWYgKG5hbWUgPT09IG51bGwgfHwgdHlwZW9mIG5hbWUgIT09ICdzdHJpbmcnKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgaWYgKCF0aGlzLmNvbnRhaW5zU3ViamVjdChuYW1lKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuZ2V0U3ViamVjdChuYW1lKS5jb21wbGV0ZSgpO1xuXG4gICAgZGVsZXRlIHRoaXMuc3ViamVjdHNbbmFtZV07XG4gIH1cblxufVxuIl19