@singleton-i18n/angular-client
Version:
Singleton client code for Angular 10.
305 lines • 32.2 kB
JavaScript
/*
* Copyright 2019-2021 VMware, Inc.
* SPDX-License-Identifier: EPL-2.0
*/
import { NgModule, Pipe, Injectable } from '@angular/core';
import { Directive, ElementRef, Input } from '@angular/core';
import { Subject, BehaviorSubject, of } from 'rxjs';
import { DateFormatter } from './src/formatters/date.formatter';
import { L10nService } from './src/services/l10n.service';
import { I18nService } from './src/services/i18n.service';
import { VIPService } from './src/services/vip.service';
import { PatternCategories, getNameSpace } from './src/config';
import { VIPServiceConstants } from './src/constants';
import { isDefined } from './src/util';
export class MockL10nPipe {
transform(key, value) {
const args = [];
for (let i = 2; i < arguments.length; i++) {
args[i - 2] = arguments[i];
}
return L10nFormat(value, args);
}
}
MockL10nPipe.decorators = [
{ type: Pipe, args: [{ name: 'translate' },] }
];
export class MockL10nPipePlus {
constructor(l10nService) {
this.l10nService = l10nService;
}
transform(key, ...args) {
if (typeof key !== 'string') {
return undefined;
}
if (!isDefined(key)) {
return null;
}
const source = this.l10nService.getSourceString(key);
// If source is undefined return key. Avoid error due to source parsing in L10nFormat.
if (!source) {
return key;
}
return L10nFormat(source, args);
}
}
MockL10nPipePlus.decorators = [
{ type: Pipe, args: [{ name: 'vtranslate' },] }
];
MockL10nPipePlus.ctorParameters = () => [
{ type: L10nService }
];
export class MockCurrencyPipe {
transform(value, currency) {
return {
'USD': '$',
}[currency] + value;
}
}
MockCurrencyPipe.decorators = [
{ type: Pipe, args: [{ name: 'currencyFormat' },] }
];
export class MockDatePipe {
transform(value, format) {
const date = new Date(value);
return {
'medium': `${date.getUTCMonth()}/${date.getUTCDate()}/${date.getUTCFullYear()}`,
'short': `${date.getUTCMonth()}/${date.getUTCDate()}/${date.getUTCFullYear()}`,
}[format] || value;
}
}
MockDatePipe.decorators = [
{ type: Pipe, args: [{ name: 'dateFormat' },] }
];
export class MockNumberFormatPipe {
transform(value, locale) {
return value + '';
}
}
MockNumberFormatPipe.decorators = [
{ type: Pipe, args: [{ name: 'numberFormat' },] }
];
export class MockL10nDirective {
constructor(el, l10nService) {
this.el = el;
this.l10nService = l10nService;
}
ngAfterViewInit() {
if (!isDefined(this.l10n)) {
throw Error('key error');
}
const source = isDefined(this.source) ? this.source : this.l10nService.getSourceString(this.l10n);
// If source is undefined return key. Avoid error due to source parsing in L10nFormat.
this.el.nativeElement.textContent = source ? L10nFormat(source, this.params) : this.l10n;
}
}
MockL10nDirective.decorators = [
{ type: Directive, args: [{
selector: '[l10n]'
},] }
];
MockL10nDirective.ctorParameters = () => [
{ type: ElementRef },
{ type: L10nService }
];
MockL10nDirective.propDecorators = {
l10n: [{ type: Input, args: ['l10n',] }],
source: [{ type: Input }],
comment: [{ type: Input }],
params: [{ type: Input }]
};
export class TranslationLoader {
getTranslationByComponent(url) {
return Promise.resolve('mock');
}
}
export class VIPServiceMock {
constructor(translationLoader) {
this.mainConfig = {};
this.translationLoader = translationLoader;
}
initData(initData) {
this.mainConfig = initData;
// there's really no need to ever call this
return Promise.resolve('mock');
}
registerComponent(config, isMain = false) {
return;
}
getLocale() {
return 'en_US';
}
localeData() {
return {};
}
getI18nScope() {
return [
PatternCategories.CURRENCIES,
PatternCategories.DATE,
PatternCategories.NUMBER,
PatternCategories.PLURAL,
];
}
}
VIPServiceMock.decorators = [
{ type: Injectable }
];
VIPServiceMock.ctorParameters = () => [
{ type: TranslationLoader }
];
export class BaseDataServiceMock {
constructor() {
this.coreService = {
onTranslationChange: new Subject(),
};
this.currentLocale = 'en-US';
this.current = new BehaviorSubject(this.currentLocale);
this.stream = new BehaviorSubject(this.currentLocale);
this.onLocaleChange = new BehaviorSubject(this.currentLocale);
}
}
export class L10nServiceMock extends BaseDataServiceMock {
constructor() {
super();
}
getLongKey(config, key) {
const nameSpace = config ? getNameSpace(config) : undefined;
return nameSpace ? nameSpace
.concat(VIPServiceConstants.NAME_SPACE_SEPARATOR)
.concat(key) : key;
}
translate(key, value, args, comment) {
return L10nFormat(value, args);
}
getTranslation(key, source, args, comment) {
return of(this.translate(key, source, args));
}
getMessage(key, args) {
if (typeof key !== 'string') {
return undefined;
}
if (!isDefined(key)) {
return null;
}
const source = this.getSourceString(key);
// If source is undefined return key. Avoid error due to source parsing in L10nFormat.
if (!source) {
return key;
}
const translation = this.translate(key, source, args);
return translation;
}
// Todo: add method to register sourceBundle under certain namespace.
getSourceString(key) {
return undefined;
}
registerSourceBundles(...args) { }
}
export class I18nServiceMock extends BaseDataServiceMock {
constructor() {
super();
}
formatCurrency(value, currencyCode) {
return {
'USD': '$',
}[currencyCode] + value;
}
formatDate(value, pattern, timezone) {
return value;
}
formatNumber(value, locale) {
return value + '';
}
formatPercent(value, locale) {
return value;
}
getLocalizedPattern(pattern, locale) {
return {
'shortTime': 'h:mm a',
'mediumTime': 'h:mm:ss a',
'longTime': 'h:mm:ss z',
'fullTime': 'h:mm:ss zzzz',
'shortDate': 'M/d/yy',
'mediumDate': 'MMM d, y',
'longDate': 'MMMM d, y',
'fullDate': 'EEEE, MMMM d, y',
'short': 'M/d/yy, h:mm a',
'medium': 'MMM d, y, h:mm:ss a',
'long': 'MMMM d, y, h:mm:ss a z',
'full': 'EEEE, MMMM d, y, h:mm:ss a zzzz',
}[pattern];
}
}
export class VIPModuleMock {
/**
* Use this method in your root module to provide the mocked VIP Service
* @static
* @returns {ModuleWithProviders}
* @memberof VIPModule
*/
static forRoot() {
return {
ngModule: VIPModuleMock,
providers: [
TranslationLoader,
DateFormatter,
{ provide: VIPService, useClass: VIPServiceMock },
{ provide: L10nService, useClass: L10nServiceMock },
{ provide: I18nService, useClass: I18nServiceMock },
]
};
}
}
VIPModuleMock.decorators = [
{ type: NgModule, args: [{
imports: [],
declarations: [
MockL10nPipe,
MockL10nPipePlus,
MockL10nDirective,
MockCurrencyPipe,
MockDatePipe,
MockNumberFormatPipe,
],
exports: [
MockL10nPipe,
MockL10nPipePlus,
MockL10nDirective,
MockCurrencyPipe,
MockDatePipe,
MockNumberFormatPipe,
]
},] }
];
export function L10nFormat(message, args) {
if (message.indexOf('=0') > -1 || message.indexOf('=1') > -1) {
let substr, wordNumber;
switch (args[0]) {
case 0:
substr = '=0';
wordNumber = "";
break;
case 1:
substr = '=1';
wordNumber = "one";
break;
default:
substr = 'other';
wordNumber = args[0].toString();
break;
}
const startSubstr = message.indexOf(substr) + substr.length + 1;
return message.substring(startSubstr, message.indexOf('}', startSubstr)).replace('#', wordNumber);
}
const templateMatcher = /{\s?([\d]*)\s?}/g;
if (args && args.length) {
const strings = [].concat(...args); // args could be an array of arrays, or just an array so flatten
for (let i = 0; i < strings.length; i++) {
message = message.replace(templateMatcher, function (substring, b) {
return (b.trim() === i.toString() && strings[i] != null) ? strings[i] : substring;
});
}
}
return message.trim();
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidmlwLm1vZHVsZS5tb2NrLmpzIiwic291cmNlUm9vdCI6Ii9ob21lL3JsaWdlbmcvUHJvamVjdHMvRGV2b3BzL0NsaWVudF9Bbmd1bGFyX0dpdEh1Yl9OcG1qcy92aXAvY2kvcHViMm9yZy9DbGllbnRfQW5ndWxhcl9HaXRIdWJfTnBtanMvc2luZ2xldG9uL3Byb2plY3RzL2FuZ3VsYXItY2xpZW50LyIsInNvdXJjZXMiOlsidmlwLm1vZHVsZS5tb2NrLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7R0FHRztBQUNILE9BQU8sRUFBdUIsUUFBUSxFQUFFLElBQUksRUFBaUIsVUFBVSxFQUFFLE1BQU0sZUFBZSxDQUFDO0FBQy9GLE9BQU8sRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUFFLEtBQUssRUFBaUIsTUFBTSxlQUFlLENBQUM7QUFDNUUsT0FBTyxFQUFjLE9BQU8sRUFBRSxlQUFlLEVBQUUsRUFBRSxFQUFFLE1BQU0sTUFBTSxDQUFDO0FBRWhFLE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSxpQ0FBaUMsQ0FBQztBQUNoRSxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sNkJBQTZCLENBQUM7QUFDMUQsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLDZCQUE2QixDQUFDO0FBQzFELE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUN4RCxPQUFPLEVBQUUsaUJBQWlCLEVBQWEsWUFBWSxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQzFFLE9BQU8sRUFBRSxtQkFBbUIsRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBQ3RELE9BQU8sRUFBRSxTQUFTLEVBQUUsTUFBTSxZQUFZLENBQUM7QUFHdkMsTUFBTSxPQUFPLFlBQVk7SUFDckIsU0FBUyxDQUFDLEdBQVcsRUFBRSxLQUFhO1FBQ2hDLE1BQU0sSUFBSSxHQUFHLEVBQUUsQ0FBQztRQUNoQixLQUFLLElBQUksQ0FBQyxHQUFHLENBQUMsRUFBRSxDQUFDLEdBQUcsU0FBUyxDQUFDLE1BQU0s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QyxPQUFPLENBQUMsZUFBZSxFQUFFLFVBQVUsU0FBaUIsRUFBRSxDQUFTO2dCQUM3RSxPQUFPLENBQUMsQ0FBQyxDQUFDLElBQUksRUFBRSxLQUFLLENBQUMsQ0FBQyxRQUFRLEVBQUUsSUFBSSxPQUFPLENBQUMsQ0FBQyxDQUFDLElBQUksSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLE9BQU8sQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsU0FBUyxDQUFDO1lBQ3RGLENBQUMsQ0FBQyxDQUFDO1NBQ047S0FDSjtJQUNELE9BQU8sT0FBTyxDQUFDLElBQUksRUFBRSxDQUFDO0FBQzFCLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKlxuICogQ29weXJpZ2h0IDIwMTktMjAyMSBWTXdhcmUsIEluYy5cbiAqIFNQRFgtTGljZW5zZS1JZGVudGlmaWVyOiBFUEwtMi4wXG4gKi9cbmltcG9ydCB7IE1vZHVsZVdpdGhQcm92aWRlcnMsIE5nTW9kdWxlLCBQaXBlLCBQaXBlVHJhbnNmb3JtLCBJbmplY3RhYmxlIH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBEaXJlY3RpdmUsIEVsZW1lbnRSZWYsIElucHV0LCBBZnRlclZpZXdJbml0IH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBPYnNlcnZhYmxlLCBTdWJqZWN0LCBCZWhhdmlvclN1YmplY3QsIG9mIH0gZnJvbSAncnhqcyc7XG5cbmltcG9ydCB7IERhdGVGb3JtYXR0ZXIgfSBmcm9tICcuL3NyYy9mb3JtYXR0ZXJzL2RhdGUuZm9ybWF0dGVyJztcbmltcG9ydCB7IEwxMG5TZXJ2aWNlIH0gZnJvbSAnLi9zcmMvc2VydmljZXMvbDEwbi5zZXJ2aWNlJztcbmltcG9ydCB7IEkxOG5TZXJ2aWNlIH0gZnJvbSAnLi9zcmMvc2VydmljZXMvaTE4bi5zZXJ2aWNlJztcbmltcG9ydCB7IFZJUFNlcnZpY2UgfSBmcm9tICcuL3NyYy9zZXJ2aWNlcy92aXAuc2VydmljZSc7XG5pbXBvcnQgeyBQYXR0ZXJuQ2F0ZWdvcmllcywgVklQQ29uZmlnLCBnZXROYW1lU3BhY2UgfSBmcm9tICcuL3NyYy9jb25maWcnO1xuaW1wb3J0IHsgVklQU2VydmljZUNvbnN0YW50cyB9IGZyb20gJy4vc3JjL2NvbnN0YW50cyc7XG5pbXBvcnQgeyBpc0RlZmluZWQgfSBmcm9tICcuL3NyYy91dGlsJztcblxuQFBpcGUoeyBuYW1lOiAndHJhbnNsYXRlJyB9KVxuZXhwb3J0IGNsYXNzIE1vY2tMMTBuUGlwZSBpbXBsZW1lbnRzIFBpcGVUcmFuc2Zvcm0ge1xuICAgIHRyYW5zZm9ybShrZXk6IHN0cmluZywgdmFsdWU6IHN0cmluZyk6IHN0cmluZyB7XG4gICAgICAgIGNvbnN0IGFyZ3MgPSBbXTtcbiAgICAgICAgZm9yIChsZXQgaSA9IDI7IGkgPCBhcmd1bWVudHMubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgICAgIGFyZ3NbaSAtIDJdID0gYXJndW1lbnRzW2ldO1xuICAgICAgICB9XG4gICAgICAgIHJldHVybiBMMTBuRm9ybWF0KHZhbHVlLCBhcmdzKTtcbiAgICB9XG59XG5cbkBQaXBlKHsgbmFtZTogJ3Z0cmFuc2xhdGUnIH0pXG5leHBvcnQgY2xhc3MgTW9ja0wxMG5QaXBlUGx1cyBpbXBsZW1lbnRzIFBpcGVUcmFuc2Zvcm0ge1xuICAgIGNvbnN0cnVjdG9yKHByaXZhdGUgbDEwblNlcnZpY2U6IEwxMG5TZXJ2aWNlKSB7IH1cbiAgICB0cmFuc2Zvcm0oa2V5OiBzdHJpbmcsIC4uLmFyZ3M6IHN0cmluZ1tdKTogc3RyaW5nIHtcbiAgICAgICAgaWYgKHR5cGVvZiBrZXkgIT09ICdzdHJpbmcnKSB7IHJldHVybiB1bmRlZmluZWQ7IH1cbiAgICAgICAgaWYgKCFpc0RlZmluZWQoa2V5KSkge1xuICAgICAgICAgICAgcmV0dXJuIG51bGw7XG4gICAgICAgIH1cbiAgICAgICAgY29uc3Qgc291cmNlID0gdGhpcy5sMTBuU2VydmljZS5nZXRTb3VyY2VTdHJpbmcoa2V5KTtcbiAgICAgICAgLy8gSWYgc291cmNlIGlzIHVuZGVmaW5lZCByZXR1cm4ga2V5LiBBdm9pZCBlcnJvciBkdWUgdG8gc291cmNlIHBhcnNpbmcgaW4gTDEwbkZvcm1hdC5cbiAgICAgICAgaWYgKCFzb3VyY2UpIHsgcmV0dXJuIGtleTsgfVxuICAgICAgICByZXR1cm4gTDEwbkZvcm1hdChzb3VyY2UsIGFyZ3MpO1xuICAgIH1cbn1cblxuQFBpcGUoeyBuYW1lOiAnY3VycmVuY3lGb3JtYXQnIH0pXG5leHBvcnQgY2xhc3MgTW9ja0N1cnJlbmN5UGlwZSBpbXBsZW1lbnRzIFBpcGVUcmFuc2Zvcm0ge1xuICAgIHRyYW5zZm9ybSh2YWx1ZTogc3RyaW5nLCBjdXJyZW5jeTogc3RyaW5nKTogc3RyaW5nIHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgICdVU0QnOiAnJCcsXG4gICAgICAgIH1bY3VycmVuY3ldICsgdmFsdWU7XG4gICAgfVxufVxuXG5AUGlwZSh7IG5hbWU6ICdkYXRlRm9ybWF0JyB9KVxuZXhwb3J0IGNsYXNzIE1vY2tEYXRlUGlwZSBpbXBsZW1lbnRzIFBpcGVUcmFuc2Zvcm0ge1xuICAgIHRyYW5zZm9ybSh2YWx1ZTogc3RyaW5nLCBmb3JtYXQ6IHN0cmluZyk6IHN0cmluZyB7XG4gICAgICAgIGNvbnN0IGRhdGUgPSBuZXcgRGF0ZSh2YWx1ZSk7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgICAnbWVkaXVtJzogYCR7ZGF0ZS5nZXRVVENNb250aCgpfS8ke2RhdGUuZ2V0VVRDRGF0ZSgpfS8ke2RhdGUuZ2V0VVRDRnVsbFllYXIoKX1gLFxuICAgICAgICAgICAgJ3Nob3J0JzogYCR7ZGF0ZS5nZXRVVENNb250aCgpfS8ke2RhdGUuZ2V0VVRDRGF0ZSgpfS8ke2RhdGUuZ2V0VVRDRnVsbFllYXIoKX1gLFxuICAgICAgICB9W2Zvcm1hdF0gfHwgdmFsdWU7XG4gICAgfVxufVxuXG5AUGlwZSh7IG5hbWU6ICdudW1iZXJGb3JtYXQnIH0pXG5leHBvcnQgY2xhc3MgTW9ja051bWJlckZvcm1hdFBpcGUgaW1wbGVtZW50cyBQaXBlVHJhbnNmb3JtIHtcbiAgICB0cmFuc2Zvcm0odmFsdWU6IGFueSwgbG9jYWxlPzogc3RyaW5nKTogc3RyaW5nIHtcbiAgICAgICAgcmV0dXJuIHZhbHVlICsgJyc7XG4gICAgfVxufVxuXG5ARGlyZWN0aXZlKHtcbiAgICBzZWxlY3RvcjogJ1tsMTBuXSdcbn0pXG5leHBvcnQgY2xhc3MgTW9ja0wxMG5EaXJlY3RpdmUgaW1wbGVtZW50cyBBZnRlclZpZXdJbml0IHtcblxuICAgIEBJbnB1dCgnbDEwbicpIGwxMG46IHN0cmluZztcbiAgICBASW5wdXQoKSBzb3VyY2U6IHN0cmluZztcbiAgICBASW5wdXQoKSBjb21tZW50OiBzdHJpbmc7XG4gICAgQElucHV0KCkgcGFyYW1zOiBzdHJpbmdbXTtcbiAgICBjb25zdHJ1Y3Rvcihwcml2YXRlIGVsOiBFbGVtZW50UmVmLCBwcml2YXRlIGwxMG5TZXJ2aWNlOiBMMTBuU2VydmljZSkgeyB9XG5cbiAgICBuZ0FmdGVyVmlld0luaXQoKSB7XG4gICAgICAgIGlmICghaXNEZWZpbmVkKHRoaXMubDEwbikpIHtcbiAgICAgICAgICAgIHRocm93IEVycm9yKCdrZXkgZXJyb3InKTtcbiAgICAgICAgfVxuICAgICAgICBjb25zdCBzb3VyY2UgPSBpc0RlZmluZWQodGhpcy5zb3VyY2UpID8gdGhpcy5zb3VyY2UgOiB0aGlzLmwxMG5TZXJ2aWNlLmdldFNvdXJjZVN0cmluZyh0aGlzLmwxMG4pO1xuICAgICAgICAvLyBJZiBzb3VyY2UgaXMgdW5kZWZpbmVkIHJldHVybiBrZXkuIEF2b2lkIGVycm9yIGR1ZSB0byBzb3VyY2UgcGFyc2luZyBpbiBMMTBuRm9ybWF0LlxuICAgICAgICB0aGlzLmVsLm5hdGl2ZUVsZW1lbnQudGV4dENvbnRlbnQgPSBzb3VyY2UgPyBMMTBuRm9ybWF0KHNvdXJjZSwgdGhpcy5wYXJhbXMpIDogdGhpcy5sMTBuO1xuICAgIH1cblxufVxuXG5cbmV4cG9ydCBjbGFzcyBUcmFuc2xhdGlvbkxvYWRlciB7XG4gICAgZ2V0VHJhbnNsYXRpb25CeUNvbXBvbmVudCh1cmw6IHN0cmluZyk6IFByb21pc2U8YW55PiB7XG4gICAgICAgIHJldHVybiBQcm9taXNlLnJlc29sdmUoJ21vY2snKTtcbiAgICB9XG59XG5cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBWSVBTZXJ2aWNlTW9jayB7XG4gICAgcHJpdmF0ZSB0cmFuc2xhdGlvbkxvYWRlcjogVHJhbnNsYXRpb25Mb2FkZXI7XG4gICAgcHVibGljIG1haW5Db25maWc6IGFueSA9IHt9O1xuXG4gICAgY29uc3RydWN0b3IodHJhbnNsYXRpb25Mb2FkZXI6IFRyYW5zbGF0aW9uTG9hZGVyKSB7XG4gICAgICAgIHRoaXMudHJhbnNsYXRpb25Mb2FkZXIgPSB0cmFuc2xhdGlvbkxvYWRlcjtcbiAgICB9XG5cbiAgICBpbml0RGF0YShpbml0RGF0YTogVklQQ29uZmlnKTogUHJvbWlzZTxhbnk+IHtcbiAgICAgICAgdGhpcy5tYWluQ29uZmlnID0gaW5pdERhdGE7XG4gICAgICAgIC8vIHRoZXJlJ3MgcmVhbGx5IG5vIG5lZWQgdG8gZXZlciBjYWxsIHRoaXNcbiAgICAgICAgcmV0dXJuIFByb21pc2UucmVzb2x2ZSgnbW9jaycpO1xuICAgIH1cblxuICAgIHJlZ2lzdGVyQ29tcG9uZW50KGNvbmZpZzogVklQQ29uZmlnLCBpc01haW46IGJvb2xlYW4gPSBmYWxzZSkge1xuICAgICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgZ2V0TG9jYWxlKCk6IHN0cmluZyB7XG4gICAgICAgIHJldHVybiAnZW5fVVMnO1xuICAgIH1cblxuICAgIGxvY2FsZURhdGEoKSB7XG4gICAgICAgIHJldHVybiB7fTtcbiAgICB9XG5cbiAgICBnZXRJMThuU2NvcGUoKTogUGF0dGVybkNhdGVnb3JpZXNbXSB7XG4gICAgICAgIHJldHVybiBbXG4gICAgICAgICAgICBQYXR0ZXJuQ2F0ZWdvcmllcy5DVVJSRU5DSUVTLFxuICAgICAgICAgICAgUGF0dGVybkNhdGVnb3JpZXMuREFURSxcbiAgICAgICAgICAgIFBhdHRlcm5DYXRlZ29yaWVzLk5VTUJFUixcbiAgICAgICAgICAgIFBhdHRlcm5DYXRlZ29yaWVzLlBMVVJBTCxcbiAgICAgICAgXTtcbiAgICB9XG59XG5cbmV4cG9ydCBjbGFzcyBCYXNlRGF0YVNlcnZpY2VNb2NrIHtcbiAgICBjb3JlU2VydmljZSA9IHtcbiAgICAgICAgb25UcmFuc2xhdGlvbkNoYW5nZTogbmV3IFN1YmplY3QoKSxcbiAgICB9O1xuICAgIGN1cnJlbnRMb2NhbGUgPSAnZW4tVVMnO1xuXG4gICAgY3VycmVudCA9IG5ldyBCZWhhdmlvclN1YmplY3QodGhpcy5jdXJyZW50TG9jYWxlKTtcbiAgICBzdHJlYW0gPSBuZXcgQmVoYXZpb3JTdWJqZWN0KHRoaXMuY3VycmVudExvY2FsZSk7XG4gICAgb25Mb2NhbGVDaGFuZ2UgPSBuZXcgQmVoYXZpb3JTdWJqZWN0KHRoaXMuY3VycmVudExvY2FsZSk7XG59XG5cbnR5cGUgc291cmNlQnVuZGxlT2JqZWN0ID0geyBba2V5OiBzdHJpbmddOiBhbnkgfTtcblxuZXhwb3J0IGNsYXNzIEwxMG5TZXJ2aWNlTW9jayBleHRlbmRzIEJhc2VEYXRhU2VydmljZU1vY2sge1xuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgICBzdXBlcigpO1xuICAgIH1cblxuICAgIGdldExvbmdLZXkoY29uZmlnOiBWSVBDb25maWcsIGtleTogc3RyaW5nKSB7XG4gICAgICAgIGNvbnN0IG5hbWVTcGFjZSA9IGNvbmZpZyA/IGdldE5hbWVTcGFjZShjb25maWcpIDogdW5kZWZpbmVkO1xuICAgICAgICByZXR1cm4gbmFtZVNwYWNlID8gbmFtZVNwYWNlXG4gICAgICAgICAgICAuY29uY2F0KFZJUFNlcnZpY2VDb25zdGFudHMuTkFNRV9TUEFDRV9TRVBBUkFUT1IpXG4gICAgICAgICAgICAuY29uY2F0KGtleSkgOiBrZXk7XG4gICAgfVxuXG4gICAgdHJhbnNsYXRlKGtleTogc3RyaW5nLCB2YWx1ZTogc3RyaW5nLCBhcmdzPzogYW55W10sIGNvbW1lbnQ/OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4gTDEwbkZvcm1hdCh2YWx1ZSwgYXJncyk7XG4gICAgfVxuXG4gICAgZ2V0VHJhbnNsYXRpb24oa2V5OiBzdHJpbmcsIHNvdXJjZTogc3RyaW5nLCBhcmdzPzogYW55W10sIGNvbW1lbnQ/OiBzdHJpbmcpOiBPYnNlcnZhYmxlPHN0cmluZz4ge1xuICAgICAgICByZXR1cm4gb2YodGhpcy50cmFuc2xhdGUoa2V5LCBzb3VyY2UsIGFyZ3MpKTtcbiAgICB9XG5cbiAgICBnZXRNZXNzYWdlKGtleTogc3RyaW5nLCBhcmdzPzogYW55W10pOiBzdHJpbmcge1xuICAgICAgICBpZiAodHlwZW9mIGtleSAhPT0gJ3N0cmluZycpIHsgcmV0dXJuIHVuZGVmaW5lZDsgfVxuICAgICAgICBpZiAoIWlzRGVmaW5lZChrZXkpKSB7XG4gICAgICAgICAgICByZXR1cm4gbnVsbDtcbiAgICAgICAgfVxuICAgICAgICBjb25zdCBzb3VyY2UgPSB0aGlzLmdldFNvdXJjZVN0cmluZyhrZXkpO1xuICAgICAgICAvLyBJZiBzb3VyY2UgaXMgdW5kZWZpbmVkIHJldHVybiBrZXkuIEF2b2lkIGVycm9yIGR1ZSB0byBzb3VyY2UgcGFyc2luZyBpbiBMMTBuRm9ybWF0LlxuICAgICAgICBpZiAoIXNvdXJjZSkgeyByZXR1cm4ga2V5OyB9XG4gICAgICAgIGNvbnN0IHRyYW5zbGF0aW9uID0gdGhpcy50cmFuc2xhdGUoa2V5LCBzb3VyY2UsIGFyZ3MpO1xuICAgICAgICByZXR1cm4gdHJhbnNsYXRpb247XG4gICAgfVxuXG4gICAgLy8gVG9kbzogYWRkIG1ldGhvZCB0byByZWdpc3RlciBzb3VyY2VCdW5kbGUgdW5kZXIgY2VydGFpbiBuYW1lc3BhY2UuXG4gICAgZ2V0U291cmNlU3RyaW5nKGtleTogc3RyaW5nKTogc3RyaW5nIHtcbiAgICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICB9XG5cbiAgICByZWdpc3RlclNvdXJjZUJ1bmRsZXMoLi4uYXJnczogc291cmNlQnVuZGxlT2JqZWN0W10pOiB2b2lkIHsgfVxufVxuXG5leHBvcnQgY2xhc3MgSTE4blNlcnZpY2VNb2NrIGV4dGVuZHMgQmFzZURhdGFTZXJ2aWNlTW9jayB7XG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICAgIHN1cGVyKCk7XG4gICAgfVxuXG4gICAgcHVibGljIGZvcm1hdEN1cnJlbmN5KHZhbHVlOiBhbnksIGN1cnJlbmN5Q29kZTogc3RyaW5nKTogYW55IHtcbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgICdVU0QnOiAnJCcsXG4gICAgICAgIH1bY3VycmVuY3lDb2RlXSArIHZhbHVlO1xuICAgIH1cblxuICAgIHB1YmxpYyBmb3JtYXREYXRlKHZhbHVlOiBhbnksIHBhdHRlcm46IHN0cmluZywgdGltZXpvbmU/OiBzdHJpbmcpOiBhbnkge1xuICAgICAgICByZXR1cm4gdmFsdWU7XG4gICAgfVxuXG4gICAgcHVibGljIGZvcm1hdE51bWJlcih2YWx1ZTogYW55LCBsb2NhbGU/OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4gdmFsdWUgKyAnJztcbiAgICB9XG5cbiAgICBwdWJsaWMgZm9ybWF0UGVyY2VudCh2YWx1ZTogYW55LCBsb2NhbGU/OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4gdmFsdWU7XG4gICAgfVxuXG4gICAgcHVibGljIGdldExvY2FsaXplZFBhdHRlcm4ocGF0dGVybjogc3RyaW5nLCBsb2NhbGU/OiBzdHJpbmcpOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4ge1xuICAgICAgICAgICAgJ3Nob3J0VGltZSc6ICdoOm1tIGEnLFxuICAgICAgICAgICAgJ21lZGl1bVRpbWUnOiAnaDptbTpzcyBhJyxcbiAgICAgICAgICAgICdsb25nVGltZSc6ICdoOm1tOnNzIHonLFxuICAgICAgICAgICAgJ2Z1bGxUaW1lJzogJ2g6bW06c3Mgenp6eicsXG4gICAgICAgICAgICAnc2hvcnREYXRlJzogJ00vZC95eScsXG4gICAgICAgICAgICAnbWVkaXVtRGF0ZSc6ICdNTU0gZCwgeScsXG4gICAgICAgICAgICAnbG9uZ0RhdGUnOiAnTU1NTSBkLCB5JyxcbiAgICAgICAgICAgICdmdWxsRGF0ZSc6ICdFRUVFLCBNTU1NIGQsIHknLFxuICAgICAgICAgICAgJ3Nob3J0JzogJ00vZC95eSwgaDptbSBhJyxcbiAgICAgICAgICAgICdtZWRpdW0nOiAnTU1NIGQsIHksIGg6bW06c3MgYScsXG4gICAgICAgICAgICAnbG9uZyc6ICdNTU1NIGQsIHksIGg6bW06c3MgYSB6JyxcbiAgICAgICAgICAgICdmdWxsJzogJ0VFRUUsIE1NTU0gZCwgeSwgaDptbTpzcyBhIHp6enonLFxuICAgICAgICB9W3BhdHRlcm5dO1xuICAgIH1cbn1cblxuQE5nTW9kdWxlKHtcbiAgICBpbXBvcnRzOiBbXSxcbiAgICBkZWNsYXJhdGlvbnM6IFtcbiAgICAgICAgTW9ja0wxMG5QaXBlLFxuICAgICAgICBNb2NrTDEwblBpcGVQbHVzLFxuICAgICAgICBNb2NrTDEwbkRpcmVjdGl2ZSxcbiAgICAgICAgTW9ja0N1cnJlbmN5UGlwZSxcbiAgICAgICAgTW9ja0RhdGVQaXBlLFxuICAgICAgICBNb2NrTnVtYmVyRm9ybWF0UGlwZSxcbiAgICBdLFxuICAgIGV4cG9ydHM6IFtcbiAgICAgICAgTW9ja0wxMG5QaXBlLFxuICAgICAgICBNb2NrTDEwblBpcGVQbHVzLFxuICAgICAgICBNb2NrTDEwbkRpcmVjdGl2ZSxcbiAgICAgICAgTW9ja0N1cnJlbmN5UGlwZSxcbiAgICAgICAgTW9ja0RhdGVQaXBlLFxuICAgICAgICBNb2NrTnVtYmVyRm9ybWF0UGlwZSxcbiAgICBdXG59KVxuZXhwb3J0IGNsYXNzIFZJUE1vZHVsZU1vY2sge1xuICAgIC8qKlxuICAgICAqIFVzZSB0aGlzIG1ldGhvZCBpbiB5b3VyIHJvb3QgbW9kdWxlIHRvIHByb3ZpZGUgdGhlIG1vY2tlZCBWSVAgU2VydmljZVxuICAgICAqIEBzdGF0aWNcbiAgICAgKiBAcmV0dXJucyB7TW9kdWxlV2l0aFByb3ZpZGVyc31cbiAgICAgKiBAbWVtYmVyb2YgVklQTW9kdWxlXG4gICAgICovXG4gICAgc3RhdGljIGZvclJvb3QoKTogTW9kdWxlV2l0aFByb3ZpZGVyczxWSVBNb2R1bGVNb2NrPiB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgICBuZ01vZHVsZTogVklQTW9kdWxlTW9jayxcbiAgICAgICAgICAgIHByb3ZpZGVyczogW1xuICAgICAgICAgICAgICAgIFRyYW5zbGF0aW9uTG9hZGVyLFxuICAgICAgICAgICAgICAgIERhdGVGb3JtYXR0ZXIsXG4gICAgICAgICAgICAgICAgeyBwcm92aWRlOiBWSVBTZXJ2aWNlLCB1c2VDbGFzczogVklQU2VydmljZU1vY2sgfSxcbiAgICAgICAgICAgICAgICB7IHByb3ZpZGU6IEwxMG5TZXJ2aWNlLCB1c2VDbGFzczogTDEwblNlcnZpY2VNb2NrIH0sXG4gICAgICAgICAgICAgICAgeyBwcm92aWRlOiBJMThuU2VydmljZSwgdXNlQ2xhc3M6IEkxOG5TZXJ2aWNlTW9jayB9LFxuICAgICAgICAgICAgXVxuICAgICAgICB9O1xuICAgIH1cbn1cblxuZXhwb3J0IGZ1bmN0aW9uIEwxMG5Gb3JtYXQobWVzc2FnZTogc3RyaW5nLCBhcmdzOiBhbnlbXSkge1xuICAgIGlmIChtZXNzYWdlLmluZGV4T2YoJz0wJyk+LTEgfHwgbWVzc2FnZS5pbmRleE9mKCc9MScpPi0xKSB7XG4gICAgICAgIGxldCBzdWJzdHIsIHdvcmROdW1iZXI6IHN0cmluZztcbiAgICAgICAgc3dpdGNoIChhcmdzWzBdKSB7XG4gICAgICAgICAgICBjYXNlIDA6XG4gICAgICAgICAgICAgICAgc3Vic3RyID0gJz0wJztcbiAgICAgICAgICAgICAgICB3b3JkTnVtYmVyID0gXCJcIjtcbiAgICAgICAgICAgICAgICBicmVhaztcbiAgICAgICAgICAgIGNhc2UgMTpcbiAgICAgICAgICAgICAgICBzdWJzdHIgPSAnPTEnO1xuICAgICAgICAgICAgICAgIHdvcmROdW1iZXIgPSBcIm9uZVwiO1xuICAgICAgICAgICAgICAgIGJyZWFrO1xuICAgICAgICAgICAgZGVmYXVsdDpcbiAgICAgICAgICAgICAgICBzdWJzdHIgPSAnb3RoZXInO1xuICAgICAgICAgICAgICAgIHdvcmROdW1iZXIgPSBhcmdzWzBdLnRvU3RyaW5nKCk7XG4gICAgICAgICAgICAgICAgYnJlYWs7XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCBzdGFydFN1YnN0ciA9IG1lc3NhZ2UuaW5kZXhPZihzdWJzdHIpICsgc3Vic3RyLmxlbmd0aCArIDE7XG4gICAgICAgIHJldHVybiBtZXNzYWdlLnN1YnN0cmluZyhzdGFydFN1YnN0ciwgbWVzc2FnZS5pbmRleE9mKCd9Jywgc3RhcnRTdWJzdHIpKS5yZXBsYWNlKCcjJywgd29yZE51bWJlcik7XG4gICAgfVxuXG4gICAgY29uc3QgdGVtcGxhdGVNYXRjaGVyID0gL3tcXHM/KFtcXGRdKilcXHM/fS9nO1xuXG4gICAgaWYgKGFyZ3MgJiYgYXJncy5sZW5ndGgpIHtcbiAgICAgICAgY29uc3Qgc3RyaW5ncyA9IFtdLmNvbmNhdCguLi5hcmdzKTsgICAvLyBhcmdzIGNvdWxkIGJlIGFuIGFycmF5IG9mIGFycmF5cywgb3IganVzdCBhbiBhcnJheSBzbyBmbGF0dGVuXG4gICAgICAgIGZvciAobGV0IGkgPSAwOyBpIDwgc3RyaW5ncy5sZW5ndGg7IGkrKykge1xuICAgICAgICAgICAgbWVzc2FnZSA9IG1lc3NhZ2UucmVwbGFjZSh0ZW1wbGF0ZU1hdGNoZXIsIGZ1bmN0aW9uIChzdWJzdHJpbmc6IHN0cmluZywgYjogc3RyaW5nKSB7XG4gICAgICAgICAgICAgICAgcmV0dXJuIChiLnRyaW0oKSA9PT0gaS50b1N0cmluZygpICYmIHN0cmluZ3NbaV0gIT0gbnVsbCkgPyBzdHJpbmdzW2ldIDogc3Vic3RyaW5nO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIG1lc3NhZ2UudHJpbSgpO1xufVxuIl19