UNPKG

ngx-router-meta

Version:

Configure HTML meta tags in route configuration of Angular

160 lines 23.8 kB
import { isPlatformServer } from '@angular/common'; import { Inject, Injectable, Optional, PLATFORM_ID, } from '@angular/core'; import { makeStateKey, Meta, Title, TransferState, } from '@angular/platform-browser'; import { Router } from '@angular/router'; import { combineLatest, filter, map, Subject, switchMap, takeUntil, } from 'rxjs'; import { isDataWithMeta, ROUTE_META_CONFIG, } from './router-meta'; import { RouterMetaContextService, } from './router-meta-context.service'; import { isNavigationEndEvent } from './util'; import * as i0 from "@angular/core"; import * as i1 from "@angular/router"; import * as i2 from "@angular/platform-browser"; import * as i3 from "./router-meta-context.service"; const TITLE_STATE = makeStateKey('RouterMetaTitle'); /** * Service responsible for updating meta tags based on router configuration * * To provide context - use {@link RouterMetaContextService} */ export class RouterMetaService { constructor(platformId, config, router, title, meta, contextService, transferState) { this.platformId = platformId; this.config = config; this.router = router; this.title = title; this.meta = meta; this.contextService = contextService; this.transferState = transferState; this.initialized = false; this.metaTags = {}; this.defaultMeta = this.config.defaultMeta || {}; this.originalTitle = this.transferState ? this.transferState.get(TITLE_STATE, this.title.getTitle()) : this.title.getTitle(); this.destroyed$ = new Subject(); this.navigationEnd$ = this.router.events.pipe(filter(isNavigationEndEvent)); this.routeData$ = this.navigationEnd$.pipe(map(() => this.router.routerState.root), map((route) => this.getLastRoute(route)), filter((route) => route.outlet === 'primary'), switchMap((route) => route.data)); } /** * Returns original title of index page. * * If SSR was used with {@link StateTransfer} - * then original title will be preserved between server and client states */ getOriginalTitle() { return this.originalTitle; } /** @internal */ ngOnDestroy() { this.destroyed$.next(); } /** @internal */ _setup() { if (this.initialized) { return; } this.initialized = true; if (this.transferState && isPlatformServer(this.platformId)) { this.transferState.set(TITLE_STATE, this.originalTitle); } combineLatest(this.routeData$, this.contextService.getContext()) .pipe(takeUntil(this.destroyed$)) .subscribe(([data, ctx]) => this.updateAllMeta(data, ctx)); } updateAllMeta(data, ctx = {}) { const { _templates_: defaultTemplates, ...defaultAllMeta } = this.defaultMeta; if (!isDataWithMeta(data)) { this.resetAllMeta(ctx, defaultAllMeta); return; } const { meta } = data; const { _templates_, ...allMeta } = meta; const { title, ...otherMeta } = allMeta; const { title: _, ...defaultOtherMeta } = defaultAllMeta; const allMetaDefaulted = { ...defaultAllMeta, ...allMeta }; const otherMetaDefaulted = { ...defaultOtherMeta, ...otherMeta }; const templates = { ...defaultTemplates, ..._templates_, }; const processedMeta = this.contextService._processContext(allMetaDefaulted); this.updateTitle(title, ctx, templates, processedMeta); Object.keys(otherMetaDefaulted).forEach((name) => this.updateMeta(name, otherMetaDefaulted[name], ctx, templates, processedMeta)); // Cleanup leftover meta tags Object.keys(this.metaTags) .filter((name) => name in otherMetaDefaulted === false) .forEach((name) => this.resetMeta(name, ctx, templates, processedMeta)); } resetAllMeta(ctx, defaultMeta) { const { title, ...defaultOtherMeta } = defaultMeta; const metaDefaulted = { ...defaultOtherMeta, ...this.metaTags }; const meta = this.contextService._processContext(defaultMeta); this.resetTitle(ctx, this.defaultMeta._templates_, meta); Object.keys(metaDefaulted).forEach((name) => this.resetMeta(name, ctx, this.defaultMeta._templates_, meta)); } updateTitle(title, ctx, templates, meta) { if (title) { this.title.setTitle(this.contextService._templateStr(title, ctx, { name: 'title', templates, meta, })); } else { this.resetTitle(ctx, templates, meta); } } resetTitle(ctx, templates, meta) { this.title.setTitle(this.contextService._templateStr(this.defaultMeta.title || this.originalTitle, ctx, { name: 'title', meta, templates, })); } updateMeta(name, content, ctx, templates, meta) { if (content) { const metaDef = typeof content === 'string' ? { name, content } : content; metaDef.content = this.contextService._templateStr(metaDef.content, ctx, { name, meta, templates, }); this.meta.updateTag(metaDef); this.metaTags[name] = true; } else { this.resetMeta(name, ctx, templates, meta); } } resetMeta(name, ctx, templates, meta) { const defaultMeta = this.defaultMeta[name]; if (defaultMeta) { this.updateMeta(name, defaultMeta, ctx, templates, meta); } else { this.meta.removeTag(`name="${name}"`); delete this.metaTags[name]; } } getLastRoute(route) { while (route.firstChild) { route = route.firstChild; } return route; } } RouterMetaService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.0.5", ngImport: i0, type: RouterMetaService, deps: [{ token: PLATFORM_ID }, { token: ROUTE_META_CONFIG }, { token: i1.Router }, { token: i2.Title }, { token: i2.Meta }, { token: i3.RouterMetaContextService }, { token: i2.TransferState, optional: true }], target: i0.ɵɵFactoryTarget.Injectable }); RouterMetaService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.0.5", ngImport: i0, type: RouterMetaService, providedIn: 'root' }); i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.0.5", ngImport: i0, type: RouterMetaService, decorators: [{ type: Injectable, args: [{ providedIn: 'root' }] }], ctorParameters: function () { return [{ type: undefined, decorators: [{ type: Inject, args: [PLATFORM_ID] }] }, { type: undefined, decorators: [{ type: Inject, args: [ROUTE_META_CONFIG] }] }, { type: i1.Router }, { type: i2.Title }, { type: i2.Meta }, { type: i3.RouterMetaContextService }, { type: i2.TransferState, decorators: [{ type: Optional }] }]; } }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicm91dGVyLW1ldGEuc2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3Byb2plY3RzL25neC1yb3V0ZXItbWV0YS9zcmMvbGliL3JvdXRlci1tZXRhLnNlcnZpY2UudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLGdCQUFnQixFQUFFLE1BQU0saUJBQWlCLENBQUM7QUFDbkQsT0FBTyxFQUNMLE1BQU0sRUFDTixVQUFVLEVBRVYsUUFBUSxFQUNSLFdBQVcsR0FDWixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQ0wsWUFBWSxFQUNaLElBQUksRUFFSixLQUFLLEVBQ0wsYUFBYSxHQUNkLE1BQU0sMkJBQTJCLENBQUM7QUFDbkMsT0FBTyxFQUF3QixNQUFNLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQUMvRCxPQUFPLEVBQ0wsYUFBYSxFQUNiLE1BQU0sRUFDTixHQUFHLEVBQ0gsT0FBTyxFQUNQLFNBQVMsRUFDVCxTQUFTLEdBQ1YsTUFBTSxNQUFNLENBQUM7QUFFZCxPQUFPLEVBQ0wsY0FBYyxFQUtkLGlCQUFpQixHQUNsQixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBRUwsd0JBQXdCLEdBQ3pCLE1BQU0sK0JBQStCLENBQUM7QUFFdkMsT0FBTyxFQUFFLG9CQUFvQixFQUFFLE1BQU0sUUFBUSxDQUFDOzs7OztBQUU5QyxNQUFNLFdBQVcsR0FBRyxZQUFZLENBQVMsaUJBQWlCLENBQUMsQ0FBQztBQUU1RDs7OztHQUlHO0FBRUgsTUFBTSxPQUFPLGlCQUFpQjtJQXVCNUIsWUFDK0IsVUFBZSxFQUNULE1BQXdCLEVBQ25ELE1BQWMsRUFDZCxLQUFZLEVBQ1osSUFBVSxFQUNWLGNBQXdDLEVBQzVCLGFBQTZCO1FBTnBCLGVBQVUsR0FBVixVQUFVLENBQUs7UUFDVCxXQUFNLEdBQU4sTUFBTSxDQUFrQjtRQUNuRCxXQUFNLEdBQU4sTUFBTSxDQUFRO1FBQ2QsVUFBSyxHQUFMLEtBQUss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UyxDQUFDLFNBQVMsSUFBSSxHQUFHLENBQUMsQ0FBQztZQUN0QyxPQUFPLElBQUksQ0FBQyxRQUFRLENBQUMsSUFBSSxDQUFDLENBQUM7U0FDNUI7SUFDSCxDQUFDO0lBRU8sWUFBWSxDQUFDLEtBQXFCO1FBQ3hDLE9BQU8sS0FBSyxDQUFDLFVBQVUsRUFBRTtZQUN2QixLQUFLLEdBQUcsS0FBSyxDQUFDLFVBQVUsQ0FBQztTQUMxQjtRQUNELE9BQU8sS0FBSyxDQUFDO0lBQ2YsQ0FBQzs7OEdBdk1VLGlCQUFpQixrQkF3QmxCLFdBQVcsYUFDWCxpQkFBaUI7a0hBekJoQixpQkFBaUIsY0FESixNQUFNOzJGQUNuQixpQkFBaUI7a0JBRDdCLFVBQVU7bUJBQUMsRUFBRSxVQUFVLEVBQUUsTUFBTSxFQUFFOzswQkF5QjdCLE1BQU07MkJBQUMsV0FBVzs7MEJBQ2xCLE1BQU07MkJBQUMsaUJBQWlCOzswQkFLeEIsUUFBUSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGlzUGxhdGZvcm1TZXJ2ZXIgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHtcbiAgSW5qZWN0LFxuICBJbmplY3RhYmxlLFxuICBPbkRlc3Ryb3ksXG4gIE9wdGlvbmFsLFxuICBQTEFURk9STV9JRCxcbn0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQge1xuICBtYWtlU3RhdGVLZXksXG4gIE1ldGEsXG4gIE1ldGFEZWZpbml0aW9uLFxuICBUaXRsZSxcbiAgVHJhbnNmZXJTdGF0ZSxcbn0gZnJvbSAnQGFuZ3VsYXIvcGxhdGZvcm0tYnJvd3Nlcic7XG5pbXBvcnQgeyBBY3RpdmF0ZWRSb3V0ZSwgRGF0YSwgUm91dGVyIH0gZnJvbSAnQGFuZ3VsYXIvcm91dGVyJztcbmltcG9ydCB7XG4gIGNvbWJpbmVMYXRlc3QsXG4gIGZpbHRlcixcbiAgbWFwLFxuICBTdWJqZWN0LFxuICBzd2l0Y2hNYXAsXG4gIHRha2VVbnRpbCxcbn0gZnJvbSAncnhqcyc7XG5cbmltcG9ydCB7XG4gIGlzRGF0YVdpdGhNZXRhLFxuICBNZXRhQ29udGV4dCxcbiAgUm91dGVNZXRhLFxuICBSb3V0ZU1ldGFUZW1wbGF0ZXMsXG4gIFJvdXRlck1ldGFDb25maWcsXG4gIFJPVVRFX01FVEFfQ09ORklHLFxufSBmcm9tICcuL3JvdXRlci1tZXRhJztcbmltcG9ydCB7XG4gIFByb2Nlc3NlZE1ldGFDb250ZXh0LFxuICBSb3V0ZXJNZXRhQ29udGV4dFNlcnZpY2UsXG59IGZyb20gJy4vcm91dGVyLW1ldGEtY29udGV4dC5zZXJ2aWNlJztcbmltcG9ydCB7IEluZGV4YWJsZSB9IGZyb20gJy4vdHlwZXMnO1xuaW1wb3J0IHsgaXNOYXZpZ2F0aW9uRW5kRXZlbnQgfSBmcm9tICcuL3V0aWwnO1xuXG5jb25zdCBUSVRMRV9TVEFURSA9IG1ha2VTdGF0ZUtleTxzdHJpbmc+KCdSb3V0ZXJNZXRhVGl0bGUnKTtcblxuLyoqXG4gKiBTZXJ2aWNlIHJlc3BvbnNpYmxlIGZvciB1cGRhdGluZyBtZXRhIHRhZ3MgYmFzZWQgb24gcm91dGVyIGNvbmZpZ3VyYXRpb25cbiAqXG4gKiBUbyBwcm92aWRlIGNvbnRleHQgLSB1c2Uge0BsaW5rIFJvdXRlck1ldGFDb250ZXh0U2VydmljZX1cbiAqL1xuQEluamVjdGFibGUoeyBwcm92aWRlZEluOiAncm9vdCcgfSlcbmV4cG9ydCBjbGFzcyBSb3V0ZXJNZXRhU2VydmljZSBpbXBsZW1lbnRzIE9uRGVzdHJveSB7XG4gIHByaXZhdGUgaW5pdGlhbGl6ZWQgPSBmYWxzZTtcbiAgcHJpdmF0ZSBtZXRhVGFnczogSW5kZXhhYmxlPGJvb2xlYW4+ID0ge307XG5cbiAgcHJpdmF0ZSBkZWZhdWx0TWV0YSA9IHRoaXMuY29uZmlnLmRlZmF1bHRNZXRhIHx8IHt9O1xuXG4gIHByaXZhdGUgb3JpZ2luYWxUaXRsZSA9IHRoaXMudHJhbnNmZXJTdGF0ZVxuICAgID8gdGhpcy50cmFuc2ZlclN0YXRlLmdldChUSVRMRV9TVEFURSwgdGhpcy50aXRsZS5nZXRUaXRsZSgpKVxuICAgIDogdGhpcy50aXRsZS5nZXRUaXRsZSgpO1xuXG4gIHByaXZhdGUgZGVzdHJveWVkJCA9IG5ldyBTdWJqZWN0PHZvaWQ+KCk7XG5cbiAgcHJpdmF0ZSBuYXZpZ2F0aW9uRW5kJCA9IHRoaXMucm91dGVyLmV2ZW50cy5waXBlKFxuICAgIGZpbHRlcihpc05hdmlnYXRpb25FbmRFdmVudCksXG4gICk7XG5cbiAgcHJpdmF0ZSByb3V0ZURhdGEkID0gdGhpcy5uYXZpZ2F0aW9uRW5kJC5waXBlKFxuICAgIG1hcCgoKSA9PiB0aGlzLnJvdXRlci5yb3V0ZXJTdGF0ZS5yb290KSxcbiAgICBtYXAoKHJvdXRlKSA9PiB0aGlzLmdldExhc3RSb3V0ZShyb3V0ZSkpLFxuICAgIGZpbHRlcigocm91dGUpID0+IHJvdXRlLm91dGxldCA9PT0gJ3ByaW1hcnknKSxcbiAgICBzd2l0Y2hNYXAoKHJvdXRlKSA9PiByb3V0ZS5kYXRhKSxcbiAgKTtcblxuICBjb25zdHJ1Y3RvcihcbiAgICBASW5qZWN0KFBMQVRGT1JNX0lEKSBwcml2YXRlIHBsYXRmb3JtSWQ6IGFueSxcbiAgICBASW5qZWN0KFJPVVRFX01FVEFfQ09ORklHKSBwcml2YXRlIGNvbmZpZzogUm91dGVyTWV0YUNvbmZpZyxcbiAgICBwcml2YXRlIHJvdXRlcjogUm91dGVyLFxuICAgIHByaXZhdGUgdGl0bGU6IFRpdGxlLFxuICAgIHByaXZhdGUgbWV0YTogTWV0YSxcbiAgICBwcml2YXRlIGNvbnRleHRTZXJ2aWNlOiBSb3V0ZXJNZXRhQ29udGV4dFNlcnZpY2UsXG4gICAgQE9wdGlvbmFsKCkgcHJpdmF0ZSB0cmFuc2ZlclN0YXRlPzogVHJhbnNmZXJTdGF0ZSxcbiAgKSB7fVxuXG4gIC8qKlxuICAgKiBSZXR1cm5zIG9yaWdpbmFsIHRpdGxlIG9mIGluZGV4IHBhZ2UuXG4gICAqXG4gICAqIElmIFNTUiB3YXMgdXNlZCB3aXRoIHtAbGluayBTdGF0ZVRyYW5zZmVyfSAtXG4gICAqIHRoZW4gb3JpZ2luYWwgdGl0bGUgd2lsbCBiZSBwcmVzZXJ2ZWQgYmV0d2VlbiBzZXJ2ZXIgYW5kIGNsaWVudCBzdGF0ZXNcbiAgICovXG4gIGdldE9yaWdpbmFsVGl0bGUoKSB7XG4gICAgcmV0dXJuIHRoaXMub3JpZ2luYWxUaXRsZTtcbiAgfVxuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgbmdPbkRlc3Ryb3koKTogdm9pZCB7XG4gICAgdGhpcy5kZXN0cm95ZWQkLm5leHQoKTtcbiAgfVxuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgX3NldHVwKCkge1xuICAgIGlmICh0aGlzLmluaXRpYWxpemVkKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIHRoaXMuaW5pdGlhbGl6ZWQgPSB0cnVlO1xuXG4gICAgaWYgKHRoaXMudHJhbnNmZXJTdGF0ZSAmJiBpc1BsYXRmb3JtU2VydmVyKHRoaXMucGxhdGZvcm1JZCkpIHtcbiAgICAgIHRoaXMudHJhbnNmZXJTdGF0ZS5zZXQoVElUTEVfU1RBVEUsIHRoaXMub3JpZ2luYWxUaXRsZSk7XG4gICAgfVxuXG4gICAgY29tYmluZUxhdGVzdCh0aGlzLnJvdXRlRGF0YSQsIHRoaXMuY29udGV4dFNlcnZpY2UuZ2V0Q29udGV4dCgpKVxuICAgICAgLnBpcGUodGFrZVVudGlsKHRoaXMuZGVzdHJveWVkJCkpXG4gICAgICAuc3Vic2NyaWJlKChbZGF0YSwgY3R4XSkgPT4gdGhpcy51cGRhdGVBbGxNZXRhKGRhdGEsIGN0eCkpO1xuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVBbGxNZXRhKGRhdGE6IERhdGEsIGN0eDogUHJvY2Vzc2VkTWV0YUNvbnRleHQgPSB7fSkge1xuICAgIGNvbnN0IHsgX3RlbXBsYXRlc186IGRlZmF1bHRUZW1wbGF0ZXMsIC4uLmRlZmF1bHRBbGxNZXRhIH0gPVxuICAgICAgdGhpcy5kZWZhdWx0TWV0YTtcblxuICAgIGlmICghaXNEYXRhV2l0aE1ldGEoZGF0YSkpIHtcbiAgICAgIHRoaXMucmVzZXRBbGxNZXRhKGN0eCwgZGVmYXVsdEFsbE1ldGEpO1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IHsgbWV0YSB9ID0gZGF0YTtcbiAgICBjb25zdCB7IF90ZW1wbGF0ZXNfLCAuLi5hbGxNZXRhIH0gPSBtZXRhO1xuICAgIGNvbnN0IHsgdGl0bGUsIC4uLm90aGVyTWV0YSB9ID0gYWxsTWV0YTtcbiAgICBjb25zdCB7IHRpdGxlOiBfLCAuLi5kZWZhdWx0T3RoZXJNZXRhIH0gPSBkZWZhdWx0QWxsTWV0YTtcblxuICAgIGNvbnN0IGFsbE1ldGFEZWZhdWx0ZWQgPSB7IC4uLmRlZmF1bHRBbGxNZXRhLCAuLi5hbGxNZXRhIH07XG4gICAgY29uc3Qgb3RoZXJNZXRhRGVmYXVsdGVkID0geyAuLi5kZWZhdWx0T3RoZXJNZXRhLCAuLi5vdGhlck1ldGEgfTtcbiAgICBjb25zdCB0ZW1wbGF0ZXMgPSB7XG4gICAgICAuLi5kZWZhdWx0VGVtcGxhdGVzLFxuICAgICAgLi4uX3RlbXBsYXRlc18sXG4gICAgfSBhcyBSb3V0ZU1ldGFUZW1wbGF0ZXM7XG5cbiAgICBjb25zdCBwcm9jZXNzZWRNZXRhID0gdGhpcy5jb250ZXh0U2VydmljZS5fcHJvY2Vzc0NvbnRleHQoYWxsTWV0YURlZmF1bHRlZCk7XG5cbiAgICB0aGlzLnVwZGF0ZVRpdGxlKHRpdGxlLCBjdHgsIHRlbXBsYXRlcywgcHJvY2Vzc2VkTWV0YSk7XG5cbiAgICBPYmplY3Qua2V5cyhvdGhlck1ldGFEZWZhdWx0ZWQpLmZvckVhY2goKG5hbWUpID0+XG4gICAgICB0aGlzLnVwZGF0ZU1ldGEoXG4gICAgICAgIG5hbWUsXG4gICAgICAgIG90aGVyTWV0YURlZmF1bHRlZFtuYW1lXSxcbiAgICAgICAgY3R4LFxuICAgICAgICB0ZW1wbGF0ZXMsXG4gICAgICAgIHByb2Nlc3NlZE1ldGEsXG4gICAgICApLFxuICAgICk7XG5cbiAgICAvLyBDbGVhbnVwIGxlZnRvdmVyIG1ldGEgdGFnc1xuICAgIE9iamVjdC5rZXlzKHRoaXMubWV0YVRhZ3MpXG4gICAgICAuZmlsdGVyKChuYW1lKSA9PiBuYW1lIGluIG90aGVyTWV0YURlZmF1bHRlZCA9PT0gZmFsc2UpXG4gICAgICAuZm9yRWFjaCgobmFtZSkgPT4gdGhpcy5yZXNldE1ldGEobmFtZSwgY3R4LCB0ZW1wbGF0ZXMsIHByb2Nlc3NlZE1ldGEpKTtcbiAgfVxuXG4gIHByaXZhdGUgcmVzZXRBbGxNZXRhKGN0eDogUHJvY2Vzc2VkTWV0YUNvbnRleHQsIGRlZmF1bHRNZXRhOiBSb3V0ZU1ldGEpIHtcbiAgICBjb25zdCB7IHRpdGxlLCAuLi5kZWZhdWx0T3RoZXJNZXRhIH0gPSBkZWZhdWx0TWV0YTtcbiAgICBjb25zdCBtZXRhRGVmYXVsdGVkID0geyAuLi5kZWZhdWx0T3RoZXJNZXRhLCAuLi50aGlzLm1ldGFUYWdzIH07XG4gICAgY29uc3QgbWV0YSA9IHRoaXMuY29udGV4dFNlcnZpY2UuX3Byb2Nlc3NDb250ZXh0KGRlZmF1bHRNZXRhKTtcblxuICAgIHRoaXMucmVzZXRUaXRsZShjdHgsIHRoaXMuZGVmYXVsdE1ldGEuX3RlbXBsYXRlc18sIG1ldGEpO1xuXG4gICAgT2JqZWN0LmtleXMobWV0YURlZmF1bHRlZCkuZm9yRWFjaCgobmFtZSkgPT5cbiAgICAgIHRoaXMucmVzZXRNZXRhKG5hbWUsIGN0eCwgdGhpcy5kZWZhdWx0TWV0YS5fdGVtcGxhdGVzXywgbWV0YSksXG4gICAgKTtcbiAgfVxuXG4gIHByaXZhdGUgdXBkYXRlVGl0bGUoXG4gICAgdGl0bGU/OiBzdHJpbmcsXG4gICAgY3R4PzogUHJvY2Vzc2VkTWV0YUNvbnRleHQsXG4gICAgdGVtcGxhdGVzPzogUm91dGVNZXRhVGVtcGxhdGVzLFxuICAgIG1ldGE/OiBQcm9jZXNzZWRNZXRhQ29udGV4dCxcbiAgKSB7XG4gICAgaWYgKHRpdGxlKSB7XG4gICAgICB0aGlzLnRpdGxlLnNldFRpdGxlKFxuICAgICAgICB0aGlzLmNvbnRleHRTZXJ2aWNlLl90ZW1wbGF0ZVN0cih0aXRsZSwgY3R4LCB7XG4gICAgICAgICAgbmFtZTogJ3RpdGxlJyxcbiAgICAgICAgICB0ZW1wbGF0ZXMsXG4gICAgICAgICAgbWV0YSxcbiAgICAgICAgfSksXG4gICAgICApO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLnJlc2V0VGl0bGUoY3R4LCB0ZW1wbGF0ZXMsIG1ldGEpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgcmVzZXRUaXRsZShcbiAgICBjdHg/OiBQcm9jZXNzZWRNZXRhQ29udGV4dCxcbiAgICB0ZW1wbGF0ZXM/OiBSb3V0ZU1ldGFUZW1wbGF0ZXMsXG4gICAgbWV0YT86IFByb2Nlc3NlZE1ldGFDb250ZXh0LFxuICApIHtcbiAgICB0aGlzLnRpdGxlLnNldFRpdGxlKFxuICAgICAgdGhpcy5jb250ZXh0U2VydmljZS5fdGVtcGxhdGVTdHIoXG4gICAgICAgIHRoaXMuZGVmYXVsdE1ldGEudGl0bGUgfHwgdGhpcy5vcmlnaW5hbFRpdGxlLFxuICAgICAgICBjdHgsXG4gICAgICAgIHtcbiAgICAgICAgICBuYW1lOiAndGl0bGUnLFxuICAgICAgICAgIG1ldGEsXG4gICAgICAgICAgdGVtcGxhdGVzLFxuICAgICAgICB9LFxuICAgICAgKSxcbiAgICApO1xuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVNZXRhKFxuICAgIG5hbWU6IHN0cmluZyxcbiAgICBjb250ZW50Pzogc3RyaW5nIHwgTWV0YURlZmluaXRpb24sXG4gICAgY3R4PzogUHJvY2Vzc2VkTWV0YUNvbnRleHQsXG4gICAgdGVtcGxhdGVzPzogUm91dGVNZXRhVGVtcGxhdGVzLFxuICAgIG1ldGE/OiBQcm9jZXNzZWRNZXRhQ29udGV4dCxcbiAgKSB7XG4gICAgaWYgKGNvbnRlbnQpIHtcbiAgICAgIGNvbnN0IG1ldGFEZWY6IE1ldGFEZWZpbml0aW9uID1cbiAgICAgICAgdHlwZW9mIGNvbnRlbnQgPT09ICdzdHJpbmcnID8geyBuYW1lLCBjb250ZW50IH0gOiBjb250ZW50O1xuXG4gICAgICBtZXRhRGVmLmNvbnRlbnQgPSB0aGlzLmNvbnRleHRTZXJ2aWNlLl90ZW1wbGF0ZVN0cihtZXRhRGVmLmNvbnRlbnQsIGN0eCwge1xuICAgICAgICBuYW1lLFxuICAgICAgICBtZXRhLFxuICAgICAgICB0ZW1wbGF0ZXMsXG4gICAgICB9KTtcblxuICAgICAgdGhpcy5tZXRhLnVwZGF0ZVRhZyhtZXRhRGVmKTtcbiAgICAgIHRoaXMubWV0YVRhZ3NbbmFtZV0gPSB0cnVlO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLnJlc2V0TWV0YShuYW1lLCBjdHgsIHRlbXBsYXRlcywgbWV0YSk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSByZXNldE1ldGEoXG4gICAgbmFtZTogc3RyaW5nLFxuICAgIGN0eD86IE1ldGFDb250ZXh0LFxuICAgIHRlbXBsYXRlcz86IFJvdXRlTWV0YVRlbXBsYXRlcyxcbiAgICBtZXRhPzogUHJvY2Vzc2VkTWV0YUNvbnRleHQsXG4gICkge1xuICAgIGNvbnN0IGRlZmF1bHRNZXRhID0gdGhpcy5kZWZhdWx0TWV0YVtuYW1lXTtcblxuICAgIGlmIChkZWZhdWx0TWV0YSkge1xuICAgICAgdGhpcy51cGRhdGVNZXRhKG5hbWUsIGRlZmF1bHRNZXRhLCBjdHgsIHRlbXBsYXRlcywgbWV0YSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRoaXMubWV0YS5yZW1vdmVUYWcoYG5hbWU9XCIke25hbWV9XCJgKTtcbiAgICAgIGRlbGV0ZSB0aGlzLm1ldGFUYWdzW25hbWVdO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgZ2V0TGFzdFJvdXRlKHJvdXRlOiBBY3RpdmF0ZWRSb3V0ZSkge1xuICAgIHdoaWxlIChyb3V0ZS5maXJzdENoaWxkKSB7XG4gICAgICByb3V0ZSA9IHJvdXRlLmZpcnN0Q2hpbGQ7XG4gICAgfVxuICAgIHJldHVybiByb3V0ZTtcbiAgfVxufVxuIl19