textlane 0.0.0 → 0.1.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/LICENSE.md +9 -0
- package/README.md +80 -2
- package/build/actions/addon/resolve.d.ts +7 -0
- package/build/actions/addon/resolve.js +22 -0
- package/build/actions/attacher/check.d.ts +3 -0
- package/build/actions/attacher/check.js +5 -0
- package/build/actions/host/call.d.ts +13 -0
- package/build/actions/host/call.js +47 -0
- package/build/actions/options/merge.d.ts +5 -0
- package/build/actions/options/merge.js +29 -0
- package/build/actions/pluggable/map.d.ts +8 -0
- package/build/actions/pluggable/map.js +29 -0
- package/build/actions/run/finish.d.ts +12 -0
- package/build/actions/run/finish.js +52 -0
- package/build/actions/transformer/check.d.ts +3 -0
- package/build/actions/transformer/check.js +5 -0
- package/build/generated/html.d.ts +250 -0
- package/build/generated/html.js +74 -0
- package/build/generated/md.d.ts +333 -0
- package/build/generated/md.js +94 -0
- package/build/generated/mdx.d.ts +28 -0
- package/build/generated/mdx.js +8 -0
- package/build/generated/nl.d.ts +99 -0
- package/build/generated/nl.js +62 -0
- package/build/index.d.ts +18 -0
- package/build/index.js +27 -0
- package/build/models/addon.d.ts +35 -0
- package/build/models/addon.js +2 -0
- package/build/models/file.d.ts +52 -0
- package/build/models/file.js +2 -0
- package/build/models/host.d.ts +7 -0
- package/build/models/host.js +2 -0
- package/build/models/plugin.d.ts +26 -0
- package/build/models/plugin.js +2 -0
- package/build/models/processor.d.ts +39 -0
- package/build/models/processor.js +154 -0
- package/build/models/vfile.d.ts +52 -0
- package/build/models/vfile.js +164 -0
- package/build/settings.d.ts +14 -0
- package/build/settings.js +17 -0
- package/package.json +36 -3
- package/skills/textlane-usage/SKILL.md +146 -0
|
@@ -0,0 +1,250 @@
|
|
|
1
|
+
import type { Plugin } from "../models/plugin.ts";
|
|
2
|
+
/** `html.parse`: HTML into hast; options named as rehype-parse names them. */
|
|
3
|
+
export interface ParseOptions {
|
|
4
|
+
/** Parse a fragment, as in a `template`, rather than a whole document. @default false */
|
|
5
|
+
fragment?: boolean;
|
|
6
|
+
/** Report parse errors as messages on the file. @default false */
|
|
7
|
+
emitParseErrors?: boolean;
|
|
8
|
+
/** Add the positions of opening and closing tags and attributes to elements. @default false */
|
|
9
|
+
verbose?: boolean;
|
|
10
|
+
}
|
|
11
|
+
/** `html.raw`: reparse raw HTML and fix nesting through the HTML parser; options named as hast-util-raw names them. */
|
|
12
|
+
export interface RawOptions {
|
|
13
|
+
/** Node types, unknown to hast, to copy through as they are; their children are reparsed on their own. @default [] */
|
|
14
|
+
passThrough?: string[];
|
|
15
|
+
/** Escape the opening `<` of the tags GFM's tagfilter disallows in raw nodes. @default false */
|
|
16
|
+
tagfilter?: boolean;
|
|
17
|
+
}
|
|
18
|
+
/** `html.format`: indent and collapse whitespace for readable HTML; options named as hast-util-format names them. */
|
|
19
|
+
export interface FormatOptions {
|
|
20
|
+
/** Tag names of elements to put a blank line between, when both are one. @default [] */
|
|
21
|
+
blanks?: string[];
|
|
22
|
+
/** One level of indentation: a number of spaces or the text itself; two spaces when left out. */
|
|
23
|
+
indent?: Indent | null;
|
|
24
|
+
/** Indent the first level, usually `<html>`'s `head` and `body`; `true` when left out. */
|
|
25
|
+
indentInitial?: boolean | null;
|
|
26
|
+
}
|
|
27
|
+
/** One level of indentation. */
|
|
28
|
+
export type Indent = number | string;
|
|
29
|
+
/** `html.sanitize`: keep only what a schema allows; options: hast-util-sanitize's schema, where a field left out keeps the default schema's, which is GitHub's. */
|
|
30
|
+
export interface SanitizeOptions {
|
|
31
|
+
/** Keep comments. */
|
|
32
|
+
allowComments?: boolean | null;
|
|
33
|
+
/** Keep doctypes. */
|
|
34
|
+
allowDoctypes?: boolean | null;
|
|
35
|
+
/** Elements allowed only inside one of these ancestors, by tag name. */
|
|
36
|
+
ancestors?: Record<string, string[]> | null;
|
|
37
|
+
/** Properties allowed per tag name, `*` for every element; a list names a property and the values it may have. */
|
|
38
|
+
attributes?: Record<string, AttributeDefinition[]> | null;
|
|
39
|
+
/** Properties whose values get `clobber_prefix`, so they cannot clobber globals. */
|
|
40
|
+
clobber?: string[] | null;
|
|
41
|
+
/** The prefix of clobbered values. */
|
|
42
|
+
clobberPrefix?: string | null;
|
|
43
|
+
/** URL properties and the protocols they may use. */
|
|
44
|
+
protocols?: Record<string, string[]> | null;
|
|
45
|
+
/** Properties set on elements whatever they had, by tag name. */
|
|
46
|
+
required?: Record<string, Record<string, Primitive>> | null;
|
|
47
|
+
/** Elements dropped with their content rather than unwrapped. */
|
|
48
|
+
strip?: string[] | null;
|
|
49
|
+
/** The elements kept. */
|
|
50
|
+
tagNames?: string[] | null;
|
|
51
|
+
}
|
|
52
|
+
/** A property a sanitize schema allows: by name, or a name and its allowed values. */
|
|
53
|
+
export type AttributeDefinition = string | Primitive[];
|
|
54
|
+
/** A primitive property value. */
|
|
55
|
+
export type Primitive = boolean | number | string;
|
|
56
|
+
/** `html.slug`: ids on headings, from their text; options named as rehype-slug names them. */
|
|
57
|
+
export interface SlugOptions {
|
|
58
|
+
/** Put before each id. @default "" */
|
|
59
|
+
prefix?: string;
|
|
60
|
+
}
|
|
61
|
+
/** `html.externalLinks`: `rel`, `target` and more on links to other sites, as rehype-external-links adds them; options named as it names them, JSON values only. */
|
|
62
|
+
export interface ExternalLinksOptions {
|
|
63
|
+
/** The `target` of each external link, such as `_blank`. */
|
|
64
|
+
target?: string | null;
|
|
65
|
+
/** The `rel` of each external link: a list, or tokens separated by white space; `nofollow` when left out or empty, none for an empty list. */
|
|
66
|
+
rel?: Tokens | null;
|
|
67
|
+
/** The protocols of absolute URLs that count as external; `http` and `https` when left out. A protocol-relative `//…` URL always counts. */
|
|
68
|
+
protocols?: string[] | null;
|
|
69
|
+
/** More properties for each external link, as hast names them. */
|
|
70
|
+
properties?: Record<string, unknown> | null;
|
|
71
|
+
/** hast content appended to each external link in a `<span>`: one node or a list. */
|
|
72
|
+
content?: unknown;
|
|
73
|
+
/** The properties of that `<span>`. */
|
|
74
|
+
contentProperties?: Record<string, unknown> | null;
|
|
75
|
+
}
|
|
76
|
+
/** Tokens: a list, or one string of them separated by white space. */
|
|
77
|
+
export type Tokens = string | string[];
|
|
78
|
+
/** `html.highlight`: code blocks colored as Shiki colors them, natively by giallo; options named as @shikijs/rehype names them. */
|
|
79
|
+
export interface HighlightOptions {
|
|
80
|
+
/** The theme of each color mode, `light` first, as `{"light": …, "dark": …}`. */
|
|
81
|
+
themes?: Record<string, unknown> | null;
|
|
82
|
+
/** The one theme, when `themes` is not given. */
|
|
83
|
+
theme?: string | null;
|
|
84
|
+
/** The language of a block that names none; such a block is left alone without it. */
|
|
85
|
+
defaultLanguage?: string | null;
|
|
86
|
+
/** The language of a block naming one Shiki does not know; left alone without it. */
|
|
87
|
+
fallbackLanguage?: string | null;
|
|
88
|
+
/** Colors to replace, by their lowercase spelling: a color for every theme, or a theme's name to a map of its own. */
|
|
89
|
+
colorReplacements?: Record<string, ColorReplacement>;
|
|
90
|
+
/** Add `language-<name>` to each highlighted `<code>`. @default false */
|
|
91
|
+
addLanguageClass?: boolean;
|
|
92
|
+
/** Highlight inline code too, by how it names its language: `tailing-curly-colon` reads `` `a(){:js}` ``. */
|
|
93
|
+
inline?: InlineCode | null;
|
|
94
|
+
/** The `<pre>` property that gets a block's meta, the text after its language; the JSON stand-in for `parseMetaString: meta => ({ [name]: meta })`. */
|
|
95
|
+
metaProperty?: string | null;
|
|
96
|
+
/** The transformers of @shikijs/transformers to run, in order, by name or with options. */
|
|
97
|
+
transformers?: HighlightTransformer[];
|
|
98
|
+
}
|
|
99
|
+
/** A replacement color, or a theme's own replacements. */
|
|
100
|
+
export type ColorReplacement = string | Record<string, string>;
|
|
101
|
+
/** How inline code names its language. */
|
|
102
|
+
export type InlineCode = "tailing-curly-colon";
|
|
103
|
+
/** A transformer of @shikijs/transformers: its name alone, or its name and options. */
|
|
104
|
+
export type HighlightTransformer = TransformerName | ConfiguredTransformer;
|
|
105
|
+
/** The transformers `html.highlight` runs natively. */
|
|
106
|
+
export type TransformerName = "notationDiff" | "notationFocus" | "notationHighlight" | "notationErrorLevel" | "metaHighlight" | "renderLineNumber";
|
|
107
|
+
/** A transformer with its options, as @shikijs/transformers names them. */
|
|
108
|
+
export type ConfiguredTransformer = {
|
|
109
|
+
name: "notationDiff";
|
|
110
|
+
classLineAdd?: Classes | null;
|
|
111
|
+
classLineRemove?: Classes | null;
|
|
112
|
+
classActivePre?: Classes | null;
|
|
113
|
+
classActiveCode?: Classes | null;
|
|
114
|
+
} | {
|
|
115
|
+
name: "notationFocus";
|
|
116
|
+
classActiveLine?: Classes | null;
|
|
117
|
+
classActivePre?: Classes | null;
|
|
118
|
+
classActiveCode?: Classes | null;
|
|
119
|
+
} | {
|
|
120
|
+
name: "notationHighlight";
|
|
121
|
+
classActiveLine?: Classes | null;
|
|
122
|
+
classActivePre?: Classes | null;
|
|
123
|
+
classActiveCode?: Classes | null;
|
|
124
|
+
} | {
|
|
125
|
+
name: "notationErrorLevel";
|
|
126
|
+
classMap?: Record<string, Classes> | null;
|
|
127
|
+
classActivePre?: Classes | null;
|
|
128
|
+
classActiveCode?: Classes | null;
|
|
129
|
+
} | {
|
|
130
|
+
name: "metaHighlight";
|
|
131
|
+
className?: Classes | null;
|
|
132
|
+
zeroIndexed?: boolean;
|
|
133
|
+
} | {
|
|
134
|
+
name: "renderLineNumber";
|
|
135
|
+
classLineNumber?: Classes | null;
|
|
136
|
+
start?: number | null;
|
|
137
|
+
};
|
|
138
|
+
/** Class names: a list, or one string of them separated by white space. */
|
|
139
|
+
export type Classes = string | string[];
|
|
140
|
+
/** `html.katex`: math rendered as rehype-katex renders it, natively by katex-rs; options named as KaTeX names them. */
|
|
141
|
+
export interface KatexOptions {
|
|
142
|
+
/** The markup to write, both HTML and MathML by default. */
|
|
143
|
+
output?: KatexOutput | null;
|
|
144
|
+
/** Put equation numbers on the left. @default false */
|
|
145
|
+
leqno?: boolean;
|
|
146
|
+
/** Align display math to the left instead of centering it. @default false */
|
|
147
|
+
fleqn?: boolean;
|
|
148
|
+
/** The color of math that fails to render, `#cc0000` by default. */
|
|
149
|
+
errorColor?: string | null;
|
|
150
|
+
/** Macros by name, each to the TeX it expands to, as `{"\\RR": "\\mathbb{R}"}`. @default {} */
|
|
151
|
+
macros?: Record<string, string>;
|
|
152
|
+
/** The thinnest a rule, such as a fraction line, is drawn, in ems. */
|
|
153
|
+
minRuleThickness?: number | null;
|
|
154
|
+
/** Let `\color` color the text after it, as LaTeX does. @default false */
|
|
155
|
+
colorIsTextColor?: boolean;
|
|
156
|
+
/** What to do with input LaTeX would reject: `true` or `"error"` fails it, `"warn"` prints a warning, `false` or `"ignore"` (the default) accepts it. */
|
|
157
|
+
strict?: KatexStrict | null;
|
|
158
|
+
/** Allow commands that can run untrusted input, such as `\href` and `\includegraphics`. @default false */
|
|
159
|
+
trust?: boolean;
|
|
160
|
+
/** The largest a user-given size may be, in ems. */
|
|
161
|
+
maxSize?: number | null;
|
|
162
|
+
/** How many macro expansions one formula may take, 1000 by default. */
|
|
163
|
+
maxExpand?: number | null;
|
|
164
|
+
/** Let definitions such as `\def` last past the formula they are in. @default false */
|
|
165
|
+
globalGroup?: boolean;
|
|
166
|
+
}
|
|
167
|
+
/** The markup KaTeX writes. */
|
|
168
|
+
export type KatexOutput = "html" | "mathml" | "htmlAndMathml";
|
|
169
|
+
/** How strictly KaTeX holds input to LaTeX. */
|
|
170
|
+
export type KatexStrict = boolean | KatexStrictMode;
|
|
171
|
+
/** One level of KaTeX's strictness. */
|
|
172
|
+
export type KatexStrictMode = "ignore" | "warn" | "error";
|
|
173
|
+
/** `html.toMarkdown`: hast into mdast; options named as hast-util-to-mdast names them. */
|
|
174
|
+
export interface ToMarkdownOptions {
|
|
175
|
+
/** Wrap all phrasing content of the root in paragraphs, as for a whole document. @default false */
|
|
176
|
+
document?: boolean;
|
|
177
|
+
/** Collapse whitespace holding a line ending to that line ending instead of a space. @default false */
|
|
178
|
+
newlines?: boolean;
|
|
179
|
+
/** The text of a checked checkbox or radio, `[x]` by default. */
|
|
180
|
+
checked?: string | null;
|
|
181
|
+
/** The text of an unchecked checkbox or radio, `[ ]` by default. */
|
|
182
|
+
unchecked?: string | null;
|
|
183
|
+
/** The quotes `<q>` uses, an opening and closing character each, alternating by how deep it nests; `"` by default. */
|
|
184
|
+
quotes?: string[] | null;
|
|
185
|
+
}
|
|
186
|
+
/** `html.stringify`: hast into HTML; options named as hast-util-to-html names them. */
|
|
187
|
+
export interface StringifyOptions {
|
|
188
|
+
/** Write raw nodes as they are instead of escaping them. @default false */
|
|
189
|
+
allowDangerousHtml?: boolean;
|
|
190
|
+
/** Leave characters that are only dangerous in some contexts, such as `` ` ``, as they are. @default false */
|
|
191
|
+
allowDangerousCharacters?: boolean;
|
|
192
|
+
/** Leave characters as they are where browsers accept them though the spec does not. @default false */
|
|
193
|
+
allowParseErrors?: boolean;
|
|
194
|
+
/** Write comments as bogus comments, `<?a>`. @default false */
|
|
195
|
+
bogusComments?: boolean;
|
|
196
|
+
/** Close empty foreign elements, `<a />`. @default false */
|
|
197
|
+
closeEmptyElements?: boolean;
|
|
198
|
+
/** Close void elements, `<br />`. @default false */
|
|
199
|
+
closeSelfClosing?: boolean;
|
|
200
|
+
/** Write empty attributes as bare names, `a` rather than `a=""`. @default false */
|
|
201
|
+
collapseEmptyAttributes?: boolean;
|
|
202
|
+
/** Leave out tags the HTML spec lets a parser imply. @default false */
|
|
203
|
+
omitOptionalTags?: boolean;
|
|
204
|
+
/** Leave attribute values unquoted where that is safe. @default false */
|
|
205
|
+
preferUnquoted?: boolean;
|
|
206
|
+
/** The quote attribute values are wrapped in: `"` or `'`. */
|
|
207
|
+
quote?: string | null;
|
|
208
|
+
/** Use the other quote when the value holds more of the preferred one. @default false */
|
|
209
|
+
quoteSmart?: boolean;
|
|
210
|
+
/** The space the tree is in: `html` or `svg`. */
|
|
211
|
+
space?: string | null;
|
|
212
|
+
/** Leave out the space between quoted attributes. @default false */
|
|
213
|
+
tightAttributes?: boolean;
|
|
214
|
+
/** Join comma-separated values with `,` rather than `, `. @default false */
|
|
215
|
+
tightCommaSeparatedLists?: boolean;
|
|
216
|
+
/** Write `<!doctypehtml>`. @default false */
|
|
217
|
+
tightDoctype?: boolean;
|
|
218
|
+
/** Leave out the space before `/>` when the attributes allow. @default false */
|
|
219
|
+
tightSelfClosing?: boolean;
|
|
220
|
+
/** Write `<!DOCTYPE html>`. @default false */
|
|
221
|
+
upperDoctype?: boolean;
|
|
222
|
+
/** The tag names of void elements, which have no closing tag. */
|
|
223
|
+
voids?: string[] | null;
|
|
224
|
+
}
|
|
225
|
+
/** The `html.parse` plugin. */
|
|
226
|
+
export declare function parse(options?: ParseOptions): Plugin<"html.parse", ParseOptions>;
|
|
227
|
+
/** The `html.raw` plugin. */
|
|
228
|
+
export declare function raw(options?: RawOptions): Plugin<"html.raw", RawOptions>;
|
|
229
|
+
/** The `html.format` plugin. */
|
|
230
|
+
export declare function format(options?: FormatOptions): Plugin<"html.format", FormatOptions>;
|
|
231
|
+
/** The `html.sanitize` plugin. */
|
|
232
|
+
export declare function sanitize(options?: SanitizeOptions): Plugin<"html.sanitize", SanitizeOptions>;
|
|
233
|
+
/** The `html.slug` plugin. */
|
|
234
|
+
export declare function slug(options?: SlugOptions): Plugin<"html.slug", SlugOptions>;
|
|
235
|
+
/** The `html.externalLinks` plugin. */
|
|
236
|
+
export declare function externalLinks(options?: ExternalLinksOptions): Plugin<"html.externalLinks", ExternalLinksOptions>;
|
|
237
|
+
/** The `html.unwrapImages` plugin. */
|
|
238
|
+
export declare function unwrapImages(): Plugin<"html.unwrapImages">;
|
|
239
|
+
/** The `html.extractToc` plugin. */
|
|
240
|
+
export declare function extractToc(): Plugin<"html.extractToc">;
|
|
241
|
+
/** The `html.highlight` plugin. */
|
|
242
|
+
export declare function highlight(options?: HighlightOptions): Plugin<"html.highlight", HighlightOptions>;
|
|
243
|
+
/** The `html.katex` plugin. */
|
|
244
|
+
export declare function katex(options?: KatexOptions): Plugin<"html.katex", KatexOptions>;
|
|
245
|
+
/** The `html.toMarkdown` plugin. */
|
|
246
|
+
export declare function toMarkdown(options?: ToMarkdownOptions): Plugin<"html.toMarkdown", ToMarkdownOptions>;
|
|
247
|
+
/** The `html.toNaturalLanguage` plugin. */
|
|
248
|
+
export declare function toNaturalLanguage(): Plugin<"html.toNaturalLanguage">;
|
|
249
|
+
/** The `html.stringify` plugin. */
|
|
250
|
+
export declare function stringify(options?: StringifyOptions): Plugin<"html.stringify", StringifyOptions>;
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
// Generated by `pnpm generate:bindings` from the crate's plugins; do not edit.
|
|
2
|
+
/** The `html.parse` plugin. */
|
|
3
|
+
export function parse(options) {
|
|
4
|
+
if (options === undefined)
|
|
5
|
+
return { name: "html.parse" };
|
|
6
|
+
return { name: "html.parse", options };
|
|
7
|
+
}
|
|
8
|
+
/** The `html.raw` plugin. */
|
|
9
|
+
export function raw(options) {
|
|
10
|
+
if (options === undefined)
|
|
11
|
+
return { name: "html.raw" };
|
|
12
|
+
return { name: "html.raw", options };
|
|
13
|
+
}
|
|
14
|
+
/** The `html.format` plugin. */
|
|
15
|
+
export function format(options) {
|
|
16
|
+
if (options === undefined)
|
|
17
|
+
return { name: "html.format" };
|
|
18
|
+
return { name: "html.format", options };
|
|
19
|
+
}
|
|
20
|
+
/** The `html.sanitize` plugin. */
|
|
21
|
+
export function sanitize(options) {
|
|
22
|
+
if (options === undefined)
|
|
23
|
+
return { name: "html.sanitize" };
|
|
24
|
+
return { name: "html.sanitize", options };
|
|
25
|
+
}
|
|
26
|
+
/** The `html.slug` plugin. */
|
|
27
|
+
export function slug(options) {
|
|
28
|
+
if (options === undefined)
|
|
29
|
+
return { name: "html.slug" };
|
|
30
|
+
return { name: "html.slug", options };
|
|
31
|
+
}
|
|
32
|
+
/** The `html.externalLinks` plugin. */
|
|
33
|
+
export function externalLinks(options) {
|
|
34
|
+
if (options === undefined)
|
|
35
|
+
return { name: "html.externalLinks" };
|
|
36
|
+
return { name: "html.externalLinks", options };
|
|
37
|
+
}
|
|
38
|
+
/** The `html.unwrapImages` plugin. */
|
|
39
|
+
export function unwrapImages() {
|
|
40
|
+
return { name: "html.unwrapImages" };
|
|
41
|
+
}
|
|
42
|
+
/** The `html.extractToc` plugin. */
|
|
43
|
+
export function extractToc() {
|
|
44
|
+
return { name: "html.extractToc" };
|
|
45
|
+
}
|
|
46
|
+
/** The `html.highlight` plugin. */
|
|
47
|
+
export function highlight(options) {
|
|
48
|
+
if (options === undefined)
|
|
49
|
+
return { name: "html.highlight" };
|
|
50
|
+
return { name: "html.highlight", options };
|
|
51
|
+
}
|
|
52
|
+
/** The `html.katex` plugin. */
|
|
53
|
+
export function katex(options) {
|
|
54
|
+
if (options === undefined)
|
|
55
|
+
return { name: "html.katex" };
|
|
56
|
+
return { name: "html.katex", options };
|
|
57
|
+
}
|
|
58
|
+
/** The `html.toMarkdown` plugin. */
|
|
59
|
+
export function toMarkdown(options) {
|
|
60
|
+
if (options === undefined)
|
|
61
|
+
return { name: "html.toMarkdown" };
|
|
62
|
+
return { name: "html.toMarkdown", options };
|
|
63
|
+
}
|
|
64
|
+
/** The `html.toNaturalLanguage` plugin. */
|
|
65
|
+
export function toNaturalLanguage() {
|
|
66
|
+
return { name: "html.toNaturalLanguage" };
|
|
67
|
+
}
|
|
68
|
+
/** The `html.stringify` plugin. */
|
|
69
|
+
export function stringify(options) {
|
|
70
|
+
if (options === undefined)
|
|
71
|
+
return { name: "html.stringify" };
|
|
72
|
+
return { name: "html.stringify", options };
|
|
73
|
+
}
|
|
74
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaHRtbC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uL2dlbmVyYXRlZC9odG1sLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLCtFQUErRTtBQTZOL0UsK0JBQStCO0FBQy9CLE1BQU0sVUFBVSxLQUFLLENBQUMsT0FBc0I7SUFDMUMsSUFBSSxPQUFPLEtBQUssU0FBUztRQUFFLE9BQU8sRUFBRSxJQUFJLEVBQUUsWUFBWSxFQUFFLENBQUE7SUFDeEQsT0FBTyxFQUFFLElBQUksRUFBRSxZQUFZLEVBQUUsT0FBTyxFQUFFLENBQUE7QUFDeEMsQ0FBQztBQUVELDZCQUE2QjtBQUM3QixNQUFNLFVBQVUsR0FBRyxDQUFDLE9BQW9CO0lBQ3RDLElBQUksT0FBTyxLQUFLLFNBQVM7UUFBRSxPQUFPLEVBQUUsSUFBSSxFQUFFLFVBQVUsRUFBRSxDQUFBO0lBQ3RELE9BQU8sRUFBRSxJQUFJLEVBQUUsVUFBVSxFQUFFLE9BQU8sRUFBRSxDQUFBO0FBQ3RDLENBQUM7QUFFRCxnQ0FBZ0M7QUFDaEMsTUFBTSxVQUFVLE1BQU0sQ0FBQyxPQUF1QjtJQUM1QyxJQUFJLE9BQU8sS0FBSyxTQUFTO1FBQUUsT0FBTyxFQUFFLElBQUksRUFBRSxhQUFhLEVBQUUsQ0FBQTtJQUN6RCxPQUFPLEVBQUUsSUFBSSxFQUFFLGFBQWEsRUFBRSxPQUFPLEVBQUUsQ0FBQTtBQUN6QyxDQUFDO0FBRUQsa0NBQWtDO0FBQ2xDLE1BQU0sVUFBVSxRQUFRLENBQUMsT0FBeUI7SUFDaEQsSUFBSSxPQUFPLEtBQUssU0FBUztRQUFFLE9BQU8sRUFBRSxJQUFJLEVBQUUsZUFBZSxFQUFFLENBQUE7SUFDM0QsT0FBTyxFQUFFLElBQUksRUFBRSxlQUFlLEVBQUUsT0FBTyxFQUFFLENBQUE7QUFDM0MsQ0FBQztBQUVELDhCQUE4QjtBQUM5QixNQUFNLFVBQVUsSUFBSSxDQUFDLE9BQXFCO0lBQ3hDLElBQUksT0FBTyxLQUFLLFNBQVM7UUFBRSxPQUFPLEVBQUUsSUFBSSxFQUFFLFdBQVcsRUFBRSxDQUFBO0lBQ3ZELE9BQU8sRUFBRSxJQUFJLEVBQUUsV0FBVyxFQUFFLE9BQU8sRUFBRSxDQUFBO0FBQ3ZDLENBQUM7QUFFRCx1Q0FBdUM7QUFDdkMsTUFBTSxVQUFVLGFBQWEsQ0FBQyxPQUE4QjtJQUMxRCxJQUFJLE9BQU8sS0FBSyxTQUFTO1FBQUUsT0FBTyxFQUFFLElBQUksRUFBRSxvQkFBb0IsRUFBRSxDQUFBO0lBQ2hFLE9BQU8sRUFBRSxJQUFJLEVBQUUsb0JBQW9CLEVBQUUsT0FBTyxFQUFFLENBQUE7QUFDaEQsQ0FBQztBQUVELHNDQUFzQztBQUN0QyxNQUFNLFVBQVUsWUFBWTtJQUMxQixPQUFPLEVBQUUsSUFBSSxFQUFFLG1CQUFtQixFQUFFLENBQUE7QUFDdEMsQ0FBQztBQUVELG9DQUFvQztBQUNwQyxNQUFNLFVBQVUsVUFBVTtJQUN4QixPQUFPLEVBQUUsSUFBSSxFQUFFLGlCQUFpQixFQUFFLENBQUE7QUFDcEMsQ0FBQztBQUVELG1DQUFtQztBQUNuQyxNQUFNLFVBQVUsU0FBUyxDQUFDLE9BQTBCO0lBQ2xELElBQUksT0FBTyxLQUFLLFNBQVM7UUFBRSxPQUFPLEVBQUUsSUFBSSxFQUFFLGdCQUFnQixFQUFFLENBQUE7SUFDNUQsT0FBTyxFQUFFLElBQUksRUFBRSxnQkFBZ0IsRUFBRSxPQUFPLEVBQUUsQ0FBQTtBQUM1QyxDQUFDO0FBRUQsK0JBQStCO0FBQy9CLE1BQU0sVUFBVSxLQUFLLENBQUMsT0FBc0I7SUFDMUMsSUFBSSxPQUFPLEtBQUssU0FBUztRQUFFLE9BQU8sRUFBRSxJQUFJLEVBQUUsWUFBWSxFQUFFLENBQUE7SUFDeEQsT0FBTyxFQUFFLElBQUksRUFBRSxZQUFZLEVBQUUsT0FBTyxFQUFFLENBQUE7QUFDeEMsQ0FBQztBQUVELG9DQUFvQztBQUNwQyxNQUFNLFVBQVUsVUFBVSxDQUFDLE9BQTJCO0lBQ3BELElBQUksT0FBTyxLQUFLLFNBQVM7UUFBRSxPQUFPLEVBQUUsSUFBSSxFQUFFLGlCQUFpQixFQUFFLENBQUE7SUFDN0QsT0FBTyxFQUFFLElBQUksRUFBRSxpQkFBaUIsRUFBRSxPQUFPLEVBQUUsQ0FBQTtBQUM3QyxDQUFDO0FBRUQsMkNBQTJDO0FBQzNDLE1BQU0sVUFBVSxpQkFBaUI7SUFDL0IsT0FBTyxFQUFFLElBQUksRUFBRSx3QkFBd0IsRUFBRSxDQUFBO0FBQzNDLENBQUM7QUFFRCxtQ0FBbUM7QUFDbkMsTUFBTSxVQUFVLFNBQVMsQ0FBQyxPQUEwQjtJQUNsRCxJQUFJLE9BQU8sS0FBSyxTQUFTO1FBQUUsT0FBTyxFQUFFLElBQUksRUFBRSxnQkFBZ0IsRUFBRSxDQUFBO0lBQzVELE9BQU8sRUFBRSxJQUFJLEVBQUUsZ0JBQWdCLEVBQUUsT0FBTyxFQUFFLENBQUE7QUFDNUMsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8vIEdlbmVyYXRlZCBieSBgcG5wbSBnZW5lcmF0ZTpiaW5kaW5nc2AgZnJvbSB0aGUgY3JhdGUncyBwbHVnaW5zOyBkbyBub3QgZWRpdC5cblxuaW1wb3J0IHR5cGUgeyBQbHVnaW4gfSBmcm9tIFwiLi4vbW9kZWxzL3BsdWdpbi50c1wiXG5cbi8qKiBgaHRtbC5wYXJzZWA6IEhUTUwgaW50byBoYXN0OyBvcHRpb25zIG5hbWVkIGFzIHJlaHlwZS1wYXJzZSBuYW1lcyB0aGVtLiAqL1xuZXhwb3J0IGludGVyZmFjZSBQYXJzZU9wdGlvbnMge1xuICAvKiogUGFyc2UgYSBmcmFnbWVudCwgYXMgaW4gYSBgdGVtcGxhdGVgLCByYXRoZXIgdGhhbiBhIHdob2xlIGRvY3VtZW50LiBAZGVmYXVsdCBmYWxzZSAqL1xuICBmcmFnbWVudD86IGJvb2xlYW5cbiAgLyoqIFJlcG9ydCBwYXJzZSBlcnJvcnMgYXMgbWVzc2FnZXMgb24gdGhlIGZpbGUuIEBkZWZhdWx0IGZhbHNlICovXG4gIGVtaXRQYXJzZUVycm9ycz86IGJvb2xlYW5cbiAgLyoqIEFkZCB0aGUgcG9zaXRpb25zIG9mIG9wZW5pbmcgYW5kIGNsb3NpbmcgdGFncyBhbmQgYXR0cmlidXRlcyB0byBlbGVtZW50cy4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgdmVyYm9zZT86IGJvb2xlYW5cbn1cblxuLyoqIGBodG1sLnJhd2A6IHJlcGFyc2UgcmF3IEhUTUwgYW5kIGZpeCBuZXN0aW5nIHRocm91Z2ggdGhlIEhUTUwgcGFyc2VyOyBvcHRpb25zIG5hbWVkIGFzIGhhc3QtdXRpbC1yYXcgbmFtZXMgdGhlbS4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUmF3T3B0aW9ucyB7XG4gIC8qKiBOb2RlIHR5cGVzLCB1bmtub3duIHRvIGhhc3QsIHRvIGNvcHkgdGhyb3VnaCBhcyB0aGV5IGFyZTsgdGhlaXIgY2hpbGRyZW4gYXJlIHJlcGFyc2VkIG9uIHRoZWlyIG93bi4gQGRlZmF1bHQgW10gKi9cbiAgcGFzc1Rocm91Z2g/OiBzdHJpbmdbXVxuICAvKiogRXNjYXBlIHRoZSBvcGVuaW5nIGA8YCBvZiB0aGUgdGFncyBHRk0ncyB0YWdmaWx0ZXIgZGlzYWxsb3dzIGluIHJhdyBub2Rlcy4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgdGFnZmlsdGVyPzogYm9vbGVhblxufVxuXG4vKiogYGh0bWwuZm9ybWF0YDogaW5kZW50IGFuZCBjb2xsYXBzZSB3aGl0ZXNwYWNlIGZvciByZWFkYWJsZSBIVE1MOyBvcHRpb25zIG5hbWVkIGFzIGhhc3QtdXRpbC1mb3JtYXQgbmFtZXMgdGhlbS4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgRm9ybWF0T3B0aW9ucyB7XG4gIC8qKiBUYWcgbmFtZXMgb2YgZWxlbWVudHMgdG8gcHV0IGEgYmxhbmsgbGluZSBiZXR3ZWVuLCB3aGVuIGJvdGggYXJlIG9uZS4gQGRlZmF1bHQgW10gKi9cbiAgYmxhbmtzPzogc3RyaW5nW11cbiAgLyoqIE9uZSBsZXZlbCBvZiBpbmRlbnRhdGlvbjogYSBudW1iZXIgb2Ygc3BhY2VzIG9yIHRoZSB0ZXh0IGl0c2VsZjsgdHdvIHNwYWNlcyB3aGVuIGxlZnQgb3V0LiAqL1xuICBpbmRlbnQ/OiBJbmRlbnQgfCBudWxsXG4gIC8qKiBJbmRlbnQgdGhlIGZpcnN0IGxldmVsLCB1c3VhbGx5IGA8aHRtbD5gJ3MgYGhlYWRgIGFuZCBgYm9keWA7IGB0cnVlYCB3aGVuIGxlZnQgb3V0LiAqL1xuICBpbmRlbnRJbml0aWFsPzogYm9vbGVhbiB8IG51bGxcbn1cblxuLyoqIE9uZSBsZXZlbCBvZiBpbmRlbnRhdGlvbi4gKi9cbmV4cG9ydCB0eXBlIEluZGVudCA9IG51bWJlciB8IHN0cmluZ1xuXG4vKiogYGh0bWwuc2FuaXRpemVgOiBrZWVwIG9ubHkgd2hhdCBhIHNjaGVtYSBhbGxvd3M7IG9wdGlvbnM6IGhhc3QtdXRpbC1zYW5pdGl6ZSdzIHNjaGVtYSwgd2hlcmUgYSBmaWVsZCBsZWZ0IG91dCBrZWVwcyB0aGUgZGVmYXVsdCBzY2hlbWEncywgd2hpY2ggaXMgR2l0SHViJ3MuICovXG5leHBvcnQgaW50ZXJmYWNlIFNhbml0aXplT3B0aW9ucyB7XG4gIC8qKiBLZWVwIGNvbW1lbnRzLiAqL1xuICBhbGxvd0NvbW1lbnRzPzogYm9vbGVhbiB8IG51bGxcbiAgLyoqIEtlZXAgZG9jdHlwZXMuICovXG4gIGFsbG93RG9jdHlwZXM/OiBib29sZWFuIHwgbnVsbFxuICAvKiogRWxlbWVudHMgYWxsb3dlZCBvbmx5IGluc2lkZSBvbmUgb2YgdGhlc2UgYW5jZXN0b3JzLCBieSB0YWcgbmFtZS4gKi9cbiAgYW5jZXN0b3JzPzogUmVjb3JkPHN0cmluZywgc3RyaW5nW10+IHwgbnVsbFxuICAvKiogUHJvcGVydGllcyBhbGxvd2VkIHBlciB0YWcgbmFtZSwgYCpgIGZvciBldmVyeSBlbGVtZW50OyBhIGxpc3QgbmFtZXMgYSBwcm9wZXJ0eSBhbmQgdGhlIHZhbHVlcyBpdCBtYXkgaGF2ZS4gKi9cbiAgYXR0cmlidXRlcz86IFJlY29yZDxzdHJpbmcsIEF0dHJpYnV0ZURlZmluaXRpb25bXT4gfCBudWxsXG4gIC8qKiBQcm9wZXJ0aWVzIHdob3NlIHZhbHVlcyBnZXQgYGNsb2JiZXJfcHJlZml4YCwgc28gdGhleSBjYW5ub3QgY2xvYmJlciBnbG9iYWxzLiAqL1xuICBjbG9iYmVyPzogc3RyaW5nW10gfCBudWxsXG4gIC8qKiBUaGUgcHJlZml4IG9mIGNsb2JiZXJlZCB2YWx1ZXMuICovXG4gIGNsb2JiZXJQcmVmaXg/OiBzdHJpbmcgfCBudWxsXG4gIC8qKiBVUkwgcHJvcGVydGllcyBhbmQgdGhlIHByb3RvY29scyB0aGV5IG1heSB1c2UuICovXG4gIHByb3RvY29scz86IFJlY29yZDxzdHJpbmcsIHN0cmluZ1tdPiB8IG51bGxcbiAgLyoqIFByb3BlcnRpZXMgc2V0IG9uIGVsZW1lbnRzIHdoYXRldmVyIHRoZXkgaGFkLCBieSB0YWcgbmFtZS4gKi9cbiAgcmVxdWlyZWQ/OiBSZWNvcmQ8c3RyaW5nLCBSZWNvcmQ8c3RyaW5nLCBQcmltaXRpdmU+PiB8IG51bGxcbiAgLyoqIEVsZW1lbnRzIGRyb3BwZWQgd2l0aCB0aGVpciBjb250ZW50IHJhdGhlciB0aGFuIHVud3JhcHBlZC4gKi9cbiAgc3RyaXA/OiBzdHJpbmdbXSB8IG51bGxcbiAgLyoqIFRoZSBlbGVtZW50cyBrZXB0LiAqL1xuICB0YWdOYW1lcz86IHN0cmluZ1tdIHwgbnVsbFxufVxuXG4vKiogQSBwcm9wZXJ0eSBhIHNhbml0aXplIHNjaGVtYSBhbGxvd3M6IGJ5IG5hbWUsIG9yIGEgbmFtZSBhbmQgaXRzIGFsbG93ZWQgdmFsdWVzLiAqL1xuZXhwb3J0IHR5cGUgQXR0cmlidXRlRGVmaW5pdGlvbiA9IHN0cmluZyB8IFByaW1pdGl2ZVtdXG5cbi8qKiBBIHByaW1pdGl2ZSBwcm9wZXJ0eSB2YWx1ZS4gKi9cbmV4cG9ydCB0eXBlIFByaW1pdGl2ZSA9IGJvb2xlYW4gfCBudW1iZXIgfCBzdHJpbmdcblxuLyoqIGBodG1sLnNsdWdgOiBpZHMgb24gaGVhZGluZ3MsIGZyb20gdGhlaXIgdGV4dDsgb3B0aW9ucyBuYW1lZCBhcyByZWh5cGUtc2x1ZyBuYW1lcyB0aGVtLiAqL1xuZXhwb3J0IGludGVyZmFjZSBTbHVnT3B0aW9ucyB7XG4gIC8qKiBQdXQgYmVmb3JlIGVhY2ggaWQuIEBkZWZhdWx0IFwiXCIgKi9cbiAgcHJlZml4Pzogc3RyaW5nXG59XG5cbi8qKiBgaHRtbC5leHRlcm5hbExpbmtzYDogYHJlbGAsIGB0YXJnZXRgIGFuZCBtb3JlIG9uIGxpbmtzIHRvIG90aGVyIHNpdGVzLCBhcyByZWh5cGUtZXh0ZXJuYWwtbGlua3MgYWRkcyB0aGVtOyBvcHRpb25zIG5hbWVkIGFzIGl0IG5hbWVzIHRoZW0sIEpTT04gdmFsdWVzIG9ubHkuICovXG5leHBvcnQgaW50ZXJmYWNlIEV4dGVybmFsTGlua3NPcHRpb25zIHtcbiAgLyoqIFRoZSBgdGFyZ2V0YCBvZiBlYWNoIGV4dGVybmFsIGxpbmssIHN1Y2ggYXMgYF9ibGFua2AuICovXG4gIHRhcmdldD86IHN0cmluZyB8IG51bGxcbiAgLyoqIFRoZSBgcmVsYCBvZiBlYWNoIGV4dGVybmFsIGxpbms6IGEgbGlzdCwgb3IgdG9rZW5zIHNlcGFyYXRlZCBieSB3aGl0ZSBzcGFjZTsgYG5vZm9sbG93YCB3aGVuIGxlZnQgb3V0IG9yIGVtcHR5LCBub25lIGZvciBhbiBlbXB0eSBsaXN0LiAqL1xuICByZWw/OiBUb2tlbnMgfCBudWxsXG4gIC8qKiBUaGUgcHJvdG9jb2xzIG9mIGFic29sdXRlIFVSTHMgdGhhdCBjb3VudCBhcyBleHRlcm5hbDsgYGh0dHBgIGFuZCBgaHR0cHNgIHdoZW4gbGVmdCBvdXQuIEEgcHJvdG9jb2wtcmVsYXRpdmUgYC8v4oCmYCBVUkwgYWx3YXlzIGNvdW50cy4gKi9cbiAgcHJvdG9jb2xzPzogc3RyaW5nW10gfCBudWxsXG4gIC8qKiBNb3JlIHByb3BlcnRpZXMgZm9yIGVhY2ggZXh0ZXJuYWwgbGluaywgYXMgaGFzdCBuYW1lcyB0aGVtLiAqL1xuICBwcm9wZXJ0aWVzPzogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCBudWxsXG4gIC8qKiBoYXN0IGNvbnRlbnQgYXBwZW5kZWQgdG8gZWFjaCBleHRlcm5hbCBsaW5rIGluIGEgYDxzcGFuPmA6IG9uZSBub2RlIG9yIGEgbGlzdC4gKi9cbiAgY29udGVudD86IHVua25vd25cbiAgLyoqIFRoZSBwcm9wZXJ0aWVzIG9mIHRoYXQgYDxzcGFuPmAuICovXG4gIGNvbnRlbnRQcm9wZXJ0aWVzPzogUmVjb3JkPHN0cmluZywgdW5rbm93bj4gfCBudWxsXG59XG5cbi8qKiBUb2tlbnM6IGEgbGlzdCwgb3Igb25lIHN0cmluZyBvZiB0aGVtIHNlcGFyYXRlZCBieSB3aGl0ZSBzcGFjZS4gKi9cbmV4cG9ydCB0eXBlIFRva2VucyA9IHN0cmluZyB8IHN0cmluZ1tdXG5cbi8qKiBgaHRtbC5oaWdobGlnaHRgOiBjb2RlIGJsb2NrcyBjb2xvcmVkIGFzIFNoaWtpIGNvbG9ycyB0aGVtLCBuYXRpdmVseSBieSBnaWFsbG87IG9wdGlvbnMgbmFtZWQgYXMgQHNoaWtpanMvcmVoeXBlIG5hbWVzIHRoZW0uICovXG5leHBvcnQgaW50ZXJmYWNlIEhpZ2hsaWdodE9wdGlvbnMge1xuICAvKiogVGhlIHRoZW1lIG9mIGVhY2ggY29sb3IgbW9kZSwgYGxpZ2h0YCBmaXJzdCwgYXMgYHtcImxpZ2h0XCI6IOKApiwgXCJkYXJrXCI6IOKApn1gLiAqL1xuICB0aGVtZXM/OiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPiB8IG51bGxcbiAgLyoqIFRoZSBvbmUgdGhlbWUsIHdoZW4gYHRoZW1lc2AgaXMgbm90IGdpdmVuLiAqL1xuICB0aGVtZT86IHN0cmluZyB8IG51bGxcbiAgLyoqIFRoZSBsYW5ndWFnZSBvZiBhIGJsb2NrIHRoYXQgbmFtZXMgbm9uZTsgc3VjaCBhIGJsb2NrIGlzIGxlZnQgYWxvbmUgd2l0aG91dCBpdC4gKi9cbiAgZGVmYXVsdExhbmd1YWdlPzogc3RyaW5nIHwgbnVsbFxuICAvKiogVGhlIGxhbmd1YWdlIG9mIGEgYmxvY2sgbmFtaW5nIG9uZSBTaGlraSBkb2VzIG5vdCBrbm93OyBsZWZ0IGFsb25lIHdpdGhvdXQgaXQuICovXG4gIGZhbGxiYWNrTGFuZ3VhZ2U/OiBzdHJpbmcgfCBudWxsXG4gIC8qKiBDb2xvcnMgdG8gcmVwbGFjZSwgYnkgdGhlaXIgbG93ZXJjYXNlIHNwZWxsaW5nOiBhIGNvbG9yIGZvciBldmVyeSB0aGVtZSwgb3IgYSB0aGVtZSdzIG5hbWUgdG8gYSBtYXAgb2YgaXRzIG93bi4gKi9cbiAgY29sb3JSZXBsYWNlbWVudHM/OiBSZWNvcmQ8c3RyaW5nLCBDb2xvclJlcGxhY2VtZW50PlxuICAvKiogQWRkIGBsYW5ndWFnZS08bmFtZT5gIHRvIGVhY2ggaGlnaGxpZ2h0ZWQgYDxjb2RlPmAuIEBkZWZhdWx0IGZhbHNlICovXG4gIGFkZExhbmd1YWdlQ2xhc3M/OiBib29sZWFuXG4gIC8qKiBIaWdobGlnaHQgaW5saW5lIGNvZGUgdG9vLCBieSBob3cgaXQgbmFtZXMgaXRzIGxhbmd1YWdlOiBgdGFpbGluZy1jdXJseS1jb2xvbmAgcmVhZHMgYGAgYGEoKXs6anN9YCBgYC4gKi9cbiAgaW5saW5lPzogSW5saW5lQ29kZSB8IG51bGxcbiAgLyoqIFRoZSBgPHByZT5gIHByb3BlcnR5IHRoYXQgZ2V0cyBhIGJsb2NrJ3MgbWV0YSwgdGhlIHRleHQgYWZ0ZXIgaXRzIGxhbmd1YWdlOyB0aGUgSlNPTiBzdGFuZC1pbiBmb3IgYHBhcnNlTWV0YVN0cmluZzogbWV0YSA9PiAoeyBbbmFtZV06IG1ldGEgfSlgLiAqL1xuICBtZXRhUHJvcGVydHk/OiBzdHJpbmcgfCBudWxsXG4gIC8qKiBUaGUgdHJhbnNmb3JtZXJzIG9mIEBzaGlraWpzL3RyYW5zZm9ybWVycyB0byBydW4sIGluIG9yZGVyLCBieSBuYW1lIG9yIHdpdGggb3B0aW9ucy4gKi9cbiAgdHJhbnNmb3JtZXJzPzogSGlnaGxpZ2h0VHJhbnNmb3JtZXJbXVxufVxuXG4vKiogQSByZXBsYWNlbWVudCBjb2xvciwgb3IgYSB0aGVtZSdzIG93biByZXBsYWNlbWVudHMuICovXG5leHBvcnQgdHlwZSBDb2xvclJlcGxhY2VtZW50ID0gc3RyaW5nIHwgUmVjb3JkPHN0cmluZywgc3RyaW5nPlxuXG4vKiogSG93IGlubGluZSBjb2RlIG5hbWVzIGl0cyBsYW5ndWFnZS4gKi9cbmV4cG9ydCB0eXBlIElubGluZUNvZGUgPSBcInRhaWxpbmctY3VybHktY29sb25cIlxuXG4vKiogQSB0cmFuc2Zvcm1lciBvZiBAc2hpa2lqcy90cmFuc2Zvcm1lcnM6IGl0cyBuYW1lIGFsb25lLCBvciBpdHMgbmFtZSBhbmQgb3B0aW9ucy4gKi9cbmV4cG9ydCB0eXBlIEhpZ2hsaWdodFRyYW5zZm9ybWVyID0gVHJhbnNmb3JtZXJOYW1lIHwgQ29uZmlndXJlZFRyYW5zZm9ybWVyXG5cbi8qKiBUaGUgdHJhbnNmb3JtZXJzIGBodG1sLmhpZ2hsaWdodGAgcnVucyBuYXRpdmVseS4gKi9cbmV4cG9ydCB0eXBlIFRyYW5zZm9ybWVyTmFtZSA9IFwibm90YXRpb25EaWZmXCIgfCBcIm5vdGF0aW9uRm9jdXNcIiB8IFwibm90YXRpb25IaWdobGlnaHRcIiB8IFwibm90YXRpb25FcnJvckxldmVsXCIgfCBcIm1ldGFIaWdobGlnaHRcIiB8IFwicmVuZGVyTGluZU51bWJlclwiXG5cbi8qKiBBIHRyYW5zZm9ybWVyIHdpdGggaXRzIG9wdGlvbnMsIGFzIEBzaGlraWpzL3RyYW5zZm9ybWVycyBuYW1lcyB0aGVtLiAqL1xuZXhwb3J0IHR5cGUgQ29uZmlndXJlZFRyYW5zZm9ybWVyID0geyBuYW1lOiBcIm5vdGF0aW9uRGlmZlwiOyBjbGFzc0xpbmVBZGQ/OiBDbGFzc2VzIHwgbnVsbDsgY2xhc3NMaW5lUmVtb3ZlPzogQ2xhc3NlcyB8IG51bGw7IGNsYXNzQWN0aXZlUHJlPzogQ2xhc3NlcyB8IG51bGw7IGNsYXNzQWN0aXZlQ29kZT86IENsYXNzZXMgfCBudWxsIH0gfCB7IG5hbWU6IFwibm90YXRpb25Gb2N1c1wiOyBjbGFzc0FjdGl2ZUxpbmU/OiBDbGFzc2VzIHwgbnVsbDsgY2xhc3NBY3RpdmVQcmU/OiBDbGFzc2VzIHwgbnVsbDsgY2xhc3NBY3RpdmVDb2RlPzogQ2xhc3NlcyB8IG51bGwgfSB8IHsgbmFtZTogXCJub3RhdGlvbkhpZ2hsaWdodFwiOyBjbGFzc0FjdGl2ZUxpbmU/OiBDbGFzc2VzIHwgbnVsbDsgY2xhc3NBY3RpdmVQcmU/OiBDbGFzc2VzIHwgbnVsbDsgY2xhc3NBY3RpdmVDb2RlPzogQ2xhc3NlcyB8IG51bGwgfSB8IHsgbmFtZTogXCJub3RhdGlvbkVycm9yTGV2ZWxcIjsgY2xhc3NNYXA/OiBSZWNvcmQ8c3RyaW5nLCBDbGFzc2VzPiB8IG51bGw7IGNsYXNzQWN0aXZlUHJlPzogQ2xhc3NlcyB8IG51bGw7IGNsYXNzQWN0aXZlQ29kZT86IENsYXNzZXMgfCBudWxsIH0gfCB7IG5hbWU6IFwibWV0YUhpZ2hsaWdodFwiOyBjbGFzc05hbWU/OiBDbGFzc2VzIHwgbnVsbDsgemVyb0luZGV4ZWQ/OiBib29sZWFuIH0gfCB7IG5hbWU6IFwicmVuZGVyTGluZU51bWJlclwiOyBjbGFzc0xpbmVOdW1iZXI/OiBDbGFzc2VzIHwgbnVsbDsgc3RhcnQ/OiBudW1iZXIgfCBudWxsIH1cblxuLyoqIENsYXNzIG5hbWVzOiBhIGxpc3QsIG9yIG9uZSBzdHJpbmcgb2YgdGhlbSBzZXBhcmF0ZWQgYnkgd2hpdGUgc3BhY2UuICovXG5leHBvcnQgdHlwZSBDbGFzc2VzID0gc3RyaW5nIHwgc3RyaW5nW11cblxuLyoqIGBodG1sLmthdGV4YDogbWF0aCByZW5kZXJlZCBhcyByZWh5cGUta2F0ZXggcmVuZGVycyBpdCwgbmF0aXZlbHkgYnkga2F0ZXgtcnM7IG9wdGlvbnMgbmFtZWQgYXMgS2FUZVggbmFtZXMgdGhlbS4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgS2F0ZXhPcHRpb25zIHtcbiAgLyoqIFRoZSBtYXJrdXAgdG8gd3JpdGUsIGJvdGggSFRNTCBhbmQgTWF0aE1MIGJ5IGRlZmF1bHQuICovXG4gIG91dHB1dD86IEthdGV4T3V0cHV0IHwgbnVsbFxuICAvKiogUHV0IGVxdWF0aW9uIG51bWJlcnMgb24gdGhlIGxlZnQuIEBkZWZhdWx0IGZhbHNlICovXG4gIGxlcW5vPzogYm9vbGVhblxuICAvKiogQWxpZ24gZGlzcGxheSBtYXRoIHRvIHRoZSBsZWZ0IGluc3RlYWQgb2YgY2VudGVyaW5nIGl0LiBAZGVmYXVsdCBmYWxzZSAqL1xuICBmbGVxbj86IGJvb2xlYW5cbiAgLyoqIFRoZSBjb2xvciBvZiBtYXRoIHRoYXQgZmFpbHMgdG8gcmVuZGVyLCBgI2NjMDAwMGAgYnkgZGVmYXVsdC4gKi9cbiAgZXJyb3JDb2xvcj86IHN0cmluZyB8IG51bGxcbiAgLyoqIE1hY3JvcyBieSBuYW1lLCBlYWNoIHRvIHRoZSBUZVggaXQgZXhwYW5kcyB0bywgYXMgYHtcIlxcXFxSUlwiOiBcIlxcXFxtYXRoYmJ7Un1cIn1gLiBAZGVmYXVsdCB7fSAqL1xuICBtYWNyb3M/OiBSZWNvcmQ8c3RyaW5nLCBzdHJpbmc+XG4gIC8qKiBUaGUgdGhpbm5lc3QgYSBydWxlLCBzdWNoIGFzIGEgZnJhY3Rpb24gbGluZSwgaXMgZHJhd24sIGluIGVtcy4gKi9cbiAgbWluUnVsZVRoaWNrbmVzcz86IG51bWJlciB8IG51bGxcbiAgLyoqIExldCBgXFxjb2xvcmAgY29sb3IgdGhlIHRleHQgYWZ0ZXIgaXQsIGFzIExhVGVYIGRvZXMuIEBkZWZhdWx0IGZhbHNlICovXG4gIGNvbG9ySXNUZXh0Q29sb3I/OiBib29sZWFuXG4gIC8qKiBXaGF0IHRvIGRvIHdpdGggaW5wdXQgTGFUZVggd291bGQgcmVqZWN0OiBgdHJ1ZWAgb3IgYFwiZXJyb3JcImAgZmFpbHMgaXQsIGBcIndhcm5cImAgcHJpbnRzIGEgd2FybmluZywgYGZhbHNlYCBvciBgXCJpZ25vcmVcImAgKHRoZSBkZWZhdWx0KSBhY2NlcHRzIGl0LiAqL1xuICBzdHJpY3Q/OiBLYXRleFN0cmljdCB8IG51bGxcbiAgLyoqIEFsbG93IGNvbW1hbmRzIHRoYXQgY2FuIHJ1biB1bnRydXN0ZWQgaW5wdXQsIHN1Y2ggYXMgYFxcaHJlZmAgYW5kIGBcXGluY2x1ZGVncmFwaGljc2AuIEBkZWZhdWx0IGZhbHNlICovXG4gIHRydXN0PzogYm9vbGVhblxuICAvKiogVGhlIGxhcmdlc3QgYSB1c2VyLWdpdmVuIHNpemUgbWF5IGJlLCBpbiBlbXMuICovXG4gIG1heFNpemU/OiBudW1iZXIgfCBudWxsXG4gIC8qKiBIb3cgbWFueSBtYWNybyBleHBhbnNpb25zIG9uZSBmb3JtdWxhIG1heSB0YWtlLCAxMDAwIGJ5IGRlZmF1bHQuICovXG4gIG1heEV4cGFuZD86IG51bWJlciB8IG51bGxcbiAgLyoqIExldCBkZWZpbml0aW9ucyBzdWNoIGFzIGBcXGRlZmAgbGFzdCBwYXN0IHRoZSBmb3JtdWxhIHRoZXkgYXJlIGluLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBnbG9iYWxHcm91cD86IGJvb2xlYW5cbn1cblxuLyoqIFRoZSBtYXJrdXAgS2FUZVggd3JpdGVzLiAqL1xuZXhwb3J0IHR5cGUgS2F0ZXhPdXRwdXQgPSBcImh0bWxcIiB8IFwibWF0aG1sXCIgfCBcImh0bWxBbmRNYXRobWxcIlxuXG4vKiogSG93IHN0cmljdGx5IEthVGVYIGhvbGRzIGlucHV0IHRvIExhVGVYLiAqL1xuZXhwb3J0IHR5cGUgS2F0ZXhTdHJpY3QgPSBib29sZWFuIHwgS2F0ZXhTdHJpY3RNb2RlXG5cbi8qKiBPbmUgbGV2ZWwgb2YgS2FUZVgncyBzdHJpY3RuZXNzLiAqL1xuZXhwb3J0IHR5cGUgS2F0ZXhTdHJpY3RNb2RlID0gXCJpZ25vcmVcIiB8IFwid2FyblwiIHwgXCJlcnJvclwiXG5cbi8qKiBgaHRtbC50b01hcmtkb3duYDogaGFzdCBpbnRvIG1kYXN0OyBvcHRpb25zIG5hbWVkIGFzIGhhc3QtdXRpbC10by1tZGFzdCBuYW1lcyB0aGVtLiAqL1xuZXhwb3J0IGludGVyZmFjZSBUb01hcmtkb3duT3B0aW9ucyB7XG4gIC8qKiBXcmFwIGFsbCBwaHJhc2luZyBjb250ZW50IG9mIHRoZSByb290IGluIHBhcmFncmFwaHMsIGFzIGZvciBhIHdob2xlIGRvY3VtZW50LiBAZGVmYXVsdCBmYWxzZSAqL1xuICBkb2N1bWVudD86IGJvb2xlYW5cbiAgLyoqIENvbGxhcHNlIHdoaXRlc3BhY2UgaG9sZGluZyBhIGxpbmUgZW5kaW5nIHRvIHRoYXQgbGluZSBlbmRpbmcgaW5zdGVhZCBvZiBhIHNwYWNlLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBuZXdsaW5lcz86IGJvb2xlYW5cbiAgLyoqIFRoZSB0ZXh0IG9mIGEgY2hlY2tlZCBjaGVja2JveCBvciByYWRpbywgYFt4XWAgYnkgZGVmYXVsdC4gKi9cbiAgY2hlY2tlZD86IHN0cmluZyB8IG51bGxcbiAgLyoqIFRoZSB0ZXh0IG9mIGFuIHVuY2hlY2tlZCBjaGVja2JveCBvciByYWRpbywgYFsgXWAgYnkgZGVmYXVsdC4gKi9cbiAgdW5jaGVja2VkPzogc3RyaW5nIHwgbnVsbFxuICAvKiogVGhlIHF1b3RlcyBgPHE+YCB1c2VzLCBhbiBvcGVuaW5nIGFuZCBjbG9zaW5nIGNoYXJhY3RlciBlYWNoLCBhbHRlcm5hdGluZyBieSBob3cgZGVlcCBpdCBuZXN0czsgYFwiYCBieSBkZWZhdWx0LiAqL1xuICBxdW90ZXM/OiBzdHJpbmdbXSB8IG51bGxcbn1cblxuLyoqIGBodG1sLnN0cmluZ2lmeWA6IGhhc3QgaW50byBIVE1MOyBvcHRpb25zIG5hbWVkIGFzIGhhc3QtdXRpbC10by1odG1sIG5hbWVzIHRoZW0uICovXG5leHBvcnQgaW50ZXJmYWNlIFN0cmluZ2lmeU9wdGlvbnMge1xuICAvKiogV3JpdGUgcmF3IG5vZGVzIGFzIHRoZXkgYXJlIGluc3RlYWQgb2YgZXNjYXBpbmcgdGhlbS4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgYWxsb3dEYW5nZXJvdXNIdG1sPzogYm9vbGVhblxuICAvKiogTGVhdmUgY2hhcmFjdGVycyB0aGF0IGFyZSBvbmx5IGRhbmdlcm91cyBpbiBzb21lIGNvbnRleHRzLCBzdWNoIGFzIGBgIGAgYGAsIGFzIHRoZXkgYXJlLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBhbGxvd0Rhbmdlcm91c0NoYXJhY3RlcnM/OiBib29sZWFuXG4gIC8qKiBMZWF2ZSBjaGFyYWN0ZXJzIGFzIHRoZXkgYXJlIHdoZXJlIGJyb3dzZXJzIGFjY2VwdCB0aGVtIHRob3VnaCB0aGUgc3BlYyBkb2VzIG5vdC4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgYWxsb3dQYXJzZUVycm9ycz86IGJvb2xlYW5cbiAgLyoqIFdyaXRlIGNvbW1lbnRzIGFzIGJvZ3VzIGNvbW1lbnRzLCBgPD9hPmAuIEBkZWZhdWx0IGZhbHNlICovXG4gIGJvZ3VzQ29tbWVudHM/OiBib29sZWFuXG4gIC8qKiBDbG9zZSBlbXB0eSBmb3JlaWduIGVsZW1lbnRzLCBgPGEgLz5gLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBjbG9zZUVtcHR5RWxlbWVudHM/OiBib29sZWFuXG4gIC8qKiBDbG9zZSB2b2lkIGVsZW1lbnRzLCBgPGJyIC8+YC4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgY2xvc2VTZWxmQ2xvc2luZz86IGJvb2xlYW5cbiAgLyoqIFdyaXRlIGVtcHR5IGF0dHJpYnV0ZXMgYXMgYmFyZSBuYW1lcywgYGFgIHJhdGhlciB0aGFuIGBhPVwiXCJgLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBjb2xsYXBzZUVtcHR5QXR0cmlidXRlcz86IGJvb2xlYW5cbiAgLyoqIExlYXZlIG91dCB0YWdzIHRoZSBIVE1MIHNwZWMgbGV0cyBhIHBhcnNlciBpbXBseS4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgb21pdE9wdGlvbmFsVGFncz86IGJvb2xlYW5cbiAgLyoqIExlYXZlIGF0dHJpYnV0ZSB2YWx1ZXMgdW5xdW90ZWQgd2hlcmUgdGhhdCBpcyBzYWZlLiBAZGVmYXVsdCBmYWxzZSAqL1xuICBwcmVmZXJVbnF1b3RlZD86IGJvb2xlYW5cbiAgLyoqIFRoZSBxdW90ZSBhdHRyaWJ1dGUgdmFsdWVzIGFyZSB3cmFwcGVkIGluOiBgXCJgIG9yIGAnYC4gKi9cbiAgcXVvdGU/OiBzdHJpbmcgfCBudWxsXG4gIC8qKiBVc2UgdGhlIG90aGVyIHF1b3RlIHdoZW4gdGhlIHZhbHVlIGhvbGRzIG1vcmUgb2YgdGhlIHByZWZlcnJlZCBvbmUuIEBkZWZhdWx0IGZhbHNlICovXG4gIHF1b3RlU21hcnQ/OiBib29sZWFuXG4gIC8qKiBUaGUgc3BhY2UgdGhlIHRyZWUgaXMgaW46IGBodG1sYCBvciBgc3ZnYC4gKi9cbiAgc3BhY2U/OiBzdHJpbmcgfCBudWxsXG4gIC8qKiBMZWF2ZSBvdXQgdGhlIHNwYWNlIGJldHdlZW4gcXVvdGVkIGF0dHJpYnV0ZXMuIEBkZWZhdWx0IGZhbHNlICovXG4gIHRpZ2h0QXR0cmlidXRlcz86IGJvb2xlYW5cbiAgLyoqIEpvaW4gY29tbWEtc2VwYXJhdGVkIHZhbHVlcyB3aXRoIGAsYCByYXRoZXIgdGhhbiBgLCBgLiBAZGVmYXVsdCBmYWxzZSAqL1xuICB0aWdodENvbW1hU2VwYXJhdGVkTGlzdHM/OiBib29sZWFuXG4gIC8qKiBXcml0ZSBgPCFkb2N0eXBlaHRtbD5gLiBAZGVmYXVsdCBmYWxzZSAqL1xuICB0aWdodERvY3R5cGU/OiBib29sZWFuXG4gIC8qKiBMZWF2ZSBvdXQgdGhlIHNwYWNlIGJlZm9yZSBgLz5gIHdoZW4gdGhlIGF0dHJpYnV0ZXMgYWxsb3cuIEBkZWZhdWx0IGZhbHNlICovXG4gIHRpZ2h0U2VsZkNsb3Npbmc/OiBib29sZWFuXG4gIC8qKiBXcml0ZSBgPCFET0NUWVBFIGh0bWw+YC4gQGRlZmF1bHQgZmFsc2UgKi9cbiAgdXBwZXJEb2N0eXBlPzogYm9vbGVhblxuICAvKiogVGhlIHRhZyBuYW1lcyBvZiB2b2lkIGVsZW1lbnRzLCB3aGljaCBoYXZlIG5vIGNsb3NpbmcgdGFnLiAqL1xuICB2b2lkcz86IHN0cmluZ1tdIHwgbnVsbFxufVxuXG4vKiogVGhlIGBodG1sLnBhcnNlYCBwbHVnaW4uICovXG5leHBvcnQgZnVuY3Rpb24gcGFyc2Uob3B0aW9ucz86IFBhcnNlT3B0aW9ucyk6IFBsdWdpbjxcImh0bWwucGFyc2VcIiwgUGFyc2VPcHRpb25zPiB7XG4gIGlmIChvcHRpb25zID09PSB1bmRlZmluZWQpIHJldHVybiB7IG5hbWU6IFwiaHRtbC5wYXJzZVwiIH1cbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLnBhcnNlXCIsIG9wdGlvbnMgfVxufVxuXG4vKiogVGhlIGBodG1sLnJhd2AgcGx1Z2luLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJhdyhvcHRpb25zPzogUmF3T3B0aW9ucyk6IFBsdWdpbjxcImh0bWwucmF3XCIsIFJhd09wdGlvbnM+IHtcbiAgaWYgKG9wdGlvbnMgPT09IHVuZGVmaW5lZCkgcmV0dXJuIHsgbmFtZTogXCJodG1sLnJhd1wiIH1cbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLnJhd1wiLCBvcHRpb25zIH1cbn1cblxuLyoqIFRoZSBgaHRtbC5mb3JtYXRgIHBsdWdpbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiBmb3JtYXQob3B0aW9ucz86IEZvcm1hdE9wdGlvbnMpOiBQbHVnaW48XCJodG1sLmZvcm1hdFwiLCBGb3JtYXRPcHRpb25zPiB7XG4gIGlmIChvcHRpb25zID09PSB1bmRlZmluZWQpIHJldHVybiB7IG5hbWU6IFwiaHRtbC5mb3JtYXRcIiB9XG4gIHJldHVybiB7IG5hbWU6IFwiaHRtbC5mb3JtYXRcIiwgb3B0aW9ucyB9XG59XG5cbi8qKiBUaGUgYGh0bWwuc2FuaXRpemVgIHBsdWdpbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiBzYW5pdGl6ZShvcHRpb25zPzogU2FuaXRpemVPcHRpb25zKTogUGx1Z2luPFwiaHRtbC5zYW5pdGl6ZVwiLCBTYW5pdGl6ZU9wdGlvbnM+IHtcbiAgaWYgKG9wdGlvbnMgPT09IHVuZGVmaW5lZCkgcmV0dXJuIHsgbmFtZTogXCJodG1sLnNhbml0aXplXCIgfVxuICByZXR1cm4geyBuYW1lOiBcImh0bWwuc2FuaXRpemVcIiwgb3B0aW9ucyB9XG59XG5cbi8qKiBUaGUgYGh0bWwuc2x1Z2AgcGx1Z2luLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHNsdWcob3B0aW9ucz86IFNsdWdPcHRpb25zKTogUGx1Z2luPFwiaHRtbC5zbHVnXCIsIFNsdWdPcHRpb25zPiB7XG4gIGlmIChvcHRpb25zID09PSB1bmRlZmluZWQpIHJldHVybiB7IG5hbWU6IFwiaHRtbC5zbHVnXCIgfVxuICByZXR1cm4geyBuYW1lOiBcImh0bWwuc2x1Z1wiLCBvcHRpb25zIH1cbn1cblxuLyoqIFRoZSBgaHRtbC5leHRlcm5hbExpbmtzYCBwbHVnaW4uICovXG5leHBvcnQgZnVuY3Rpb24gZXh0ZXJuYWxMaW5rcyhvcHRpb25zPzogRXh0ZXJuYWxMaW5rc09wdGlvbnMpOiBQbHVnaW48XCJodG1sLmV4dGVybmFsTGlua3NcIiwgRXh0ZXJuYWxMaW5rc09wdGlvbnM+IHtcbiAgaWYgKG9wdGlvbnMgPT09IHVuZGVmaW5lZCkgcmV0dXJuIHsgbmFtZTogXCJodG1sLmV4dGVybmFsTGlua3NcIiB9XG4gIHJldHVybiB7IG5hbWU6IFwiaHRtbC5leHRlcm5hbExpbmtzXCIsIG9wdGlvbnMgfVxufVxuXG4vKiogVGhlIGBodG1sLnVud3JhcEltYWdlc2AgcGx1Z2luLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHVud3JhcEltYWdlcygpOiBQbHVnaW48XCJodG1sLnVud3JhcEltYWdlc1wiPiB7XG4gIHJldHVybiB7IG5hbWU6IFwiaHRtbC51bndyYXBJbWFnZXNcIiB9XG59XG5cbi8qKiBUaGUgYGh0bWwuZXh0cmFjdFRvY2AgcGx1Z2luLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGV4dHJhY3RUb2MoKTogUGx1Z2luPFwiaHRtbC5leHRyYWN0VG9jXCI+IHtcbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLmV4dHJhY3RUb2NcIiB9XG59XG5cbi8qKiBUaGUgYGh0bWwuaGlnaGxpZ2h0YCBwbHVnaW4uICovXG5leHBvcnQgZnVuY3Rpb24gaGlnaGxpZ2h0KG9wdGlvbnM/OiBIaWdobGlnaHRPcHRpb25zKTogUGx1Z2luPFwiaHRtbC5oaWdobGlnaHRcIiwgSGlnaGxpZ2h0T3B0aW9ucz4ge1xuICBpZiAob3B0aW9ucyA9PT0gdW5kZWZpbmVkKSByZXR1cm4geyBuYW1lOiBcImh0bWwuaGlnaGxpZ2h0XCIgfVxuICByZXR1cm4geyBuYW1lOiBcImh0bWwuaGlnaGxpZ2h0XCIsIG9wdGlvbnMgfVxufVxuXG4vKiogVGhlIGBodG1sLmthdGV4YCBwbHVnaW4uICovXG5leHBvcnQgZnVuY3Rpb24ga2F0ZXgob3B0aW9ucz86IEthdGV4T3B0aW9ucyk6IFBsdWdpbjxcImh0bWwua2F0ZXhcIiwgS2F0ZXhPcHRpb25zPiB7XG4gIGlmIChvcHRpb25zID09PSB1bmRlZmluZWQpIHJldHVybiB7IG5hbWU6IFwiaHRtbC5rYXRleFwiIH1cbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLmthdGV4XCIsIG9wdGlvbnMgfVxufVxuXG4vKiogVGhlIGBodG1sLnRvTWFya2Rvd25gIHBsdWdpbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiB0b01hcmtkb3duKG9wdGlvbnM/OiBUb01hcmtkb3duT3B0aW9ucyk6IFBsdWdpbjxcImh0bWwudG9NYXJrZG93blwiLCBUb01hcmtkb3duT3B0aW9ucz4ge1xuICBpZiAob3B0aW9ucyA9PT0gdW5kZWZpbmVkKSByZXR1cm4geyBuYW1lOiBcImh0bWwudG9NYXJrZG93blwiIH1cbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLnRvTWFya2Rvd25cIiwgb3B0aW9ucyB9XG59XG5cbi8qKiBUaGUgYGh0bWwudG9OYXR1cmFsTGFuZ3VhZ2VgIHBsdWdpbi4gKi9cbmV4cG9ydCBmdW5jdGlvbiB0b05hdHVyYWxMYW5ndWFnZSgpOiBQbHVnaW48XCJodG1sLnRvTmF0dXJhbExhbmd1YWdlXCI+IHtcbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLnRvTmF0dXJhbExhbmd1YWdlXCIgfVxufVxuXG4vKiogVGhlIGBodG1sLnN0cmluZ2lmeWAgcGx1Z2luLiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHN0cmluZ2lmeShvcHRpb25zPzogU3RyaW5naWZ5T3B0aW9ucyk6IFBsdWdpbjxcImh0bWwuc3RyaW5naWZ5XCIsIFN0cmluZ2lmeU9wdGlvbnM+IHtcbiAgaWYgKG9wdGlvbnMgPT09IHVuZGVmaW5lZCkgcmV0dXJuIHsgbmFtZTogXCJodG1sLnN0cmluZ2lmeVwiIH1cbiAgcmV0dXJuIHsgbmFtZTogXCJodG1sLnN0cmluZ2lmeVwiLCBvcHRpb25zIH1cbn1cbiJdfQ==
|