@tolle_/tolle-ui 18.2.29 → 18.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/esm2022/lib/accordion-item.component.mjs +5 -11
- package/esm2022/lib/accordion.component.mjs +4 -9
- package/esm2022/lib/alert-dialog-dynamic.component.mjs +12 -12
- package/esm2022/lib/alert-dialog.component.mjs +82 -64
- package/esm2022/lib/alert-dialog.service.mjs +38 -6
- package/esm2022/lib/alert.component.mjs +5 -11
- package/esm2022/lib/aspect-ratio.component.mjs +119 -0
- package/esm2022/lib/attachment.component.mjs +334 -0
- package/esm2022/lib/avatar-fallback.component.mjs +3 -3
- package/esm2022/lib/avatar.component.mjs +4 -9
- package/esm2022/lib/badge.component.mjs +4 -9
- package/esm2022/lib/breadcrumb-item.component.mjs +3 -3
- package/esm2022/lib/breadcrumb-link.component.mjs +3 -3
- package/esm2022/lib/breadcrumb-separator.component.mjs +3 -3
- package/esm2022/lib/breadcrumb.component.mjs +3 -3
- package/esm2022/lib/bubble.component.mjs +301 -0
- package/esm2022/lib/button.component.mjs +5 -11
- package/esm2022/lib/calendar.component.mjs +5 -11
- package/esm2022/lib/card.component.mjs +14 -43
- package/esm2022/lib/carousel/carousel.component.mjs +5 -12
- package/esm2022/lib/chain-of-thought.component.mjs +380 -0
- package/esm2022/lib/chart-pie.component.mjs +386 -0
- package/esm2022/lib/chart.component.mjs +1146 -0
- package/esm2022/lib/chart.service.mjs +555 -0
- package/esm2022/lib/checkbox.component.mjs +5 -11
- package/esm2022/lib/checkpoint.component.mjs +134 -0
- package/esm2022/lib/collapsible.component.mjs +4 -11
- package/esm2022/lib/combobox.component.mjs +372 -0
- package/esm2022/lib/command-dialog.component.mjs +164 -0
- package/esm2022/lib/command.component.mjs +514 -0
- package/esm2022/lib/command.service.mjs +130 -0
- package/esm2022/lib/confirmation.component.mjs +219 -0
- package/esm2022/lib/context-menu-trigger.directive.mjs +36 -0
- package/esm2022/lib/context-menu.component.mjs +460 -0
- package/esm2022/lib/context-menu.service.mjs +125 -0
- package/esm2022/lib/context.component.mjs +377 -0
- package/esm2022/lib/conversation.component.mjs +442 -0
- package/esm2022/lib/country-selector.component.mjs +5 -11
- package/esm2022/lib/data-table.component.mjs +59 -12
- package/esm2022/lib/date-picker.component.mjs +251 -198
- package/esm2022/lib/date-range-picker.component.mjs +224 -116
- package/esm2022/lib/date-time-picker.component.mjs +506 -0
- package/esm2022/lib/direction.component.mjs +79 -0
- package/esm2022/lib/dropdown-item.component.mjs +3 -3
- package/esm2022/lib/dropdown-label.component.mjs +3 -3
- package/esm2022/lib/dropdown-menu.component.mjs +3 -3
- package/esm2022/lib/dropdown-separator.component.mjs +3 -3
- package/esm2022/lib/dropdown-trigger.directive.mjs +6 -4
- package/esm2022/lib/empty-state.component.mjs +4 -9
- package/esm2022/lib/field.component.mjs +394 -0
- package/esm2022/lib/hover-card.component.mjs +6 -16
- package/esm2022/lib/inline-citation.component.mjs +263 -0
- package/esm2022/lib/input-group.component.mjs +418 -0
- package/esm2022/lib/input.component.mjs +5 -11
- package/esm2022/lib/item.component.mjs +243 -0
- package/esm2022/lib/kbd.component.mjs +82 -0
- package/esm2022/lib/label.component.mjs +4 -9
- package/esm2022/lib/marker.component.mjs +135 -0
- package/esm2022/lib/masked-input.component.mjs +5 -11
- package/esm2022/lib/menubar.component.mjs +683 -0
- package/esm2022/lib/message-scroller.component.mjs +353 -0
- package/esm2022/lib/message-scroller.service.mjs +157 -0
- package/esm2022/lib/message.component.mjs +228 -0
- package/esm2022/lib/modal-ref.mjs +36 -7
- package/esm2022/lib/modal.component.mjs +42 -28
- package/esm2022/lib/modal.mjs +2 -29
- package/esm2022/lib/modal.service.mjs +26 -4
- package/esm2022/lib/model-selector.component.mjs +310 -0
- package/esm2022/lib/multi-select.component.mjs +155 -72
- package/esm2022/lib/native-select.component.mjs +201 -0
- package/esm2022/lib/navigation-menu.component.mjs +642 -0
- package/esm2022/lib/otp-group.component.mjs +3 -3
- package/esm2022/lib/otp-slot.component.mjs +4 -9
- package/esm2022/lib/otp.component.mjs +5 -11
- package/esm2022/lib/pagination.component.mjs +7 -10
- package/esm2022/lib/plan.component.mjs +335 -0
- package/esm2022/lib/popover-content.component.mjs +4 -9
- package/esm2022/lib/popover.component.mjs +15 -13
- package/esm2022/lib/progress.component.mjs +4 -9
- package/esm2022/lib/prompt-input.component.mjs +526 -0
- package/esm2022/lib/queue.component.mjs +280 -0
- package/esm2022/lib/radio-group.component.mjs +6 -13
- package/esm2022/lib/radio-item.component.mjs +4 -9
- package/esm2022/lib/range-calendar.component.mjs +5 -11
- package/esm2022/lib/reasoning.component.mjs +335 -0
- package/esm2022/lib/resizable-panel.component.mjs +5 -5
- package/esm2022/lib/resizable.component.mjs +219 -0
- package/esm2022/lib/segment.component.mjs +19 -9
- package/esm2022/lib/select-group.component.mjs +4 -8
- package/esm2022/lib/select-item.component.mjs +4 -9
- package/esm2022/lib/select-separator.component.mjs +4 -8
- package/esm2022/lib/select.component.mjs +133 -49
- package/esm2022/lib/separator.component.mjs +4 -9
- package/esm2022/lib/sheet.component.mjs +38 -56
- package/esm2022/lib/shimmer.component.mjs +84 -0
- package/esm2022/lib/sidebar.component.mjs +11 -1
- package/esm2022/lib/skeleton.component.mjs +4 -9
- package/esm2022/lib/sources.component.mjs +452 -0
- package/esm2022/lib/spinner.component.mjs +68 -0
- package/esm2022/lib/suggestion.component.mjs +207 -0
- package/esm2022/lib/switch.component.mjs +5 -11
- package/esm2022/lib/table.component.mjs +213 -0
- package/esm2022/lib/tabs.component.mjs +4 -11
- package/esm2022/lib/tag-input.component.mjs +5 -11
- package/esm2022/lib/task.component.mjs +359 -0
- package/esm2022/lib/textarea.component.mjs +5 -11
- package/esm2022/lib/theme.service.mjs +17 -6
- package/esm2022/lib/time-picker.component.mjs +923 -0
- package/esm2022/lib/toast.service.mjs +3 -2
- package/esm2022/lib/toaster.component.mjs +76 -39
- package/esm2022/lib/toggle-group.component.mjs +4 -9
- package/esm2022/lib/toggle.component.mjs +5 -11
- package/esm2022/lib/tool.component.mjs +462 -0
- package/esm2022/lib/typography.component.mjs +83 -0
- package/esm2022/lib/utils/color.mjs +140 -19
- package/esm2022/public-api.mjs +61 -1
- package/fesm2022/tolle-ui.mjs +16642 -1105
- package/fesm2022/tolle-ui.mjs.map +1 -1
- package/lib/alert-dialog-dynamic.component.d.ts +5 -0
- package/lib/alert-dialog.component.d.ts +23 -2
- package/lib/aspect-ratio.component.d.ts +20 -0
- package/lib/attachment.component.d.ts +101 -0
- package/lib/bubble.component.d.ts +112 -0
- package/lib/chain-of-thought.component.d.ts +166 -0
- package/lib/chart-pie.component.d.ts +108 -0
- package/lib/chart.component.d.ts +369 -0
- package/lib/chart.service.d.ts +222 -0
- package/lib/checkpoint.component.d.ts +51 -0
- package/lib/combobox.component.d.ts +90 -0
- package/lib/command-dialog.component.d.ts +53 -0
- package/lib/command.component.d.ts +189 -0
- package/lib/command.service.d.ts +67 -0
- package/lib/confirmation.component.d.ts +70 -0
- package/lib/context-menu-trigger.directive.d.ts +12 -0
- package/lib/context-menu.component.d.ts +41 -0
- package/lib/context-menu.service.d.ts +38 -0
- package/lib/context.component.d.ts +134 -0
- package/lib/conversation.component.d.ts +165 -0
- package/lib/data-table.component.d.ts +26 -1
- package/lib/date-picker.component.d.ts +72 -11
- package/lib/date-range-picker.component.d.ts +63 -6
- package/lib/date-time-picker.component.d.ts +119 -0
- package/lib/direction.component.d.ts +45 -0
- package/lib/field.component.d.ts +201 -0
- package/lib/inline-citation.component.d.ts +103 -0
- package/lib/input-group.component.d.ts +150 -0
- package/lib/item.component.d.ts +154 -0
- package/lib/kbd.component.d.ts +50 -0
- package/lib/marker.component.d.ts +58 -0
- package/lib/menubar.component.d.ts +247 -0
- package/lib/message-scroller.component.d.ts +159 -0
- package/lib/message-scroller.service.d.ts +73 -0
- package/lib/message.component.d.ts +128 -0
- package/lib/modal-ref.d.ts +6 -1
- package/lib/modal.component.d.ts +7 -4
- package/lib/modal.d.ts +9 -3
- package/lib/model-selector.component.d.ts +103 -0
- package/lib/multi-select.component.d.ts +66 -14
- package/lib/native-select.component.d.ts +57 -0
- package/lib/navigation-menu.component.d.ts +230 -0
- package/lib/plan.component.d.ts +120 -0
- package/lib/popover.component.d.ts +1 -0
- package/lib/prompt-input.component.d.ts +194 -0
- package/lib/queue.component.d.ts +106 -0
- package/lib/reasoning.component.d.ts +127 -0
- package/lib/resizable.component.d.ts +43 -0
- package/lib/segment.component.d.ts +13 -3
- package/lib/select.component.d.ts +37 -5
- package/lib/sheet.component.d.ts +3 -0
- package/lib/shimmer.component.d.ts +38 -0
- package/lib/sidebar.component.d.ts +2 -0
- package/lib/sources.component.d.ts +156 -0
- package/lib/spinner.component.d.ts +29 -0
- package/lib/suggestion.component.d.ts +96 -0
- package/lib/table.component.d.ts +106 -0
- package/lib/task.component.d.ts +151 -0
- package/lib/theme.service.d.ts +9 -0
- package/lib/time-picker.component.d.ts +243 -0
- package/lib/toast.service.d.ts +3 -1
- package/lib/toaster.component.d.ts +26 -9
- package/lib/tool.component.d.ts +158 -0
- package/lib/typography.component.d.ts +32 -0
- package/lib/utils/color.d.ts +19 -5
- package/package.json +3 -2
- package/preset.js +7 -1
- package/public-api.d.ts +50 -0
- package/registry/docs-content.json +8480 -1542
- package/registry/llms-full.txt +2679 -319
- package/registry/llms.txt +43 -4
- package/registry/manifest.json +9090 -1742
- package/registry/r/accordion-item.json +1 -1
- package/registry/r/accordion.json +1 -1
- package/registry/r/alert-dialog-dynamic.json +1 -1
- package/registry/r/alert-dialog.json +1 -1
- package/registry/r/alert.json +1 -1
- package/registry/r/attachment.json +23 -0
- package/registry/r/avatar-fallback.json +1 -1
- package/registry/r/avatar.json +1 -1
- package/registry/r/badge.json +1 -1
- package/registry/r/breadcrumb-item.json +1 -1
- package/registry/r/breadcrumb-link.json +1 -1
- package/registry/r/breadcrumb-separator.json +1 -1
- package/registry/r/breadcrumb.json +1 -1
- package/registry/r/bubble.json +23 -0
- package/registry/r/button.json +1 -1
- package/registry/r/calendar.json +1 -1
- package/registry/r/card.json +1 -1
- package/registry/r/carousel.json +1 -1
- package/registry/r/chain-of-thought.json +23 -0
- package/registry/r/chart-pie.json +30 -0
- package/registry/r/chart.json +28 -0
- package/registry/r/checkbox.json +1 -1
- package/registry/r/checkpoint.json +23 -0
- package/registry/r/collapsible.json +1 -1
- package/registry/r/combobox.json +31 -0
- package/registry/r/command-dialog.json +21 -0
- package/registry/r/command.json +26 -0
- package/registry/r/confirmation.json +23 -0
- package/registry/r/context-menu-trigger.json +1 -1
- package/registry/r/context-menu.json +1 -1
- package/registry/r/context.json +26 -0
- package/registry/r/conversation.json +23 -0
- package/registry/r/country-selector.json +1 -1
- package/registry/r/data-table.json +1 -1
- package/registry/r/date-picker.json +4 -4
- package/registry/r/date-range-picker.json +3 -3
- package/registry/r/date-time-picker.json +28 -0
- package/registry/r/direction.json +16 -0
- package/registry/r/dropdown-item.json +1 -1
- package/registry/r/dropdown-label.json +1 -1
- package/registry/r/dropdown-menu.json +1 -1
- package/registry/r/dropdown-separator.json +1 -1
- package/registry/r/dropdown-trigger.json +1 -1
- package/registry/r/empty-state.json +1 -1
- package/registry/r/field.json +23 -0
- package/registry/r/hover-card.json +1 -1
- package/registry/r/inline-citation.json +26 -0
- package/registry/r/input-group.json +23 -0
- package/registry/r/input.json +1 -1
- package/registry/r/item.json +23 -0
- package/registry/r/kbd.json +23 -0
- package/registry/r/label.json +1 -1
- package/registry/r/marker.json +23 -0
- package/registry/r/masked-input.json +1 -1
- package/registry/r/menubar.json +24 -0
- package/registry/r/message-scroller.json +26 -0
- package/registry/r/message.json +23 -0
- package/registry/r/modal.json +3 -3
- package/registry/r/model-selector.json +32 -0
- package/registry/r/multi-select.json +2 -2
- package/registry/r/native-select.json +23 -0
- package/registry/r/navigation-menu.json +24 -0
- package/registry/r/otp-group.json +1 -1
- package/registry/r/otp-slot.json +1 -1
- package/registry/r/otp.json +1 -1
- package/registry/r/pagination.json +3 -2
- package/registry/r/plan.json +23 -0
- package/registry/r/popover-content.json +1 -1
- package/registry/r/popover.json +1 -1
- package/registry/r/progress.json +1 -1
- package/registry/r/prompt-input.json +23 -0
- package/registry/r/queue.json +23 -0
- package/registry/r/radio-group.json +1 -1
- package/registry/r/radio-item.json +1 -1
- package/registry/r/range-calendar.json +1 -1
- package/registry/r/reasoning.json +23 -0
- package/registry/r/resizable-panel.json +1 -1
- package/registry/r/segment.json +1 -1
- package/registry/r/select-group.json +1 -1
- package/registry/r/select-item.json +1 -1
- package/registry/r/select-separator.json +1 -1
- package/registry/r/select.json +4 -3
- package/registry/r/separator.json +1 -1
- package/registry/r/sheet.json +1 -1
- package/registry/r/shimmer.json +23 -0
- package/registry/r/sidebar.json +1 -1
- package/registry/r/skeleton.json +1 -1
- package/registry/r/sources.json +23 -0
- package/registry/r/spinner.json +23 -0
- package/registry/r/suggestion.json +23 -0
- package/registry/r/switch.json +1 -1
- package/registry/r/table.json +21 -0
- package/registry/r/tabs.json +1 -1
- package/registry/r/tag-input.json +1 -1
- package/registry/r/task.json +23 -0
- package/registry/r/textarea.json +1 -1
- package/registry/r/time-picker.json +24 -0
- package/registry/r/toaster.json +2 -2
- package/registry/r/toggle-group.json +1 -1
- package/registry/r/toggle.json +1 -1
- package/registry/r/tool.json +23 -0
- package/registry/r/typography.json +23 -0
- package/registry/registry.json +915 -22
- package/theme.css +121 -8
|
@@ -0,0 +1,377 @@
|
|
|
1
|
+
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, Injectable, Input, forwardRef, inject } from '@angular/core';
|
|
2
|
+
import { CommonModule } from '@angular/common';
|
|
3
|
+
import { BehaviorSubject, Subscription } from 'rxjs';
|
|
4
|
+
import { cva } from 'class-variance-authority';
|
|
5
|
+
import { cn } from './utils/cn';
|
|
6
|
+
import { HoverCardComponent, HoverCardTriggerComponent, HoverCardContentComponent, } from './hover-card.component';
|
|
7
|
+
import * as i0 from "@angular/core";
|
|
8
|
+
import * as i1 from "@angular/common";
|
|
9
|
+
const contextTriggerVariants = cva('inline-flex items-center gap-1.5 rounded-md px-1.5 py-1 text-xs font-medium tabular-nums transition-colors', {
|
|
10
|
+
variants: {
|
|
11
|
+
level: {
|
|
12
|
+
normal: 'text-muted-foreground hover:text-foreground',
|
|
13
|
+
warning: 'text-warning hover:text-warning',
|
|
14
|
+
critical: 'text-destructive hover:text-destructive',
|
|
15
|
+
},
|
|
16
|
+
},
|
|
17
|
+
defaultVariants: { level: 'normal' },
|
|
18
|
+
});
|
|
19
|
+
const contextBarVariants = cva('h-full rounded-full transition-[width,background-color] duration-300', {
|
|
20
|
+
variants: {
|
|
21
|
+
level: {
|
|
22
|
+
normal: 'bg-primary',
|
|
23
|
+
warning: 'bg-warning',
|
|
24
|
+
critical: 'bg-destructive',
|
|
25
|
+
},
|
|
26
|
+
},
|
|
27
|
+
defaultVariants: { level: 'normal' },
|
|
28
|
+
});
|
|
29
|
+
/** Formats a raw token count as a short, readable string. */
|
|
30
|
+
export function formatTokens(value) {
|
|
31
|
+
if (!isFinite(value))
|
|
32
|
+
return '0';
|
|
33
|
+
const abs = Math.abs(value);
|
|
34
|
+
if (abs >= 1_000_000)
|
|
35
|
+
return (value / 1_000_000).toFixed(1).replace(/\.0$/, '') + 'M';
|
|
36
|
+
if (abs >= 1_000)
|
|
37
|
+
return (value / 1_000).toFixed(1).replace(/\.0$/, '') + 'K';
|
|
38
|
+
return String(Math.round(value));
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Publishes the parent `tolle-context`'s numbers to its OnPush trigger and
|
|
42
|
+
* content children, which receive none of it as their own inputs.
|
|
43
|
+
*/
|
|
44
|
+
export class ContextService {
|
|
45
|
+
usageSource = new BehaviorSubject({
|
|
46
|
+
used: 0,
|
|
47
|
+
total: 0,
|
|
48
|
+
inputTokens: null,
|
|
49
|
+
outputTokens: null,
|
|
50
|
+
cost: null,
|
|
51
|
+
ratio: 0,
|
|
52
|
+
level: 'normal',
|
|
53
|
+
});
|
|
54
|
+
/** Emits the current context-window usage. */
|
|
55
|
+
usage$ = this.usageSource.asObservable();
|
|
56
|
+
get usage() {
|
|
57
|
+
return this.usageSource.value;
|
|
58
|
+
}
|
|
59
|
+
setUsage(usage) {
|
|
60
|
+
this.usageSource.next(usage);
|
|
61
|
+
}
|
|
62
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
63
|
+
static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextService });
|
|
64
|
+
}
|
|
65
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextService, decorators: [{
|
|
66
|
+
type: Injectable
|
|
67
|
+
}] });
|
|
68
|
+
/**
|
|
69
|
+
* A token / context-window usage indicator: a compact percentage and bar that
|
|
70
|
+
* shifts to the warning and destructive tokens as the window fills, with a
|
|
71
|
+
* hover breakdown of input, output and cost.
|
|
72
|
+
*
|
|
73
|
+
* ```html
|
|
74
|
+
* <tolle-context [used]="82000" [total]="128000" [inputTokens]="61000" [outputTokens]="21000" [cost]="0.42"></tolle-context>
|
|
75
|
+
* ```
|
|
76
|
+
* @new
|
|
77
|
+
*/
|
|
78
|
+
export class ContextComponent {
|
|
79
|
+
/** Tokens consumed so far. @default 0 */
|
|
80
|
+
used = 0;
|
|
81
|
+
/** Size of the context window in tokens. @default 0 */
|
|
82
|
+
total = 0;
|
|
83
|
+
/** Tokens spent on the prompt, shown in the breakdown. @default null */
|
|
84
|
+
inputTokens = null;
|
|
85
|
+
/** Tokens produced by the model, shown in the breakdown. @default null */
|
|
86
|
+
outputTokens = null;
|
|
87
|
+
/** Spend for this context, shown in the breakdown. @default null */
|
|
88
|
+
cost = null;
|
|
89
|
+
/** Ratio at or above which the indicator turns warning-coloured. @default 0.75 */
|
|
90
|
+
warningThreshold = 0.75;
|
|
91
|
+
/** Ratio at or above which the indicator turns destructive-coloured. @default 0.9 */
|
|
92
|
+
criticalThreshold = 0.9;
|
|
93
|
+
/** Side of the indicator the breakdown opens on. @default 'top' */
|
|
94
|
+
placement = 'top';
|
|
95
|
+
/** Milliseconds to wait before opening the breakdown. @default 150 */
|
|
96
|
+
openDelay = 150;
|
|
97
|
+
/** Milliseconds to wait before closing the breakdown. @default 200 */
|
|
98
|
+
closeDelay = 200;
|
|
99
|
+
/** Extra Tailwind classes merged onto the indicator via `cn()` (last-wins). */
|
|
100
|
+
class = '';
|
|
101
|
+
service = inject(ContextService);
|
|
102
|
+
cdr = inject(ChangeDetectorRef);
|
|
103
|
+
refreshTimer;
|
|
104
|
+
ngOnInit() {
|
|
105
|
+
this.push();
|
|
106
|
+
}
|
|
107
|
+
ngOnChanges() {
|
|
108
|
+
this.push();
|
|
109
|
+
}
|
|
110
|
+
/** Fraction of the window consumed, clamped to 0–1. */
|
|
111
|
+
get ratio() {
|
|
112
|
+
if (!this.total || this.total <= 0)
|
|
113
|
+
return 0;
|
|
114
|
+
return Math.min(1, Math.max(0, this.used / this.total));
|
|
115
|
+
}
|
|
116
|
+
/** Which colour band the current usage falls into. */
|
|
117
|
+
get level() {
|
|
118
|
+
const ratio = this.ratio;
|
|
119
|
+
if (ratio >= this.criticalThreshold)
|
|
120
|
+
return 'critical';
|
|
121
|
+
if (ratio >= this.warningThreshold)
|
|
122
|
+
return 'warning';
|
|
123
|
+
return 'normal';
|
|
124
|
+
}
|
|
125
|
+
push() {
|
|
126
|
+
this.service.setUsage({
|
|
127
|
+
used: this.used,
|
|
128
|
+
total: this.total,
|
|
129
|
+
inputTokens: this.inputTokens,
|
|
130
|
+
outputTokens: this.outputTokens,
|
|
131
|
+
cost: this.cost,
|
|
132
|
+
ratio: this.ratio,
|
|
133
|
+
level: this.level,
|
|
134
|
+
});
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* `tolle-hover-card` toggles its own visibility from a `setTimeout`, which
|
|
138
|
+
* never marks this OnPush view dirty — re-check once the delay has elapsed.
|
|
139
|
+
*/
|
|
140
|
+
scheduleRefresh(delay) {
|
|
141
|
+
clearTimeout(this.refreshTimer);
|
|
142
|
+
this.refreshTimer = setTimeout(() => this.cdr.markForCheck(), delay + 32);
|
|
143
|
+
}
|
|
144
|
+
ngOnDestroy() {
|
|
145
|
+
clearTimeout(this.refreshTimer);
|
|
146
|
+
}
|
|
147
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
148
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: ContextComponent, isStandalone: true, selector: "tolle-context", inputs: { used: "used", total: "total", inputTokens: "inputTokens", outputTokens: "outputTokens", cost: "cost", warningThreshold: "warningThreshold", criticalThreshold: "criticalThreshold", placement: "placement", openDelay: "openDelay", closeDelay: "closeDelay", class: "class" }, providers: [ContextService], usesOnChanges: true, ngImport: i0, template: `
|
|
149
|
+
<tolle-hover-card
|
|
150
|
+
[openDelay]="openDelay"
|
|
151
|
+
[closeDelay]="closeDelay"
|
|
152
|
+
[placement]="placement"
|
|
153
|
+
(mouseenter)="scheduleRefresh(openDelay)"
|
|
154
|
+
(mouseleave)="scheduleRefresh(closeDelay)"
|
|
155
|
+
>
|
|
156
|
+
<tolle-hover-card-trigger>
|
|
157
|
+
<tolle-context-trigger></tolle-context-trigger>
|
|
158
|
+
</tolle-hover-card-trigger>
|
|
159
|
+
<tolle-hover-card-content class="w-60 p-0">
|
|
160
|
+
<tolle-context-content></tolle-context-content>
|
|
161
|
+
</tolle-hover-card-content>
|
|
162
|
+
</tolle-hover-card>
|
|
163
|
+
`, isInline: true, styles: [":host{display:block}\n"], dependencies: [{ kind: "ngmodule", type: i0.forwardRef(() => CommonModule) }, { kind: "component", type: i0.forwardRef(() => HoverCardComponent), selector: "tolle-hover-card", inputs: ["openDelay", "closeDelay", "placement"] }, { kind: "component", type: i0.forwardRef(() => HoverCardTriggerComponent), selector: "tolle-hover-card-trigger" }, { kind: "component", type: i0.forwardRef(() => HoverCardContentComponent), selector: "tolle-hover-card-content", inputs: ["class"] }, { kind: "component", type: i0.forwardRef(() => ContextTriggerComponent), selector: "tolle-context-trigger", inputs: ["class"] }, { kind: "component", type: i0.forwardRef(() => ContextContentComponent), selector: "tolle-context-content", inputs: ["currency", "class"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
164
|
+
}
|
|
165
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextComponent, decorators: [{
|
|
166
|
+
type: Component,
|
|
167
|
+
args: [{ selector: 'tolle-context', standalone: true, imports: [
|
|
168
|
+
CommonModule,
|
|
169
|
+
HoverCardComponent,
|
|
170
|
+
HoverCardTriggerComponent,
|
|
171
|
+
HoverCardContentComponent,
|
|
172
|
+
// The sub-components are declared further down this file, so they are
|
|
173
|
+
// referenced lazily rather than read at decoration time.
|
|
174
|
+
forwardRef(() => ContextTriggerComponent),
|
|
175
|
+
forwardRef(() => ContextContentComponent),
|
|
176
|
+
], providers: [ContextService], changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
177
|
+
<tolle-hover-card
|
|
178
|
+
[openDelay]="openDelay"
|
|
179
|
+
[closeDelay]="closeDelay"
|
|
180
|
+
[placement]="placement"
|
|
181
|
+
(mouseenter)="scheduleRefresh(openDelay)"
|
|
182
|
+
(mouseleave)="scheduleRefresh(closeDelay)"
|
|
183
|
+
>
|
|
184
|
+
<tolle-hover-card-trigger>
|
|
185
|
+
<tolle-context-trigger></tolle-context-trigger>
|
|
186
|
+
</tolle-hover-card-trigger>
|
|
187
|
+
<tolle-hover-card-content class="w-60 p-0">
|
|
188
|
+
<tolle-context-content></tolle-context-content>
|
|
189
|
+
</tolle-hover-card-content>
|
|
190
|
+
</tolle-hover-card>
|
|
191
|
+
`, styles: [":host{display:block}\n"] }]
|
|
192
|
+
}], propDecorators: { used: [{
|
|
193
|
+
type: Input
|
|
194
|
+
}], total: [{
|
|
195
|
+
type: Input
|
|
196
|
+
}], inputTokens: [{
|
|
197
|
+
type: Input
|
|
198
|
+
}], outputTokens: [{
|
|
199
|
+
type: Input
|
|
200
|
+
}], cost: [{
|
|
201
|
+
type: Input
|
|
202
|
+
}], warningThreshold: [{
|
|
203
|
+
type: Input
|
|
204
|
+
}], criticalThreshold: [{
|
|
205
|
+
type: Input
|
|
206
|
+
}], placement: [{
|
|
207
|
+
type: Input
|
|
208
|
+
}], openDelay: [{
|
|
209
|
+
type: Input
|
|
210
|
+
}], closeDelay: [{
|
|
211
|
+
type: Input
|
|
212
|
+
}], class: [{
|
|
213
|
+
type: Input
|
|
214
|
+
}] } });
|
|
215
|
+
/** The always-visible part of a `tolle-context`: percentage plus usage bar. */
|
|
216
|
+
export class ContextTriggerComponent {
|
|
217
|
+
/**
|
|
218
|
+
* Angular writes a bound `class` input through its styling path, which does
|
|
219
|
+
* not mark an OnPush component dirty — without this hook the component keeps
|
|
220
|
+
* rendering the class it was born with.
|
|
221
|
+
*/
|
|
222
|
+
ngOnChanges() {
|
|
223
|
+
this.cdr.markForCheck();
|
|
224
|
+
}
|
|
225
|
+
/** Extra Tailwind classes merged onto the trigger via `cn()` (last-wins). */
|
|
226
|
+
class = '';
|
|
227
|
+
service = inject(ContextService);
|
|
228
|
+
cdr = inject(ChangeDetectorRef);
|
|
229
|
+
sub = new Subscription();
|
|
230
|
+
usage = this.service.usage;
|
|
231
|
+
ngOnInit() {
|
|
232
|
+
this.sub.add(this.service.usage$.subscribe((usage) => {
|
|
233
|
+
this.usage = usage;
|
|
234
|
+
this.cdr.markForCheck();
|
|
235
|
+
}));
|
|
236
|
+
}
|
|
237
|
+
ngOnDestroy() {
|
|
238
|
+
this.sub.unsubscribe();
|
|
239
|
+
}
|
|
240
|
+
/** Usage as a whole percentage. */
|
|
241
|
+
get percent() {
|
|
242
|
+
return Math.round(this.usage.ratio * 100);
|
|
243
|
+
}
|
|
244
|
+
get computedClass() {
|
|
245
|
+
return cn(contextTriggerVariants({ level: this.usage.level }), this.class);
|
|
246
|
+
}
|
|
247
|
+
get barClass() {
|
|
248
|
+
return cn('block', contextBarVariants({ level: this.usage.level }));
|
|
249
|
+
}
|
|
250
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextTriggerComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
251
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: ContextTriggerComponent, isStandalone: true, selector: "tolle-context-trigger", inputs: { class: "class" }, usesOnChanges: true, ngImport: i0, template: `
|
|
252
|
+
<span
|
|
253
|
+
role="meter"
|
|
254
|
+
[attr.aria-valuenow]="percent"
|
|
255
|
+
aria-valuemin="0"
|
|
256
|
+
aria-valuemax="100"
|
|
257
|
+
[attr.aria-label]="'Context window ' + percent + '% used'"
|
|
258
|
+
[attr.data-level]="usage.level"
|
|
259
|
+
[class]="computedClass"
|
|
260
|
+
>
|
|
261
|
+
<span class="h-1.5 w-10 overflow-hidden rounded-full bg-muted">
|
|
262
|
+
<span [class]="barClass" [style.width.%]="percent"></span>
|
|
263
|
+
</span>
|
|
264
|
+
<span>{{ percent }}%</span>
|
|
265
|
+
<ng-content></ng-content>
|
|
266
|
+
</span>
|
|
267
|
+
`, isInline: true, styles: [":host{display:block}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
268
|
+
}
|
|
269
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextTriggerComponent, decorators: [{
|
|
270
|
+
type: Component,
|
|
271
|
+
args: [{ selector: 'tolle-context-trigger', standalone: true, imports: [CommonModule], changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
272
|
+
<span
|
|
273
|
+
role="meter"
|
|
274
|
+
[attr.aria-valuenow]="percent"
|
|
275
|
+
aria-valuemin="0"
|
|
276
|
+
aria-valuemax="100"
|
|
277
|
+
[attr.aria-label]="'Context window ' + percent + '% used'"
|
|
278
|
+
[attr.data-level]="usage.level"
|
|
279
|
+
[class]="computedClass"
|
|
280
|
+
>
|
|
281
|
+
<span class="h-1.5 w-10 overflow-hidden rounded-full bg-muted">
|
|
282
|
+
<span [class]="barClass" [style.width.%]="percent"></span>
|
|
283
|
+
</span>
|
|
284
|
+
<span>{{ percent }}%</span>
|
|
285
|
+
<ng-content></ng-content>
|
|
286
|
+
</span>
|
|
287
|
+
`, styles: [":host{display:block}\n"] }]
|
|
288
|
+
}], propDecorators: { class: [{
|
|
289
|
+
type: Input
|
|
290
|
+
}] } });
|
|
291
|
+
/** The hover breakdown of a `tolle-context`: used, total, input, output, cost. */
|
|
292
|
+
export class ContextContentComponent {
|
|
293
|
+
/**
|
|
294
|
+
* Angular writes a bound `class` input through its styling path, which does
|
|
295
|
+
* not mark an OnPush component dirty — without this hook the component keeps
|
|
296
|
+
* rendering the class it was born with.
|
|
297
|
+
*/
|
|
298
|
+
ngOnChanges() {
|
|
299
|
+
this.cdr.markForCheck();
|
|
300
|
+
}
|
|
301
|
+
/** Symbol prefixed to the cost figure. @default '$' */
|
|
302
|
+
currency = '$';
|
|
303
|
+
/** Extra Tailwind classes merged onto the breakdown via `cn()` (last-wins). */
|
|
304
|
+
class = '';
|
|
305
|
+
service = inject(ContextService);
|
|
306
|
+
cdr = inject(ChangeDetectorRef);
|
|
307
|
+
sub = new Subscription();
|
|
308
|
+
usage = this.service.usage;
|
|
309
|
+
tokens = formatTokens;
|
|
310
|
+
ngOnInit() {
|
|
311
|
+
this.sub.add(this.service.usage$.subscribe((usage) => {
|
|
312
|
+
this.usage = usage;
|
|
313
|
+
this.cdr.markForCheck();
|
|
314
|
+
}));
|
|
315
|
+
}
|
|
316
|
+
ngOnDestroy() {
|
|
317
|
+
this.sub.unsubscribe();
|
|
318
|
+
}
|
|
319
|
+
get computedClass() {
|
|
320
|
+
return cn('flex flex-col p-3', this.class);
|
|
321
|
+
}
|
|
322
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextContentComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
323
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.14", type: ContextContentComponent, isStandalone: true, selector: "tolle-context-content", inputs: { currency: "currency", class: "class" }, usesOnChanges: true, ngImport: i0, template: `
|
|
324
|
+
<div [class]="computedClass">
|
|
325
|
+
<div class="flex items-baseline justify-between gap-2">
|
|
326
|
+
<span class="text-sm font-medium text-popover-foreground">Context</span>
|
|
327
|
+
<span class="text-xs tabular-nums text-muted-foreground">{{ tokens(usage.used) }} / {{ tokens(usage.total) }}</span>
|
|
328
|
+
</div>
|
|
329
|
+
<dl class="mt-2 flex flex-col gap-1 text-xs">
|
|
330
|
+
<div *ngIf="usage.inputTokens !== null" class="flex items-center justify-between gap-2">
|
|
331
|
+
<dt class="text-muted-foreground">Input</dt>
|
|
332
|
+
<dd class="tabular-nums text-popover-foreground">{{ tokens(usage.inputTokens) }}</dd>
|
|
333
|
+
</div>
|
|
334
|
+
<div *ngIf="usage.outputTokens !== null" class="flex items-center justify-between gap-2">
|
|
335
|
+
<dt class="text-muted-foreground">Output</dt>
|
|
336
|
+
<dd class="tabular-nums text-popover-foreground">{{ tokens(usage.outputTokens) }}</dd>
|
|
337
|
+
</div>
|
|
338
|
+
<div *ngIf="usage.cost !== null" class="flex items-center justify-between gap-2">
|
|
339
|
+
<dt class="text-muted-foreground">Cost</dt>
|
|
340
|
+
<dd class="tabular-nums text-popover-foreground">{{ currency }}{{ usage.cost }}</dd>
|
|
341
|
+
</div>
|
|
342
|
+
</dl>
|
|
343
|
+
<ng-content></ng-content>
|
|
344
|
+
</div>
|
|
345
|
+
`, isInline: true, styles: [":host{display:block}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
346
|
+
}
|
|
347
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: ContextContentComponent, decorators: [{
|
|
348
|
+
type: Component,
|
|
349
|
+
args: [{ selector: 'tolle-context-content', standalone: true, imports: [CommonModule], changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
350
|
+
<div [class]="computedClass">
|
|
351
|
+
<div class="flex items-baseline justify-between gap-2">
|
|
352
|
+
<span class="text-sm font-medium text-popover-foreground">Context</span>
|
|
353
|
+
<span class="text-xs tabular-nums text-muted-foreground">{{ tokens(usage.used) }} / {{ tokens(usage.total) }}</span>
|
|
354
|
+
</div>
|
|
355
|
+
<dl class="mt-2 flex flex-col gap-1 text-xs">
|
|
356
|
+
<div *ngIf="usage.inputTokens !== null" class="flex items-center justify-between gap-2">
|
|
357
|
+
<dt class="text-muted-foreground">Input</dt>
|
|
358
|
+
<dd class="tabular-nums text-popover-foreground">{{ tokens(usage.inputTokens) }}</dd>
|
|
359
|
+
</div>
|
|
360
|
+
<div *ngIf="usage.outputTokens !== null" class="flex items-center justify-between gap-2">
|
|
361
|
+
<dt class="text-muted-foreground">Output</dt>
|
|
362
|
+
<dd class="tabular-nums text-popover-foreground">{{ tokens(usage.outputTokens) }}</dd>
|
|
363
|
+
</div>
|
|
364
|
+
<div *ngIf="usage.cost !== null" class="flex items-center justify-between gap-2">
|
|
365
|
+
<dt class="text-muted-foreground">Cost</dt>
|
|
366
|
+
<dd class="tabular-nums text-popover-foreground">{{ currency }}{{ usage.cost }}</dd>
|
|
367
|
+
</div>
|
|
368
|
+
</dl>
|
|
369
|
+
<ng-content></ng-content>
|
|
370
|
+
</div>
|
|
371
|
+
`, styles: [":host{display:block}\n"] }]
|
|
372
|
+
}], propDecorators: { currency: [{
|
|
373
|
+
type: Input
|
|
374
|
+
}], class: [{
|
|
375
|
+
type: Input
|
|
376
|
+
}] } });
|
|
377
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY29udGV4dC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9wcm9qZWN0cy90b2xsZS9zcmMvbGliL2NvbnRleHQuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSx1QkFBdUIsRUFBRSxpQkFBaUIsRUFBRSxTQUFTLEVBQUUsVUFBVSxFQUFFLEtBQUssRUFBZ0MsVUFBVSxFQUFFLE1BQU0sRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUMzSixPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0saUJBQWlCLENBQUM7QUFDL0MsT0FBTyxFQUFFLGVBQWUsRUFBRSxZQUFZLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFDckQsT0FBTyxFQUFFLEdBQUcsRUFBcUIsTUFBTSwwQkFBMEIsQ0FBQztBQUNsRSxPQUFPLEVBQUUsRUFBRSxFQUFFLE1BQU0sWUFBWSxDQUFDO0FBQ2hDLE9BQU8sRUFDTCxrQkFBa0IsRUFDbEIseUJBQXlCLEVBQ3pCLHlCQUF5QixHQUMxQixNQUFNLHdCQUF3QixDQUFDOzs7QUFpQmhDLE1BQU0sc0JBQXNCLEdBQUcsR0FBRyxDQUNoQyw0R0FBNEcsRUFDNUc7SUFDRSxRQUFRLEVBQUU7UUFDUixLQUFLLEVBQUU7WUFDTCxNQUFNLEVBQUUsNkNBQTZDO1lBQ3JELE9BQU8sRUFBRSxpQ0FBaUM7WUFDMUMsUUFBUSxFQUFFLHlDQUF5QztTQUNwRDtLQUNGO0lBQ0QsZUFBZSxFQUFFLEVBQUUsS0FBSyxFQUFFLFFBQVEsRUFBRTtDQUNyQyxDQUNGLENBQUM7QUFFRixNQUFNLGtCQUFrQixHQUFHLEdBQUcsQ0FBQyxzRUFBc0UsRUFBRTtJQUNyRyxRQUFRLEVBQUU7UUFDUixLQUFLLEVBQUU7WUFDTCxNQUFNLEVBQUUsWUFBWTtZQUNwQixPQUFPLEVBQUUsWUFBWTtZQUNyQixRQUFRLEVBQUUsZ0JBQWdCO1NBQzNCO0tBQ0Y7SUFDRCxlQUFlLEVBQUUsRUFBRSxLQUFLLEVB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eEJTLFlBQVk7OzRGQTBCWCx1QkFBdUI7a0JBOUJuQyxTQUFTOytCQUNFLHVCQUF1QixjQUVyQixJQUFJLFdBQ1AsQ0FBQyxZQUFZLENBQUMsbUJBQ04sdUJBQXVCLENBQUMsTUFBTSxZQUNyQzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztHQXNCVDs4QkFjUSxRQUFRO3NCQUFoQixLQUFLO2dCQUVHLEtBQUs7c0JBQWIsS0FBSyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IENoYW5nZURldGVjdGlvblN0cmF0ZWd5LCBDaGFuZ2VEZXRlY3RvclJlZiwgQ29tcG9uZW50LCBJbmplY3RhYmxlLCBJbnB1dCwgT25DaGFuZ2VzLCBPbkRlc3Ryb3ksIE9uSW5pdCwgZm9yd2FyZFJlZiwgaW5qZWN0IH0gZnJvbSAnQGFuZ3VsYXIvY29yZSc7XG5pbXBvcnQgeyBDb21tb25Nb2R1bGUgfSBmcm9tICdAYW5ndWxhci9jb21tb24nO1xuaW1wb3J0IHsgQmVoYXZpb3JTdWJqZWN0LCBTdWJzY3JpcHRpb24gfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IGN2YSwgdHlwZSBWYXJpYW50UHJvcHMgfSBmcm9tICdjbGFzcy12YXJpYW5jZS1hdXRob3JpdHknO1xuaW1wb3J0IHsgY24gfSBmcm9tICcuL3V0aWxzL2NuJztcbmltcG9ydCB7XG4gIEhvdmVyQ2FyZENvbXBvbmVudCxcbiAgSG92ZXJDYXJkVHJpZ2dlckNvbXBvbmVudCxcbiAgSG92ZXJDYXJkQ29udGVudENvbXBvbmVudCxcbn0gZnJvbSAnLi9ob3Zlci1jYXJkLmNvbXBvbmVudCc7XG5cbi8qKiBIb3cgY2xvc2UgdGhlIGNvbnRleHQgd2luZG93IGlzIHRvIGJlaW5nIGZ1bGwuICovXG5leHBvcnQgdHlwZSBDb250ZXh0TGV2ZWwgPSAnbm9ybWFsJyB8ICd3YXJuaW5nJyB8ICdjcml0aWNhbCc7XG5cbi8qKiBFdmVyeXRoaW5nIGEgYHRvbGxlLWNvbnRleHRgIGtub3dzIGFib3V0IHRoZSBjdXJyZW50IHdpbmRvdy4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgQ29udGV4dFVzYWdlIHtcbiAgdXNlZDogbnVtYmVyO1xuICB0b3RhbDogbnVtYmVyO1xuICBpbnB1dFRva2VuczogbnVtYmVyIHwgbnVsbDtcbiAgb3V0cHV0VG9rZW5zOiBudW1iZXIgfCBudWxsO1xuICBjb3N0OiBudW1iZXIgfCBudWxsO1xuICAvKiogRnJhY3Rpb24gb2YgdGhlIHdpbmRvdyBjb25zdW1lZCwgY2xhbXBlZCB0byAw4oCTMS4gKi9cbiAgcmF0aW86IG51bWJlcjtcbiAgbGV2ZWw6IENvbnRleHRMZXZlbDtcbn1cblxuY29uc3QgY29udGV4dFRyaWdnZXJWYXJpYW50cyA9IGN2YShcbiAgJ2lubGluZS1mbGV4IGl0ZW1zLWNlbnRlciBnYXAtMS41IHJvdW5kZWQtbWQgcHgtMS41IHB5LTEgdGV4dC14cyBmb250LW1lZGl1bSB0YWJ1bGFyLW51bXMgdHJhbnNpdGlvbi1jb2xvcnMnLFxuICB7XG4gICAgdmFyaWFudHM6IHtcbiAgICAgIGxldmVsOiB7XG4gICAgICAgIG5vcm1hbDogJ3RleHQtbXV0ZWQtZm9yZWdyb3VuZCBob3Zlcjp0ZXh0LWZvcmVncm91bmQnLFxuICAgICAgICB3YXJuaW5nOiAndGV4dC13YXJuaW5nIGhvdmVyOnRleHQtd2FybmluZycsXG4gICAgICAgIGNyaXRpY2FsOiAndGV4dC1kZXN0cnVjdGl2ZSBob3Zlcjp0ZXh0LWRlc3RydWN0aXZlJyxcbiAgICAgIH0sXG4gICAgfSxcbiAgICBkZWZhdWx0VmFyaWFudHM6IHsgbGV2ZWw6ICdub3JtYWwnIH0sXG4gIH1cbik7XG5cbmNvbnN0IGNvbnRleHRCYXJWYXJpYW50cyA9IGN2YSgnaC1mdWxsIHJvdW5kZWQtZnVsbCB0cmFuc2l0aW9uLVt3aWR0aCxiYWNrZ3JvdW5kLWNvbG9yXSBkdXJhdGlvbi0zMDAnLCB7XG4gIHZhcmlhbnRzOiB7XG4gICAgbGV2ZWw6IHtcbiAgICAgIG5vcm1hbDogJ2JnLXByaW1hcnknLFxuICAgICAgd2FybmluZzogJ2JnLXdhcm5pbmcnLFxuICAgICAgY3JpdGljYWw6ICdiZy1kZXN0cnVjdGl2ZScsXG4gICAgfSxcbiAgfSxcbiAgZGVmYXVsdFZhcmlhbnRzOiB7IGxldmVsOiAnbm9ybWFsJyB9LFxufSk7XG5cbmV4cG9ydCB0eXBlIENvbnRleHRQcm9wcyA9IFZhcmlhbnRQcm9wczx0eXBlb2YgY29udGV4dFRyaWdnZXJWYXJpYW50cz47XG5cbi8qKiBGb3JtYXRzIGEgcmF3IHRva2VuIGNvdW50IGFzIGEgc2hvcnQsIHJlYWRhYmxlIHN0cmluZy4gKi9cbmV4cG9ydCBmdW5jdGlvbiBmb3JtYXRUb2tlbnModmFsdWU6IG51bWJlcik6IHN0cmluZyB7XG4gIGlmICghaXNGaW5pdGUodmFsdWUpKSByZXR1cm4gJzAnO1xuICBjb25zdCBhYnMgPSBNYXRoLmFicyh2YWx1ZSk7XG4gIGlmIChhYnMgPj0gMV8wMDBfMDAwKSByZXR1cm4gKHZhbHVlIC8gMV8wMDBfMDAwKS50b0ZpeGVkKDEpLnJlcGxhY2UoL1xcLjAkLywgJycpICsgJ00nO1xuICBpZiAoYWJzID49IDFfMDAwKSByZXR1cm4gKHZhbHVlIC8gMV8wMDApLnRvRml4ZWQoMSkucmVwbGFjZSgvXFwuMCQvLCAnJykgKyAnSyc7XG4gIHJldHVybiBTdHJpbmcoTWF0aC5yb3VuZCh2YWx1ZSkpO1xufVxuXG4vKipcbiAqIFB1Ymxpc2hlcyB0aGUgcGFyZW50IGB0b2xsZS1jb250ZXh0YCdzIG51bWJlcnMgdG8gaXRzIE9uUHVzaCB0cmlnZ2VyIGFuZFxuICogY29udGVudCBjaGlsZHJlbiwgd2hpY2ggcmVjZWl2ZSBub25lIG9mIGl0IGFzIHRoZWlyIG93biBpbnB1dHMuXG4gKi9cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBDb250ZXh0U2VydmljZSB7XG4gIHByaXZhdGUgcmVhZG9ubHkgdXNhZ2VTb3VyY2UgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PENvbnRleHRVc2FnZT4oe1xuICAgIHVzZWQ6IDAsXG4gICAgdG90YWw6IDAsXG4gICAgaW5wdXRUb2tlbnM6IG51bGwsXG4gICAgb3V0cHV0VG9rZW5zOiBudWxsLFxuICAgIGNvc3Q6IG51bGwsXG4gICAgcmF0aW86IDAsXG4gICAgbGV2ZWw6ICdub3JtYWwnLFxuICB9KTtcblxuICAvKiogRW1pdHMgdGhlIGN1cnJlbnQgY29udGV4dC13aW5kb3cgdXNhZ2UuICovXG4gIHJlYWRvbmx5IHVzYWdlJCA9IHRoaXMudXNhZ2VTb3VyY2UuYXNPYnNlcnZhYmxlKCk7XG5cbiAgZ2V0IHVzYWdlKCk6IENvbnRleHRVc2FnZSB7XG4gICAgcmV0dXJuIHRoaXMudXNhZ2VTb3VyY2UudmFsdWU7XG4gIH1cblxuICBzZXRVc2FnZSh1c2FnZTogQ29udGV4dFVzYWdlKTogdm9pZCB7XG4gICAgdGhpcy51c2FnZVNvdXJjZS5uZXh0KHVzYWdlKTtcbiAgfVxufVxuXG4vKipcbiAqIEEgdG9rZW4gLyBjb250ZXh0LXdpbmRvdyB1c2FnZSBpbmRpY2F0b3I6IGEgY29tcGFjdCBwZXJjZW50YWdlIGFuZCBiYXIgdGhhdFxuICogc2hpZnRzIHRvIHRoZSB3YXJuaW5nIGFuZCBkZXN0cnVjdGl2ZSB0b2tlbnMgYXMgdGhlIHdpbmRvdyBmaWxscywgd2l0aCBhXG4gKiBob3ZlciBicmVha2Rvd24gb2YgaW5wdXQsIG91dHB1dCBhbmQgY29zdC5cbiAqXG4gKiBgYGBodG1sXG4gKiA8dG9sbGUtY29udGV4dCBbdXNlZF09XCI4MjAwMFwiIFt0b3RhbF09XCIxMjgwMDBcIiBbaW5wdXRUb2tlbnNdPVwiNjEwMDBcIiBbb3V0cHV0VG9rZW5zXT1cIjIxMDAwXCIgW2Nvc3RdPVwiMC40MlwiPjwvdG9sbGUtY29udGV4dD5cbiAqIGBgYFxuICogQG5ld1xuICovXG5AQ29tcG9uZW50KHtcbiAgc2VsZWN0b3I6ICd0b2xsZS1jb250ZXh0JyxcbiAgc3R5bGVzOiBbJzpob3N0IHsgZGlzcGxheTogYmxvY2s7IH0nXSxcbiAgc3RhbmRhbG9uZTogdHJ1ZSxcbiAgaW1wb3J0czogW1xuICAgIENvbW1vbk1vZHVsZSxcbiAgICBIb3ZlckNhcmRDb21wb25lbnQsXG4gICAgSG92ZXJDYXJkVHJpZ2dlckNvbXBvbmVudCxcbiAgICBIb3ZlckNhcmRDb250ZW50Q29tcG9uZW50LFxuICAgIC8vIFRoZSBzdWItY29tcG9uZW50cyBhcmUgZGVjbGFyZWQgZnVydGhlciBkb3duIHRoaXMgZmlsZSwgc28gdGhleSBhcmVcbiAgICAvLyByZWZlcmVuY2VkIGxhemlseSByYXRoZXIgdGhhbiByZWFkIGF0IGRlY29yYXRpb24gdGltZS5cbiAgICBmb3J3YXJkUmVmKCgpID0+IENvbnRleHRUcmlnZ2VyQ29tcG9uZW50KSxcbiAgICBmb3J3YXJkUmVmKCgpID0+IENvbnRleHRDb250ZW50Q29tcG9uZW50KSxcbiAgXSxcbiAgcHJvdmlkZXJzOiBbQ29udGV4dFNlcnZpY2VdLFxuICBjaGFuZ2VEZXRlY3Rpb246IENoYW5nZURldGVjdGlvblN0cmF0ZWd5Lk9uUHVzaCxcbiAgdGVtcGxhdGU6IGBcbiAgICA8dG9sbGUtaG92ZXItY2FyZFxuICAgICAgW29wZW5EZWxheV09XCJvcGVuRGVsYXlcIlxuICAgICAgW2Nsb3NlRGVsYXldPVwiY2xvc2VEZWxheVwiXG4gICAgICBbcGxhY2VtZW50XT1cInBsYWNlbWVudFwiXG4gICAgICAobW91c2VlbnRlcik9XCJzY2hlZHVsZVJlZnJlc2gob3BlbkRlbGF5KVwiXG4gICAgICAobW91c2VsZWF2ZSk9XCJzY2hlZHVsZVJlZnJlc2goY2xvc2VEZWxheSlcIlxuICAgID5cbiAgICAgIDx0b2xsZS1ob3Zlci1jYXJkLXRyaWdnZXI+XG4gICAgICAgIDx0b2xsZS1jb250ZXh0LXRyaWdnZXI+PC90b2xsZS1jb250ZXh0LXRyaWdnZXI+XG4gICAgICA8L3RvbGxlLWhvdmVyLWNhcmQtdHJpZ2dlcj5cbiAgICAgIDx0b2xsZS1ob3Zlci1jYXJkLWNvbnRlbnQgY2xhc3M9XCJ3LTYwIHAtMFwiPlxuICAgICAgICA8dG9sbGUtY29udGV4dC1jb250ZW50PjwvdG9sbGUtY29udGV4dC1jb250ZW50PlxuICAgICAgPC90b2xsZS1ob3Zlci1jYXJkLWNvbnRlbnQ+XG4gICAgPC90b2xsZS1ob3Zlci1jYXJkPlxuICBgLFxufSlcbmV4cG9ydCBjbGFzcyBDb250ZXh0Q29tcG9uZW50IGltcGxlbWVudHMgT25Jbml0LCBPbkNoYW5nZXMsIE9uRGVzdHJveSB7XG4gIC8qKiBUb2tlbnMgY29uc3VtZWQgc28gZmFyLiBAZGVmYXVsdCAwICovXG4gIEBJbnB1dCgpIHVzZWQgPSAwO1xuICAvKiogU2l6ZSBvZiB0aGUgY29udGV4dCB3aW5kb3cgaW4gdG9rZW5zLiBAZGVmYXVsdCAwICovXG4gIEBJbnB1dCgpIHRvdGFsID0gMDtcbiAgLyoqIFRva2VucyBzcGVudCBvbiB0aGUgcHJvbXB0LCBzaG93biBpbiB0aGUgYnJlYWtkb3duLiBAZGVmYXVsdCBudWxsICovXG4gIEBJbnB1dCgpIGlucHV0VG9rZW5zOiBudW1iZXIgfCBudWxsID0gbnVsbDtcbiAgLyoqIFRva2VucyBwcm9kdWNlZCBieSB0aGUgbW9kZWwsIHNob3duIGluIHRoZSBicmVha2Rvd24uIEBkZWZhdWx0IG51bGwgKi9cbiAgQElucHV0KCkgb3V0cHV0VG9rZW5zOiBudW1iZXIgfCBudWxsID0gbnVsbDtcbiAgLyoqIFNwZW5kIGZvciB0aGlzIGNvbnRleHQsIHNob3duIGluIHRoZSBicmVha2Rvd24uIEBkZWZhdWx0IG51bGwgKi9cbiAgQElucHV0KCkgY29zdDogbnVtYmVyIHwgbnVsbCA9IG51bGw7XG4gIC8qKiBSYXRpbyBhdCBvciBhYm92ZSB3aGljaCB0aGUgaW5kaWNhdG9yIHR1cm5zIHdhcm5pbmctY29sb3VyZWQuIEBkZWZhdWx0IDAuNzUgKi9cbiAgQElucHV0KCkgd2FybmluZ1RocmVzaG9sZCA9IDAuNzU7XG4gIC8qKiBSYXRpbyBhdCBvciBhYm92ZSB3aGljaCB0aGUgaW5kaWNhdG9yIHR1cm5zIGRlc3RydWN0aXZlLWNvbG91cmVkLiBAZGVmYXVsdCAwLjkgKi9cbiAgQElucHV0KCkgY3JpdGljYWxUaHJlc2hvbGQgPSAwLjk7XG4gIC8qKiBTaWRlIG9mIHRoZSBpbmRpY2F0b3IgdGhlIGJyZWFrZG93biBvcGVucyBvbi4gQGRlZmF1bHQgJ3RvcCcgKi9cbiAgQElucHV0KCkgcGxhY2VtZW50OiAndG9wJyB8ICdib3R0b20nIHwgJ2xlZnQnIHwgJ3JpZ2h0JyA9ICd0b3AnO1xuICAvKiogTWlsbGlzZWNvbmRzIHRvIHdhaXQgYmVmb3JlIG9wZW5pbmcgdGhlIGJyZWFrZG93bi4gQGRlZmF1bHQgMTUwICovXG4gIEBJbnB1dCgpIG9wZW5EZWxheSA9IDE1MDtcbiAgLyoqIE1pbGxpc2Vjb25kcyB0byB3YWl0IGJlZm9yZSBjbG9zaW5nIHRoZSBicmVha2Rvd24uIEBkZWZhdWx0IDIwMCAqL1xuICBASW5wdXQoKSBjbG9zZURlbGF5ID0gMjAwO1xuICAvKiogRXh0cmEgVGFpbHdpbmQgY2xhc3NlcyBtZXJnZWQgb250byB0aGUgaW5kaWNhdG9yIHZpYSBgY24oKWAgKGxhc3Qtd2lucykuICovXG4gIEBJbnB1dCgpIGNsYXNzID0gJyc7XG5cbiAgcHJpdmF0ZSByZWFkb25seSBzZXJ2aWNlID0gaW5qZWN0KENvbnRleHRTZXJ2aWNlKTtcbiAgcHJpdmF0ZSByZWFkb25seSBjZHIgPSBpbmplY3QoQ2hhbmdlRGV0ZWN0b3JSZWYpO1xuICBwcml2YXRlIHJlZnJlc2hUaW1lcj86IFJldHVyblR5cGU8dHlwZW9mIHNldFRpbWVvdXQ+O1xuXG4gIG5nT25Jbml0KCk6IHZvaWQge1xuICAgIHRoaXMucHVzaCgpO1xuICB9XG5cbiAgbmdPbkNoYW5nZXMoKTogdm9pZCB7XG4gICAgdGhpcy5wdXNoKCk7XG4gIH1cblxuICAvKiogRnJhY3Rpb24gb2YgdGhlIHdpbmRvdyBjb25zdW1lZCwgY2xhbXBlZCB0byAw4oCTMS4gKi9cbiAgZ2V0IHJhdGlvKCk6IG51bWJlciB7XG4gICAgaWYgKCF0aGlzLnRvdGFsIHx8IHRoaXMudG90YWwgPD0gMCkgcmV0dXJuIDA7XG4gICAgcmV0dXJuIE1hdGgubWluKDEsIE1hdGgubWF4KDAsIHRoaXMudXNlZCAvIHRoaXMudG90YWwpKTtcbiAgfVxuXG4gIC8qKiBXaGljaCBjb2xvdXIgYmFuZCB0aGUgY3VycmVudCB1c2FnZSBmYWxscyBpbnRvLiAqL1xuICBnZXQgbGV2ZWwoKTogQ29udGV4dExldmVsIHtcbiAgICBjb25zdCByYXRpbyA9IHRoaXMucmF0aW87XG4gICAgaWYgKHJhdGlvID49IHRoaXMuY3JpdGljYWxUaHJlc2hvbGQpIHJldHVybiAnY3JpdGljYWwnO1xuICAgIGlmIChyYXRpbyA+PSB0aGlzLndhcm5pbmdUaHJlc2hvbGQpIHJldHVybiAnd2FybmluZyc7XG4gICAgcmV0dXJuICdub3JtYWwnO1xuICB9XG5cbiAgcHJpdmF0ZSBwdXNoKCk6IHZvaWQge1xuICAgIHRoaXMuc2VydmljZS5zZXRVc2FnZSh7XG4gICAgICB1c2VkOiB0aGlzLnVzZWQsXG4gICAgICB0b3RhbDogdGhpcy50b3RhbCxcbiAgICAgIGlucHV0VG9rZW5zOiB0aGlzLmlucHV0VG9rZW5zLFxuICAgICAgb3V0cHV0VG9rZW5zOiB0aGlzLm91dHB1dFRva2VucyxcbiAgICAgIGNvc3Q6IHRoaXMuY29zdCxcbiAgICAgIHJhdGlvOiB0aGlzLnJhdGlvLFxuICAgICAgbGV2ZWw6IHRoaXMubGV2ZWwsXG4gICAgfSk7XG4gIH1cblxuICAvKipcbiAgICogYHRvbGxlLWhvdmVyLWNhcmRgIHRvZ2dsZXMgaXRzIG93biB2aXNpYmlsaXR5IGZyb20gYSBgc2V0VGltZW91dGAsIHdoaWNoXG4gICAqIG5ldmVyIG1hcmtzIHRoaXMgT25QdXNoIHZpZXcgZGlydHkg4oCUIHJlLWNoZWNrIG9uY2UgdGhlIGRlbGF5IGhhcyBlbGFwc2VkLlxuICAgKi9cbiAgc2NoZWR1bGVSZWZyZXNoKGRlbGF5OiBudW1iZXIpOiB2b2lkIHtcbiAgICBjbGVhclRpbWVvdXQodGhpcy5yZWZyZXNoVGltZXIpO1xuICAgIHRoaXMucmVmcmVzaFRpbWVyID0gc2V0VGltZW91dCgoKSA9PiB0aGlzLmNkci5tYXJrRm9yQ2hlY2soKSwgZGVsYXkgKyAzMik7XG4gIH1cblxuICBuZ09uRGVzdHJveSgpOiB2b2lkIHtcbiAgICBjbGVhclRpbWVvdXQodGhpcy5yZWZyZXNoVGltZXIpO1xuICB9XG59XG5cbi8qKiBUaGUgYWx3YXlzLXZpc2libGUgcGFydCBvZiBhIGB0b2xsZS1jb250ZXh0YDogcGVyY2VudGFnZSBwbHVzIHVzYWdlIGJhci4gKi9cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ3RvbGxlLWNvbnRleHQtdHJpZ2dlcicsXG4gIHN0eWxlczogWyc6aG9zdCB7IGRpc3BsYXk6IGJsb2NrOyB9J10sXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtDb21tb25Nb2R1bGVdLFxuICBjaGFuZ2VEZXRlY3Rpb246IENoYW5nZURldGVjdGlvblN0cmF0ZWd5Lk9uUHVzaCxcbiAgdGVtcGxhdGU6IGBcbiAgICA8c3BhblxuICAgICAgcm9sZT1cIm1ldGVyXCJcbiAgICAgIFthdHRyLmFyaWEtdmFsdWVub3ddPVwicGVyY2VudFwiXG4gICAgICBhcmlhLXZhbHVlbWluPVwiMFwiXG4gICAgICBhcmlhLXZhbHVlbWF4PVwiMTAwXCJcbiAgICAgIFthdHRyLmFyaWEtbGFiZWxdPVwiJ0NvbnRleHQgd2luZG93ICcgKyBwZXJjZW50ICsgJyUgdXNlZCdcIlxuICAgICAgW2F0dHIuZGF0YS1sZXZlbF09XCJ1c2FnZS5sZXZlbFwiXG4gICAgICBbY2xhc3NdPVwiY29tcHV0ZWRDbGFzc1wiXG4gICAgPlxuICAgICAgPHNwYW4gY2xhc3M9XCJoLTEuNSB3LTEwIG92ZXJmbG93LWhpZGRlbiByb3VuZGVkLWZ1bGwgYmctbXV0ZWRcIj5cbiAgICAgICAgPHNwYW4gW2NsYXNzXT1cImJhckNsYXNzXCIgW3N0eWxlLndpZHRoLiVdPVwicGVyY2VudFwiPjwvc3Bhbj5cbiAgICAgIDwvc3Bhbj5cbiAgICAgIDxzcGFuPnt7IHBlcmNlbnQgfX0lPC9zcGFuPlxuICAgICAgPG5nLWNvbnRlbnQ+PC9uZy1jb250ZW50PlxuICAgIDwvc3Bhbj5cbiAgYCxcbn0pXG5leHBvcnQgY2xhc3MgQ29udGV4dFRyaWdnZXJDb21wb25lbnQgaW1wbGVtZW50cyBPbkNoYW5nZXMsIE9uSW5pdCwgT25EZXN0cm95IHtcblxuICAvKipcbiAgICogQW5ndWxhciB3cml0ZXMgYSBib3VuZCBgY2xhc3NgIGlucHV0IHRocm91Z2ggaXRzIHN0eWxpbmcgcGF0aCwgd2hpY2ggZG9lc1xuICAgKiBub3QgbWFyayBhbiBPblB1c2ggY29tcG9uZW50IGRpcnR5IOKAlCB3aXRob3V0IHRoaXMgaG9vayB0aGUgY29tcG9uZW50IGtlZXBzXG4gICAqIHJlbmRlcmluZyB0aGUgY2xhc3MgaXQgd2FzIGJvcm4gd2l0aC5cbiAgICovXG4gIG5nT25DaGFuZ2VzKCk6IHZvaWQge1xuICAgIHRoaXMuY2RyLm1hcmtGb3JDaGVjaygpO1xuICB9XG5cbiAgLyoqIEV4dHJhIFRhaWx3aW5kIGNsYXNzZXMgbWVyZ2VkIG9udG8gdGhlIHRyaWdnZXIgdmlhIGBjbigpYCAobGFzdC13aW5zKS4gKi9cbiAgQElucHV0KCkgY2xhc3MgPSAnJztcblxuICBwcml2YXRlIHJlYWRvbmx5IHNlcnZpY2UgPSBpbmplY3QoQ29udGV4dFNlcnZpY2UpO1xuICBwcml2YXRlIHJlYWRvbmx5IGNkciA9IGluamVjdChDaGFuZ2VEZXRlY3RvclJlZik7XG4gIHByaXZhdGUgcmVhZG9ubHkgc3ViID0gbmV3IFN1YnNjcmlwdGlvbigpO1xuXG4gIHVzYWdlOiBDb250ZXh0VXNhZ2UgPSB0aGlzLnNlcnZpY2UudXNhZ2U7XG5cbiAgbmdPbkluaXQoKTogdm9pZCB7XG4gICAgdGhpcy5zdWIuYWRkKFxuICAgICAgdGhpcy5zZXJ2aWNlLnVzYWdlJC5zdWJzY3JpYmUoKHVzYWdlKSA9PiB7XG4gICAgICAgIHRoaXMudXNhZ2UgPSB1c2FnZTtcbiAgICAgICAgdGhpcy5jZHIubWFya0ZvckNoZWNrKCk7XG4gICAgICB9KVxuICAgICk7XG4gIH1cblxuICBuZ09uRGVzdHJveSgpOiB2b2lkIHtcbiAgICB0aGlzLnN1Yi51bnN1YnNjcmliZSgpO1xuICB9XG5cbiAgLyoqIFVzYWdlIGFzIGEgd2hvbGUgcGVyY2VudGFnZS4gKi9cbiAgZ2V0IHBlcmNlbnQoKTogbnVtYmVyIHtcbiAgICByZXR1cm4gTWF0aC5yb3VuZCh0aGlzLnVzYWdlLnJhdGlvICogMTAwKTtcbiAgfVxuXG4gIGdldCBjb21wdXRlZENsYXNzKCkge1xuICAgIHJldHVybiBjbihjb250ZXh0VHJpZ2dlclZhcmlhbnRzKHsgbGV2ZWw6IHRoaXMudXNhZ2UubGV2ZWwgfSksIHRoaXMuY2xhc3MpO1xuICB9XG5cbiAgZ2V0IGJhckNsYXNzKCkge1xuICAgIHJldHVybiBjbignYmxvY2snLCBjb250ZXh0QmFyVmFyaWFudHMoeyBsZXZlbDogdGhpcy51c2FnZS5sZXZlbCB9KSk7XG4gIH1cbn1cblxuLyoqIFRoZSBob3ZlciBicmVha2Rvd24gb2YgYSBgdG9sbGUtY29udGV4dGA6IHVzZWQsIHRvdGFsLCBpbnB1dCwgb3V0cHV0LCBjb3N0LiAqL1xuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAndG9sbGUtY29udGV4dC1jb250ZW50JyxcbiAgc3R5bGVzOiBbJzpob3N0IHsgZGlzcGxheTogYmxvY2s7IH0nXSxcbiAgc3RhbmRhbG9uZTogdHJ1ZSxcbiAgaW1wb3J0czogW0NvbW1vbk1vZHVsZV0sXG4gIGNoYW5nZURldGVjdGlvbjogQ2hhbmdlRGV0ZWN0aW9uU3RyYXRlZ3kuT25QdXNoLFxuICB0ZW1wbGF0ZTogYFxuICAgIDxkaXYgW2NsYXNzXT1cImNvbXB1dGVkQ2xhc3NcIj5cbiAgICAgIDxkaXYgY2xhc3M9XCJmbGV4IGl0ZW1zLWJhc2VsaW5lIGp1c3RpZnktYmV0d2VlbiBnYXAtMlwiPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRleHQtc20gZm9udC1tZWRpdW0gdGV4dC1wb3BvdmVyLWZvcmVncm91bmRcIj5Db250ZXh0PC9zcGFuPlxuICAgICAgICA8c3BhbiBjbGFzcz1cInRleHQteHMgdGFidWxhci1udW1zIHRleHQtbXV0ZWQtZm9yZWdyb3VuZFwiPnt7IHRva2Vucyh1c2FnZS51c2VkKSB9fSAvIHt7IHRva2Vucyh1c2FnZS50b3RhbCkgfX08L3NwYW4+XG4gICAgICA8L2Rpdj5cbiAgICAgIDxkbCBjbGFzcz1cIm10LTIgZmxleCBmbGV4LWNvbCBnYXAtMSB0ZXh0LXhzXCI+XG4gICAgICAgIDxkaXYgKm5nSWY9XCJ1c2FnZS5pbnB1dFRva2VucyAhPT0gbnVsbFwiIGNsYXNzPVwiZmxleCBpdGVtcy1jZW50ZXIganVzdGlmeS1iZXR3ZWVuIGdhcC0yXCI+XG4gICAgICAgICAgPGR0IGNsYXNzPVwidGV4dC1tdXRlZC1mb3JlZ3JvdW5kXCI+SW5wdXQ8L2R0PlxuICAgICAgICAgIDxkZCBjbGFzcz1cInRhYnVsYXItbnVtcyB0ZXh0LXBvcG92ZXItZm9yZWdyb3VuZFwiPnt7IHRva2Vucyh1c2FnZS5pbnB1dFRva2VucykgfX08L2RkPlxuICAgICAgICA8L2Rpdj5cbiAgICAgICAgPGRpdiAqbmdJZj1cInVzYWdlLm91dHB1dFRva2VucyAhPT0gbnVsbFwiIGNsYXNzPVwiZmxleCBpdGVtcy1jZW50ZXIganVzdGlmeS1iZXR3ZWVuIGdhcC0yXCI+XG4gICAgICAgICAgPGR0IGNsYXNzPVwidGV4dC1tdXRlZC1mb3JlZ3JvdW5kXCI+T3V0cHV0PC9kdD5cbiAgICAgICAgICA8ZGQgY2xhc3M9XCJ0YWJ1bGFyLW51bXMgdGV4dC1wb3BvdmVyLWZvcmVncm91bmRcIj57eyB0b2tlbnModXNhZ2Uub3V0cHV0VG9rZW5zKSB9fTwvZGQ+XG4gICAgICAgIDwvZGl2PlxuICAgICAgICA8ZGl2ICpuZ0lmPVwidXNhZ2UuY29zdCAhPT0gbnVsbFwiIGNsYXNzPVwiZmxleCBpdGVtcy1jZW50ZXIganVzdGlmeS1iZXR3ZWVuIGdhcC0yXCI+XG4gICAgICAgICAgPGR0IGNsYXNzPVwidGV4dC1tdXRlZC1mb3JlZ3JvdW5kXCI+Q29zdDwvZHQ+XG4gICAgICAgICAgPGRkIGNsYXNzPVwidGFidWxhci1udW1zIHRleHQtcG9wb3Zlci1mb3JlZ3JvdW5kXCI+e3sgY3VycmVuY3kgfX17eyB1c2FnZS5jb3N0IH19PC9kZD5cbiAgICAgICAgPC9kaXY+XG4gICAgICA8L2RsPlxuICAgICAgPG5nLWNvbnRlbnQ+PC9uZy1jb250ZW50PlxuICAgIDwvZGl2PlxuICBgLFxufSlcbmV4cG9ydCBjbGFzcyBDb250ZXh0Q29udGVudENvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgT25Jbml0LCBPbkRlc3Ryb3kge1xuXG4gIC8qKlxuICAgKiBBbmd1bGFyIHdyaXRlcyBhIGJvdW5kIGBjbGFzc2AgaW5wdXQgdGhyb3VnaCBpdHMgc3R5bGluZyBwYXRoLCB3aGljaCBkb2VzXG4gICAqIG5vdCBtYXJrIGFuIE9uUHVzaCBjb21wb25lbnQgZGlydHkg4oCUIHdpdGhvdXQgdGhpcyBob29rIHRoZSBjb21wb25lbnQga2VlcHNcbiAgICogcmVuZGVyaW5nIHRoZSBjbGFzcyBpdCB3YXMgYm9ybiB3aXRoLlxuICAgKi9cbiAgbmdPbkNoYW5nZXMoKTogdm9pZCB7XG4gICAgdGhpcy5jZHIubWFya0ZvckNoZWNrKCk7XG4gIH1cblxuICAvKiogU3ltYm9sIHByZWZpeGVkIHRvIHRoZSBjb3N0IGZpZ3VyZS4gQGRlZmF1bHQgJyQnICovXG4gIEBJbnB1dCgpIGN1cnJlbmN5ID0gJyQnO1xuICAvKiogRXh0cmEgVGFpbHdpbmQgY2xhc3NlcyBtZXJnZWQgb250byB0aGUgYnJlYWtkb3duIHZpYSBgY24oKWAgKGxhc3Qtd2lucykuICovXG4gIEBJbnB1dCgpIGNsYXNzID0gJyc7XG5cbiAgcHJpdmF0ZSByZWFkb25seSBzZXJ2aWNlID0gaW5qZWN0KENvbnRleHRTZXJ2aWNlKTtcbiAgcHJpdmF0ZSByZWFkb25seSBjZHIgPSBpbmplY3QoQ2hhbmdlRGV0ZWN0b3JSZWYpO1xuICBwcml2YXRlIHJlYWRvbmx5IHN1YiA9IG5ldyBTdWJzY3JpcHRpb24oKTtcblxuICB1c2FnZTogQ29udGV4dFVzYWdlID0gdGhpcy5zZXJ2aWNlLnVzYWdlO1xuICBwcm90ZWN0ZWQgdG9rZW5zID0gZm9ybWF0VG9rZW5zO1xuXG4gIG5nT25Jbml0KCk6IHZvaWQge1xuICAgIHRoaXMuc3ViLmFkZChcbiAgICAgIHRoaXMuc2VydmljZS51c2FnZSQuc3Vic2NyaWJlKCh1c2FnZSkgPT4ge1xuICAgICAgICB0aGlzLnVzYWdlID0gdXNhZ2U7XG4gICAgICAgIHRoaXMuY2RyLm1hcmtGb3JDaGVjaygpO1xuICAgICAgfSlcbiAgICApO1xuICB9XG5cbiAgbmdPbkRlc3Ryb3koKTogdm9pZCB7XG4gICAgdGhpcy5zdWIudW5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIGdldCBjb21wdXRlZENsYXNzKCkge1xuICAgIHJldHVybiBjbignZmxleCBmbGV4LWNvbCBwLTMnLCB0aGlzLmNsYXNzKTtcbiAgfVxufVxuIl19
|