printer.js 42 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538
  1. "use strict";
  2. Object.defineProperty(exports, "__esModule", {
  3. value: true
  4. });
  5. exports.default = exports.voidMap = void 0;
  6. var _util = require("./util");
  7. const voidMap = Object.create(null);
  8. exports.voidMap = voidMap;
  9. let voidTagNames = 'area base br col command embed hr img input keygen link meta param source track wbr';
  10. voidTagNames.split(' ').forEach(tagName => {
  11. voidMap[tagName] = true;
  12. });
  13. const NON_WHITESPACE = /\S/;
  14. class Printer {
  15. constructor(options) {
  16. this.buffer = '';
  17. this.options = options;
  18. }
  19. /*
  20. This is used by _all_ methods on this Printer class that add to `this.buffer`,
  21. it allows consumers of the printer to use alternate string representations for
  22. a given node.
  23. The primary use case for this are things like source -> source codemod utilities.
  24. For example, ember-template-recast attempts to always preserve the original string
  25. formatting in each AST node if no modifications are made to it.
  26. */
  27. handledByOverride(node, ensureLeadingWhitespace = false) {
  28. if (this.options.override !== undefined) {
  29. let result = this.options.override(node, this.options);
  30. if (typeof result === 'string') {
  31. if (ensureLeadingWhitespace && result !== '' && NON_WHITESPACE.test(result[0])) {
  32. result = ` ${result}`;
  33. }
  34. this.buffer += result;
  35. return true;
  36. }
  37. }
  38. return false;
  39. }
  40. Node(node) {
  41. switch (node.type) {
  42. case 'MustacheStatement':
  43. case 'BlockStatement':
  44. case 'PartialStatement':
  45. case 'MustacheCommentStatement':
  46. case 'CommentStatement':
  47. case 'TextNode':
  48. case 'ElementNode':
  49. case 'AttrNode':
  50. case 'Block':
  51. case 'Template':
  52. return this.TopLevelStatement(node);
  53. case 'StringLiteral':
  54. case 'BooleanLiteral':
  55. case 'NumberLiteral':
  56. case 'UndefinedLiteral':
  57. case 'NullLiteral':
  58. case 'PathExpression':
  59. case 'SubExpression':
  60. return this.Expression(node);
  61. case 'Program':
  62. return this.Block(node);
  63. case 'ConcatStatement':
  64. // should have an AttrNode parent
  65. return this.ConcatStatement(node);
  66. case 'Hash':
  67. return this.Hash(node);
  68. case 'HashPair':
  69. return this.HashPair(node);
  70. case 'ElementModifierStatement':
  71. return this.ElementModifierStatement(node);
  72. }
  73. }
  74. Expression(expression) {
  75. switch (expression.type) {
  76. case 'StringLiteral':
  77. case 'BooleanLiteral':
  78. case 'NumberLiteral':
  79. case 'UndefinedLiteral':
  80. case 'NullLiteral':
  81. return this.Literal(expression);
  82. case 'PathExpression':
  83. return this.PathExpression(expression);
  84. case 'SubExpression':
  85. return this.SubExpression(expression);
  86. }
  87. }
  88. Literal(literal) {
  89. switch (literal.type) {
  90. case 'StringLiteral':
  91. return this.StringLiteral(literal);
  92. case 'BooleanLiteral':
  93. return this.BooleanLiteral(literal);
  94. case 'NumberLiteral':
  95. return this.NumberLiteral(literal);
  96. case 'UndefinedLiteral':
  97. return this.UndefinedLiteral(literal);
  98. case 'NullLiteral':
  99. return this.NullLiteral(literal);
  100. }
  101. }
  102. TopLevelStatement(statement) {
  103. switch (statement.type) {
  104. case 'MustacheStatement':
  105. return this.MustacheStatement(statement);
  106. case 'BlockStatement':
  107. return this.BlockStatement(statement);
  108. case 'PartialStatement':
  109. return this.PartialStatement(statement);
  110. case 'MustacheCommentStatement':
  111. return this.MustacheCommentStatement(statement);
  112. case 'CommentStatement':
  113. return this.CommentStatement(statement);
  114. case 'TextNode':
  115. return this.TextNode(statement);
  116. case 'ElementNode':
  117. return this.ElementNode(statement);
  118. case 'Block':
  119. case 'Template':
  120. return this.Block(statement);
  121. case 'AttrNode':
  122. // should have element
  123. return this.AttrNode(statement);
  124. }
  125. }
  126. Block(block) {
  127. /*
  128. When processing a template like:
  129. ```hbs
  130. {{#if whatever}}
  131. whatever
  132. {{else if somethingElse}}
  133. something else
  134. {{else}}
  135. fallback
  136. {{/if}}
  137. ```
  138. The AST still _effectively_ looks like:
  139. ```hbs
  140. {{#if whatever}}
  141. whatever
  142. {{else}}{{#if somethingElse}}
  143. something else
  144. {{else}}
  145. fallback
  146. {{/if}}{{/if}}
  147. ```
  148. The only way we can tell if that is the case is by checking for
  149. `block.chained`, but unfortunately when the actual statements are
  150. processed the `block.body[0]` node (which will always be a
  151. `BlockStatement`) has no clue that its ancestor `Block` node was
  152. chained.
  153. This "forwards" the `chained` setting so that we can check
  154. it later when processing the `BlockStatement`.
  155. */
  156. if (block.chained) {
  157. let firstChild = block.body[0];
  158. firstChild.chained = true;
  159. }
  160. if (this.handledByOverride(block)) {
  161. return;
  162. }
  163. this.TopLevelStatements(block.body);
  164. }
  165. TopLevelStatements(statements) {
  166. statements.forEach(statement => this.TopLevelStatement(statement));
  167. }
  168. ElementNode(el) {
  169. if (this.handledByOverride(el)) {
  170. return;
  171. }
  172. this.OpenElementNode(el);
  173. this.TopLevelStatements(el.children);
  174. this.CloseElementNode(el);
  175. }
  176. OpenElementNode(el) {
  177. this.buffer += `<${el.tag}`;
  178. const parts = [...el.attributes, ...el.modifiers, ...el.comments].sort(_util.sortByLoc);
  179. for (const part of parts) {
  180. this.buffer += ' ';
  181. switch (part.type) {
  182. case 'AttrNode':
  183. this.AttrNode(part);
  184. break;
  185. case 'ElementModifierStatement':
  186. this.ElementModifierStatement(part);
  187. break;
  188. case 'MustacheCommentStatement':
  189. this.MustacheCommentStatement(part);
  190. break;
  191. }
  192. }
  193. if (el.blockParams.length) {
  194. this.BlockParams(el.blockParams);
  195. }
  196. if (el.selfClosing) {
  197. this.buffer += ' /';
  198. }
  199. this.buffer += '>';
  200. }
  201. CloseElementNode(el) {
  202. if (el.selfClosing || voidMap[el.tag.toLowerCase()]) {
  203. return;
  204. }
  205. this.buffer += `</${el.tag}>`;
  206. }
  207. AttrNode(attr) {
  208. if (this.handledByOverride(attr)) {
  209. return;
  210. }
  211. let {
  212. name,
  213. value
  214. } = attr;
  215. this.buffer += name;
  216. if (value.type !== 'TextNode' || value.chars.length > 0) {
  217. this.buffer += '=';
  218. this.AttrNodeValue(value);
  219. }
  220. }
  221. AttrNodeValue(value) {
  222. if (value.type === 'TextNode') {
  223. this.buffer += '"';
  224. this.TextNode(value, true);
  225. this.buffer += '"';
  226. } else {
  227. this.Node(value);
  228. }
  229. }
  230. TextNode(text, isAttr) {
  231. if (this.handledByOverride(text)) {
  232. return;
  233. }
  234. if (this.options.entityEncoding === 'raw') {
  235. this.buffer += text.chars;
  236. } else if (isAttr) {
  237. this.buffer += (0, _util.escapeAttrValue)(text.chars);
  238. } else {
  239. this.buffer += (0, _util.escapeText)(text.chars);
  240. }
  241. }
  242. MustacheStatement(mustache) {
  243. if (this.handledByOverride(mustache)) {
  244. return;
  245. }
  246. this.buffer += mustache.escaped ? '{{' : '{{{';
  247. if (mustache.strip.open) {
  248. this.buffer += '~';
  249. }
  250. this.Expression(mustache.path);
  251. this.Params(mustache.params);
  252. this.Hash(mustache.hash);
  253. if (mustache.strip.close) {
  254. this.buffer += '~';
  255. }
  256. this.buffer += mustache.escaped ? '}}' : '}}}';
  257. }
  258. BlockStatement(block) {
  259. if (this.handledByOverride(block)) {
  260. return;
  261. }
  262. if (block.chained) {
  263. this.buffer += block.inverseStrip.open ? '{{~' : '{{';
  264. this.buffer += 'else ';
  265. } else {
  266. this.buffer += block.openStrip.open ? '{{~#' : '{{#';
  267. }
  268. this.Expression(block.path);
  269. this.Params(block.params);
  270. this.Hash(block.hash);
  271. if (block.program.blockParams.length) {
  272. this.BlockParams(block.program.blockParams);
  273. }
  274. if (block.chained) {
  275. this.buffer += block.inverseStrip.close ? '~}}' : '}}';
  276. } else {
  277. this.buffer += block.openStrip.close ? '~}}' : '}}';
  278. }
  279. this.Block(block.program);
  280. if (block.inverse) {
  281. if (!block.inverse.chained) {
  282. this.buffer += block.inverseStrip.open ? '{{~' : '{{';
  283. this.buffer += 'else';
  284. this.buffer += block.inverseStrip.close ? '~}}' : '}}';
  285. }
  286. this.Block(block.inverse);
  287. }
  288. if (!block.chained) {
  289. this.buffer += block.closeStrip.open ? '{{~/' : '{{/';
  290. this.Expression(block.path);
  291. this.buffer += block.closeStrip.close ? '~}}' : '}}';
  292. }
  293. }
  294. BlockParams(blockParams) {
  295. this.buffer += ` as |${blockParams.join(' ')}|`;
  296. }
  297. PartialStatement(partial) {
  298. if (this.handledByOverride(partial)) {
  299. return;
  300. }
  301. this.buffer += '{{>';
  302. this.Expression(partial.name);
  303. this.Params(partial.params);
  304. this.Hash(partial.hash);
  305. this.buffer += '}}';
  306. }
  307. ConcatStatement(concat) {
  308. if (this.handledByOverride(concat)) {
  309. return;
  310. }
  311. this.buffer += '"';
  312. concat.parts.forEach(part => {
  313. if (part.type === 'TextNode') {
  314. this.TextNode(part, true);
  315. } else {
  316. this.Node(part);
  317. }
  318. });
  319. this.buffer += '"';
  320. }
  321. MustacheCommentStatement(comment) {
  322. if (this.handledByOverride(comment)) {
  323. return;
  324. }
  325. this.buffer += `{{!--${comment.value}--}}`;
  326. }
  327. ElementModifierStatement(mod) {
  328. if (this.handledByOverride(mod)) {
  329. return;
  330. }
  331. this.buffer += '{{';
  332. this.Expression(mod.path);
  333. this.Params(mod.params);
  334. this.Hash(mod.hash);
  335. this.buffer += '}}';
  336. }
  337. CommentStatement(comment) {
  338. if (this.handledByOverride(comment)) {
  339. return;
  340. }
  341. this.buffer += `<!--${comment.value}-->`;
  342. }
  343. PathExpression(path) {
  344. if (this.handledByOverride(path)) {
  345. return;
  346. }
  347. this.buffer += path.original;
  348. }
  349. SubExpression(sexp) {
  350. if (this.handledByOverride(sexp)) {
  351. return;
  352. }
  353. this.buffer += '(';
  354. this.Expression(sexp.path);
  355. this.Params(sexp.params);
  356. this.Hash(sexp.hash);
  357. this.buffer += ')';
  358. }
  359. Params(params) {
  360. // TODO: implement a top level Params AST node (just like the Hash object)
  361. // so that this can also be overridden
  362. if (params.length) {
  363. params.forEach(param => {
  364. this.buffer += ' ';
  365. this.Expression(param);
  366. });
  367. }
  368. }
  369. Hash(hash) {
  370. if (this.handledByOverride(hash, true)) {
  371. return;
  372. }
  373. hash.pairs.forEach(pair => {
  374. this.buffer += ' ';
  375. this.HashPair(pair);
  376. });
  377. }
  378. HashPair(pair) {
  379. if (this.handledByOverride(pair)) {
  380. return;
  381. }
  382. this.buffer += pair.key;
  383. this.buffer += '=';
  384. this.Node(pair.value);
  385. }
  386. StringLiteral(str) {
  387. if (this.handledByOverride(str)) {
  388. return;
  389. }
  390. this.buffer += JSON.stringify(str.value);
  391. }
  392. BooleanLiteral(bool) {
  393. if (this.handledByOverride(bool)) {
  394. return;
  395. }
  396. this.buffer += bool.value;
  397. }
  398. NumberLiteral(number) {
  399. if (this.handledByOverride(number)) {
  400. return;
  401. }
  402. this.buffer += number.value;
  403. }
  404. UndefinedLiteral(node) {
  405. if (this.handledByOverride(node)) {
  406. return;
  407. }
  408. this.buffer += 'undefined';
  409. }
  410. NullLiteral(node) {
  411. if (this.handledByOverride(node)) {
  412. return;
  413. }
  414. this.buffer += 'null';
  415. }
  416. print(node) {
  417. let {
  418. options
  419. } = this;
  420. if (options.override) {
  421. let result = options.override(node, options);
  422. if (result !== undefined) {
  423. return result;
  424. }
  425. }
  426. this.buffer = '';
  427. this.Node(node);
  428. return this.buffer;
  429. }
  430. }
  431. exports.default = Printer;
  432. //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uL3BhY2thZ2VzL0BnbGltbWVyL3N5bnRheC9saWIvZ2VuZXJhdGlvbi9wcmludGVyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7QUFDQTs7QUFFTyxNQUFNLE9BQU8sR0FFaEIsTUFBTSxDQUFOLE1BQUEsQ0FGRyxJQUVILENBRkc7O0FBSVAsSUFBSSxZQUFZLEdBQWhCLHFGQUFBO0FBRUEsWUFBWSxDQUFaLEtBQUEsQ0FBQSxHQUFBLEVBQUEsT0FBQSxDQUFpQyxPQUFELElBQVk7QUFDMUMsRUFBQSxPQUFPLENBQVAsT0FBTyxDQUFQLEdBQUEsSUFBQTtBQURGLENBQUE7QUFJQSxNQUFNLGNBQWMsR0FBcEIsSUFBQTs7QUFzQmMsTUFBQSxPQUFBLENBQWM7QUFJMUIsRUFBQSxXQUFBLENBQUEsT0FBQSxFQUFtQztBQUgzQixTQUFBLE1BQUEsR0FBQSxFQUFBO0FBSU4sU0FBQSxPQUFBLEdBQUEsT0FBQTtBQUNEO0FBRUQ7Ozs7Ozs7Ozs7QUFTQSxFQUFBLGlCQUFpQixDQUFBLElBQUEsRUFBbUIsdUJBQXVCLEdBQTFDLEtBQUEsRUFBa0Q7QUFDakUsUUFBSSxLQUFBLE9BQUEsQ0FBQSxRQUFBLEtBQUosU0FBQSxFQUF5QztBQUN2QyxVQUFJLE1BQU0sR0FBRyxLQUFBLE9BQUEsQ0FBQSxRQUFBLENBQUEsSUFBQSxFQUE0QixLQUF6QyxPQUFhLENBQWI7O0FBQ0EsVUFBSSxPQUFBLE1BQUEsS0FBSixRQUFBLEVBQWdDO0FBQzlCLFlBQUksdUJBQXVCLElBQUksTUFBTSxLQUFqQyxFQUFBLElBQTRDLGNBQWMsQ0FBZCxJQUFBLENBQW9CLE1BQU0sQ0FBMUUsQ0FBMEUsQ0FBMUIsQ0FBaEQsRUFBZ0Y7QUFDOUUsVUFBQSxNQUFNLEdBQUcsSUFBSSxNQUFiLEVBQUE7QUFDRDs7QUFFRCxhQUFBLE1BQUEsSUFBQSxNQUFBO0FBQ0EsZUFBQSxJQUFBO0FBQ0Q7QUFDRjs7QUFFRCxXQUFBLEtBQUE7QUFDRDs7QUFFRCxF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SUFBQSxFQUEyQjtBQUN2QyxRQUFJLEtBQUEsaUJBQUEsQ0FBSixJQUFJLENBQUosRUFBa0M7QUFDaEM7QUFDRDs7QUFFRCxTQUFBLE1BQUEsSUFBZSxJQUFJLENBQW5CLEtBQUE7QUFDRDs7QUFFRCxFQUFBLGFBQWEsQ0FBQSxNQUFBLEVBQTRCO0FBQ3ZDLFFBQUksS0FBQSxpQkFBQSxDQUFKLE1BQUksQ0FBSixFQUFvQztBQUNsQztBQUNEOztBQUVELFNBQUEsTUFBQSxJQUFlLE1BQU0sQ0FBckIsS0FBQTtBQUNEOztBQUVELEVBQUEsZ0JBQWdCLENBQUEsSUFBQSxFQUE2QjtBQUMzQyxRQUFJLEtBQUEsaUJBQUEsQ0FBSixJQUFJLENBQUosRUFBa0M7QUFDaEM7QUFDRDs7QUFFRCxTQUFBLE1BQUEsSUFBQSxXQUFBO0FBQ0Q7O0FBRUQsRUFBQSxXQUFXLENBQUEsSUFBQSxFQUF3QjtBQUNqQyxRQUFJLEtBQUEsaUJBQUEsQ0FBSixJQUFJLENBQUosRUFBa0M7QUFDaEM7QUFDRDs7QUFFRCxTQUFBLE1BQUEsSUFBQSxNQUFBO0FBQ0Q7O0FBRUQsRUFBQSxLQUFLLENBQUEsSUFBQSxFQUFpQjtBQUNwQixRQUFJO0FBQUUsTUFBQTtBQUFGLFFBQUosSUFBQTs7QUFFQSxRQUFJLE9BQU8sQ0FBWCxRQUFBLEVBQXNCO0FBQ3BCLFVBQUksTUFBTSxHQUFHLE9BQU8sQ0FBUCxRQUFBLENBQUEsSUFBQSxFQUFiLE9BQWEsQ0FBYjs7QUFFQSxVQUFJLE1BQU0sS0FBVixTQUFBLEVBQTBCO0FBQ3hCLGVBQUEsTUFBQTtBQUNEO0FBQ0Y7O0FBRUQsU0FBQSxNQUFBLEdBQUEsRUFBQTtBQUNBLFNBQUEsSUFBQSxDQUFBLElBQUE7QUFDQSxXQUFPLEtBQVAsTUFBQTtBQUNEOztBQXhleUIiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBBU1R2MSBmcm9tICcuLi92MS9hcGknO1xuaW1wb3J0IHsgZXNjYXBlQXR0clZhbHVlLCBlc2NhcGVUZXh0LCBzb3J0QnlMb2MgfSBmcm9tICcuL3V0aWwnO1xuXG5leHBvcnQgY29uc3Qgdm9pZE1hcDoge1xuICBbdGFnTmFtZTogc3RyaW5nXTogYm9vbGVhbjtcbn0gPSBPYmplY3QuY3JlYXRlKG51bGwpO1xuXG5sZXQgdm9pZFRhZ05hbWVzID1cbiAgJ2FyZWEgYmFzZSBiciBjb2wgY29tbWFuZCBlbWJlZCBociBpbWcgaW5wdXQga2V5Z2VuIGxpbmsgbWV0YSBwYXJhbSBzb3VyY2UgdHJhY2sgd2JyJztcbnZvaWRUYWdOYW1lcy5zcGxpdCgnICcpLmZvckVhY2goKHRhZ05hbWUpID0+IHtcbiAgdm9pZE1hcFt0YWdOYW1lXSA9IHRydWU7XG59KTtcblxuY29uc3QgTk9OX1dISVRFU1BBQ0UgPSAvXFxTLztcblxuZXhwb3J0IGludGVyZmFjZSBQcmludGVyT3B0aW9ucyB7XG4gIGVudGl0eUVuY29kaW5nOiAndHJhbnNmb3JtZWQnIHwgJ3Jhdyc7XG5cbiAgLyoqXG4gICAqIFVzZWQgdG8gb3ZlcnJpZGUgdGhlIG1lY2hhbmlzbSBvZiBwcmludGluZyBhIGdpdmVuIEFTVC5Ob2RlLlxuICAgKlxuICAgKiBUaGlzIHdpbGwgZ2VuZXJhbGx5IG9ubHkgYmUgdXNlZnVsIHRvIHNvdXJjZSAtPiBzb3VyY2UgY29kZW1vZHNcbiAgICogd2hlcmUgeW91IHdvdWxkIGxpa2UgdG8gc3BlY2lhbGl6ZS9vdmVycmlkZSB0aGUgd2F5IGEgZ2l2ZW4gbm9kZSBpc1xuICAgKiBwcmludGVkIChlLmcuIHlvdSB3b3VsZCBsaWtlIHRvIHByZXNlcnZlIGFzIG11Y2ggb2YgdGhlIG9yaWdpbmFsXG4gICAqIGZvcm1hdHRpbmcgYXMgcG9zc2libGUpLlxuICAgKlxuICAgKiBXaGVuIHRoZSBwcm92aWRlZCBvdmVycmlkZSByZXR1cm5zIHVuZGVmaW5lZCwgdGhlIGRlZmF1bHQgYnVpbHQgaW4gcHJpbnRpbmdcbiAgICogd2lsbCBiZSBkb25lIGZvciB0aGUgQVNULk5vZGUuXG4gICAqXG4gICAqIEBwYXJhbSBhc3QgdGhlIGFzdCBub2RlIHRvIGJlIHByaW50ZWRcbiAgICogQHBhcmFtIG9wdGlvbnMgdGhlIG9wdGlvbnMgc3BlY2lmaWVkIGR1cmluZyB0aGUgcHJpbnQoKSBpbnZvY2F0aW9uXG4gICAqL1xuICBvdmVycmlkZT8oYXN0OiBBU1R2MS5Ob2RlLCBvcHRpb25zOiBQcmludGVyT3B0aW9ucyk6IHZvaWQgfCBzdHJpbmc7XG59XG5cbmV4cG9ydCBkZWZhdWx0IGNsYXNzIFByaW50ZXIge1xuICBwcml2YXRlIGJ1ZmZlciA9ICcnO1xuICBwcml2YXRlIG9wdGlvbnM6IFByaW50ZXJPcHRpb25zO1xuXG4gIGNvbnN0cnVjdG9yKG9wdGlvbnM6IFByaW50ZXJPcHRpb25zKSB7XG4gICAgdGhpcy5vcHRpb25zID0gb3B0aW9ucztcbiAgfVxuXG4gIC8qXG4gICAgVGhpcyBpcyB1c2VkIGJ5IF9hbGxfIG1ldGhvZHMgb24gdGhpcyBQcmludGVyIGNsYXNzIHRoYXQgYWRkIHRvIGB0aGlzLmJ1ZmZlcmAsXG4gICAgaXQgYWxsb3dzIGNvbnN1bWVycyBvZiB0aGUgcHJpbnRlciB0byB1c2UgYWx0ZXJuYXRlIHN0cmluZyByZXByZXNlbnRhdGlvbnMgZm9yXG4gICAgYSBnaXZlbiBub2RlLlxuXG4gICAgVGhlIHByaW1hcnkgdXNlIGNhc2UgZm9yIHRoaXMgYXJlIHRoaW5ncyBsaWtlIHNvdXJjZSAtPiBzb3VyY2UgY29kZW1vZCB1dGlsaXRpZXMuXG4gICAgRm9yIGV4YW1wbGUsIGVtYmVyLXRlbXBsYXRlLXJlY2FzdCBhdHRlbXB0cyB0byBhbHdheXMgcHJlc2VydmUgdGhlIG9yaWdpbmFsIHN0cmluZ1xuICAgIGZvcm1hdHRpbmcgaW4gZWFjaCBBU1Qgbm9kZSBpZiBubyBtb2RpZmljYXRpb25zIGFyZSBtYWRlIHRvIGl0LlxuICAqL1xuICBoYW5kbGVkQnlPdmVycmlkZShub2RlOiBBU1R2MS5Ob2RlLCBlbnN1cmVMZWFkaW5nV2hpdGVzcGFjZSA9IGZhbHNlKTogYm9vbGVhbiB7XG4gICAgaWYgKHRoaXMub3B0aW9ucy5vdmVycmlkZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBsZXQgcmVzdWx0ID0gdGhpcy5vcHRpb25zLm92ZXJyaWRlKG5vZGUsIHRoaXMub3B0aW9ucyk7XG4gICAgICBpZiAodHlwZW9mIHJlc3VsdCA9PT0gJ3N0cmluZycpIHtcbiAgICAgICAgaWYgKGVuc3VyZUxlYWRpbmdXaGl0ZXNwYWNlICYmIHJlc3VsdCAhPT0gJycgJiYgTk9OX1dISVRFU1BBQ0UudGVzdChyZXN1bHRbMF0pKSB7XG4gICAgICAgICAgcmVzdWx0ID0gYCAke3Jlc3VsdH1gO1xuICAgICAgICB9XG5cbiAgICAgICAgdGhpcy5idWZmZXIgKz0gcmVzdWx0O1xuICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cblxuICBOb2RlKG5vZGU6IEFTVHYxLk5vZGUpOiB2b2lkIHtcbiAgICBzd2l0Y2ggKG5vZGUudHlwZSkge1xuICAgICAgY2FzZSAnTXVzdGFjaGVTdGF0ZW1lbnQnOlxuICAgICAgY2FzZSAnQmxvY2tTdGF0ZW1lbnQnOlxuICAgICAgY2FzZSAnUGFydGlhbFN0YXRlbWVudCc6XG4gICAgICBjYXNlICdNdXN0YWNoZUNvbW1lbnRTdGF0ZW1lbnQnOlxuICAgICAgY2FzZSAnQ29tbWVudFN0YXRlbWVudCc6XG4gICAgICBjYXNlICdUZXh0Tm9kZSc6XG4gICAgICBjYXNlICdFbGVtZW50Tm9kZSc6XG4gICAgICBjYXNlICdBdHRyTm9kZSc6XG4gICAgICBjYXNlICdCbG9jayc6XG4gICAgICBjYXNlICdUZW1wbGF0ZSc6XG4gICAgICAgIHJldHVybiB0aGlzLlRvcExldmVsU3RhdGVtZW50KG5vZGUpO1xuICAgICAgY2FzZSAnU3RyaW5nTGl0ZXJhbCc6XG4gICAgICBjYXNlICdCb29sZWFuTGl0ZXJhbCc6XG4gICAgICBjYXNlICdOdW1iZXJMaXRlcmFsJzpcbiAgICAgIGNhc2UgJ1VuZGVmaW5lZExpdGVyYWwnOlxuICAgICAgY2FzZSAnTnVsbExpdGVyYWwnOlxuICAgICAgY2FzZSAnUGF0aEV4cHJlc3Npb24nOlxuICAgICAgY2FzZSAnU3ViRXhwcmVzc2lvbic6XG4gICAgICAgIHJldHVybiB0aGlzLkV4cHJlc3Npb24obm9kZSk7XG4gICAgICBjYXNlICdQcm9ncmFtJzpcbiAgICAgICAgcmV0dXJuIHRoaXMuQmxvY2sobm9kZSk7XG4gICAgICBjYXNlICdDb25jYXRTdGF0ZW1lbnQnOlxuICAgICAgICAvLyBzaG91bGQgaGF2ZSBhbiBBdHRyTm9kZSBwYXJlbnRcbiAgICAgICAgcmV0dXJuIHRoaXMuQ29uY2F0U3RhdGVtZW50KG5vZGUpO1xuICAgICAgY2FzZSAnSGFzaCc6XG4gICAgICAgIHJldHVybiB0aGlzLkhhc2gobm9kZSk7XG4gICAgICBjYXNlICdIYXNoUGFpcic6XG4gICAgICAgIHJldHVybiB0aGlzLkhhc2hQYWlyKG5vZGUpO1xuICAgICAgY2FzZSAnRWxlbWVudE1vZGlmaWVyU3RhdGVtZW50JzpcbiAgICAgICAgcmV0dXJuIHRoaXMuRWxlbWVudE1vZGlmaWVyU3RhdGVtZW50KG5vZGUpO1xuICAgIH1cbiAgfVxuXG4gIEV4cHJlc3Npb24oZXhwcmVzc2lvbjogQVNUdjEuRXhwcmVzc2lvbik6IHZvaWQge1xuICAgIHN3aXRjaCAoZXhwcmVzc2lvbi50eXBlKSB7XG4gICAgICBjYXNlICdTdHJpbmdMaXRlcmFsJzpcbiAgICAgIGNhc2UgJ0Jvb2xlYW5MaXRlcmFsJzpcbiAgICAgIGNhc2UgJ051bWJlckxpdGVyYWwnOlxuICAgICAgY2FzZSAnVW5kZWZpbmVkTGl0ZXJhbCc6XG4gICAgICBjYXNlICdOdWxsTGl0ZXJhbCc6XG4gICAgICAgIHJldHVybiB0aGlzLkxpdGVyYWwoZXhwcmVzc2lvbik7XG4gICAgICBjYXNlICdQYXRoRXhwcmVzc2lvbic6XG4gICAgICAgIHJldHVybiB0aGlzLlBhdGhFeHByZXNzaW9uKGV4cHJlc3Npb24pO1xuICAgICAgY2FzZSAnU3ViRXhwcmVzc2lvbic6XG4gICAgICAgIHJldHVybiB0aGlzLlN1YkV4cHJlc3Npb24oZXhwcmVzc2lvbik7XG4gICAgfVxuICB9XG5cbiAgTGl0ZXJhbChsaXRlcmFsOiBBU1R2MS5MaXRlcmFsKTogdm9pZCB7XG4gICAgc3dpdGNoIChsaXRlcmFsLnR5cGUpIHtcbiAgICAgIGNhc2UgJ1N0cmluZ0xpdGVyYWwnOlxuICAgICAgICByZXR1cm4gdGhpcy5TdHJpbmdMaXRlcmFsKGxpdGVyYWwpO1xuICAgICAgY2FzZSAnQm9vbGVhbkxpdGVyYWwnOlxuICAgICAgICByZXR1cm4gdGhpcy5Cb29sZWFuTGl0ZXJhbChsaXRlcmFsKTtcbiAgICAgIGNhc2UgJ051bWJlckxpdGVyYWwnOlxuICAgICAgICByZXR1cm4gdGhpcy5OdW1iZXJMaXRlcmFsKGxpdGVyYWwpO1xuICAgICAgY2FzZSAnVW5kZWZpbmVkTGl0ZXJhbCc6XG4gICAgICAgIHJldHVybiB0aGlzLlVuZGVmaW5lZExpdGVyYWwobGl0ZXJhbCk7XG4gICAgICBjYXNlICdOdWxsTGl0ZXJhbCc6XG4gICAgICAgIHJldHVybiB0aGlzLk51bGxMaXRlcmFsKGxpdGVyYWwpO1xuICAgIH1cbiAgfVxuXG4gIFRvcExldmVsU3RhdGVtZW50KHN0YXRlbWVudDogQVNUdjEuVG9wTGV2ZWxTdGF0ZW1lbnQgfCBBU1R2MS5UZW1wbGF0ZSB8IEFTVHYxLkF0dHJOb2RlKTogdm9pZCB7XG4gICAgc3dpdGNoIChzdGF0ZW1lbnQudHlwZSkge1xuICAgICAgY2FzZSAnTXVzdGFjaGVTdGF0ZW1lbnQnOlxuICAgICAgICByZXR1cm4gdGhpcy5NdXN0YWNoZVN0YXRlbWVudChzdGF0ZW1lbnQpO1xuICAgICAgY2FzZSAnQmxvY2tTdGF0ZW1lbnQnOlxuICAgICAgICByZXR1cm4gdGhpcy5CbG9ja1N0YXRlbWVudChzdGF0ZW1lbnQpO1xuICAgICAgY2FzZSAnUGFydGlhbFN0YXRlbWVudCc6XG4gICAgICAgIHJldHVybiB0aGlzLlBhcnRpYWxTdGF0ZW1lbnQoc3RhdGVtZW50KTtcbiAgICAgIGNhc2UgJ011c3RhY2hlQ29tbWVudFN0YXRlbWVudCc6XG4gICAgICAgIHJldHVybiB0aGlzLk11c3RhY2hlQ29tbWVudFN0YXRlbWVudChzdGF0ZW1lbnQpO1xuICAgICAgY2FzZSAnQ29tbWVudFN0YXRlbWVudCc6XG4gICAgICAgIHJldHVybiB0aGlzLkNvbW1lbnRTdGF0ZW1lbnQoc3RhdGVtZW50KTtcbiAgICAgIGNhc2UgJ1RleHROb2RlJzpcbiAgICAgICAgcmV0dXJuIHRoaXMuVGV4dE5vZGUoc3RhdGVtZW50KTtcbiAgICAgIGNhc2UgJ0VsZW1lbnROb2RlJzpcbiAgICAgICAgcmV0dXJuIHRoaXMuRWxlbWVudE5vZGUoc3RhdGVtZW50KTtcbiAgICAgIGNhc2UgJ0Jsb2NrJzpcbiAgICAgIGNhc2UgJ1RlbXBsYXRlJzpcbiAgICAgICAgcmV0dXJuIHRoaXMuQmxvY2soc3RhdGVtZW50KTtcbiAgICAgIGNhc2UgJ0F0dHJOb2RlJzpcbiAgICAgICAgLy8gc2hvdWxkIGhhdmUgZWxlbWVudFxuICAgICAgICByZXR1cm4gdGhpcy5BdHRyTm9kZShzdGF0ZW1lbnQpO1xuICAgIH1cbiAgfVxuXG4gIEJsb2NrKGJsb2NrOiBBU1R2MS5CbG9jayB8IEFTVHYxLlByb2dyYW0gfCBBU1R2MS5UZW1wbGF0ZSk6IHZvaWQge1xuICAgIC8qXG4gICAgICBXaGVuIHByb2Nlc3NpbmcgYSB0ZW1wbGF0ZSBsaWtlOlxuXG4gICAgICBgYGBoYnNcbiAgICAgIHt7I2lmIHdoYXRldmVyfX1cbiAgICAgICAgd2hhdGV2ZXJcbiAgICAgIHt7ZWxzZSBpZiBzb21ldGhpbmdFbHNlfX1cbiAgICAgICAgc29tZXRoaW5nIGVsc2VcbiAgICAgIHt7ZWxzZX19XG4gICAgICAgIGZhbGxiYWNrXG4gICAgICB7ey9pZn19XG4gICAgICBgYGBcblxuICAgICAgVGhlIEFTVCBzdGlsbCBfZWZmZWN0aXZlbHlfIGxvb2tzIGxpa2U6XG5cbiAgICAgIGBgYGhic1xuICAgICAge3sjaWYgd2hhdGV2ZXJ9fVxuICAgICAgICB3aGF0ZXZlclxuICAgICAge3tlbHNlfX17eyNpZiBzb21ldGhpbmdFbHNlfX1cbiAgICAgICAgc29tZXRoaW5nIGVsc2VcbiAgICAgIHt7ZWxzZX19XG4gICAgICAgIGZhbGxiYWNrXG4gICAgICB7ey9pZn19e3svaWZ9fVxuICAgICAgYGBgXG5cbiAgICAgIFRoZSBvbmx5IHdheSB3ZSBjYW4gdGVsbCBpZiB0aGF0IGlzIHRoZSBjYXNlIGlzIGJ5IGNoZWNraW5nIGZvclxuICAgICAgYGJsb2NrLmNoYWluZWRgLCBidXQgdW5mb3J0dW5hdGVseSB3aGVuIHRoZSBhY3R1YWwgc3RhdGVtZW50cyBhcmVcbiAgICAgIHByb2Nlc3NlZCB0aGUgYGJsb2NrLmJvZHlbMF1gIG5vZGUgKHdoaWNoIHdpbGwgYWx3YXlzIGJlIGFcbiAgICAgIGBCbG9ja1N0YXRlbWVudGApIGhhcyBubyBjbHVlIHRoYXQgaXRzIGFuY2VzdG9yIGBCbG9ja2Agbm9kZSB3YXNcbiAgICAgIGNoYWluZWQuXG5cbiAgICAgIFRoaXMgXCJmb3J3YXJkc1wiIHRoZSBgY2hhaW5lZGAgc2V0dGluZyBzbyB0aGF0IHdlIGNhbiBjaGVja1xuICAgICAgaXQgbGF0ZXIgd2hlbiBwcm9jZXNzaW5nIHRoZSBgQmxvY2tTdGF0ZW1lbnRgLlxuICAgICovXG4gICAgaWYgKGJsb2NrLmNoYWluZWQpIHtcbiAgICAgIGxldCBmaXJzdENoaWxkID0gYmxvY2suYm9keVswXSBhcyBBU1R2MS5CbG9ja1N0YXRlbWVudDtcbiAgICAgIGZpcnN0Q2hpbGQuY2hhaW5lZCA9IHRydWU7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoYmxvY2spKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5Ub3BMZXZlbFN0YXRlbWVudHMoYmxvY2suYm9keSk7XG4gIH1cblxuICBUb3BMZXZlbFN0YXRlbWVudHMoc3RhdGVtZW50czogQVNUdjEuVG9wTGV2ZWxTdGF0ZW1lbnRbXSk6IHZvaWQge1xuICAgIHN0YXRlbWVudHMuZm9yRWFjaCgoc3RhdGVtZW50KSA9PiB0aGlzLlRvcExldmVsU3RhdGVtZW50KHN0YXRlbWVudCkpO1xuICB9XG5cbiAgRWxlbWVudE5vZGUoZWw6IEFTVHYxLkVsZW1lbnROb2RlKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoZWwpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5PcGVuRWxlbWVudE5vZGUoZWwpO1xuICAgIHRoaXMuVG9wTGV2ZWxTdGF0ZW1lbnRzKGVsLmNoaWxkcmVuKTtcbiAgICB0aGlzLkNsb3NlRWxlbWVudE5vZGUoZWwpO1xuICB9XG5cbiAgT3BlbkVsZW1lbnROb2RlKGVsOiBBU1R2MS5FbGVtZW50Tm9kZSk6IHZvaWQge1xuICAgIHRoaXMuYnVmZmVyICs9IGA8JHtlbC50YWd9YDtcbiAgICBjb25zdCBwYXJ0cyA9IFsuLi5lbC5hdHRyaWJ1dGVzLCAuLi5lbC5tb2RpZmllcnMsIC4uLmVsLmNvbW1lbnRzXS5zb3J0KHNvcnRCeUxvYyk7XG5cbiAgICBmb3IgKGNvbnN0IHBhcnQgb2YgcGFydHMpIHtcbiAgICAgIHRoaXMuYnVmZmVyICs9ICcgJztcbiAgICAgIHN3aXRjaCAocGFydC50eXBlKSB7XG4gICAgICAgIGNhc2UgJ0F0dHJOb2RlJzpcbiAgICAgICAgICB0aGlzLkF0dHJOb2RlKHBhcnQpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlICdFbGVtZW50TW9kaWZpZXJTdGF0ZW1lbnQnOlxuICAgICAgICAgIHRoaXMuRWxlbWVudE1vZGlmaWVyU3RhdGVtZW50KHBhcnQpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlICdNdXN0YWNoZUNvbW1lbnRTdGF0ZW1lbnQnOlxuICAgICAgICAgIHRoaXMuTXVzdGFjaGVDb21tZW50U3RhdGVtZW50KHBhcnQpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgfVxuICAgIH1cbiAgICBpZiAoZWwuYmxvY2tQYXJhbXMubGVuZ3RoKSB7XG4gICAgICB0aGlzLkJsb2NrUGFyYW1zKGVsLmJsb2NrUGFyYW1zKTtcbiAgICB9XG4gICAgaWYgKGVsLnNlbGZDbG9zaW5nKSB7XG4gICAgICB0aGlzLmJ1ZmZlciArPSAnIC8nO1xuICAgIH1cbiAgICB0aGlzLmJ1ZmZlciArPSAnPic7XG4gIH1cblxuICBDbG9zZUVsZW1lbnROb2RlKGVsOiBBU1R2MS5FbGVtZW50Tm9kZSk6IHZvaWQge1xuICAgIGlmIChlbC5zZWxmQ2xvc2luZyB8fCB2b2lkTWFwW2VsLnRhZy50b0xvd2VyQ2FzZSgpXSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICB0aGlzLmJ1ZmZlciArPSBgPC8ke2VsLnRhZ30+YDtcbiAgfVxuXG4gIEF0dHJOb2RlKGF0dHI6IEFTVHYxLkF0dHJOb2RlKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoYXR0cikpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBsZXQgeyBuYW1lLCB2YWx1ZSB9ID0gYXR0cjtcblxuICAgIHRoaXMuYnVmZmVyICs9IG5hbWU7XG4gICAgaWYgKHZhbHVlLnR5cGUgIT09ICdUZXh0Tm9kZScgfHwgdmFsdWUuY2hhcnMubGVuZ3RoID4gMCkge1xuICAgICAgdGhpcy5idWZmZXIgKz0gJz0nO1xuICAgICAgdGhpcy5BdHRyTm9kZVZhbHVlKHZhbHVlKTtcbiAgICB9XG4gIH1cblxuICBBdHRyTm9kZVZhbHVlKHZhbHVlOiBBU1R2MS5BdHRyTm9kZVsndmFsdWUnXSk6IHZvaWQge1xuICAgIGlmICh2YWx1ZS50eXBlID09PSAnVGV4dE5vZGUnKSB7XG4gICAgICB0aGlzLmJ1ZmZlciArPSAnXCInO1xuICAgICAgdGhpcy5UZXh0Tm9kZSh2YWx1ZSwgdHJ1ZSk7XG4gICAgICB0aGlzLmJ1ZmZlciArPSAnXCInO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLk5vZGUodmFsdWUpO1xuICAgIH1cbiAgfVxuXG4gIFRleHROb2RlKHRleHQ6IEFTVHYxLlRleHROb2RlLCBpc0F0dHI/OiBib29sZWFuKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUodGV4dCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAodGhpcy5vcHRpb25zLmVudGl0eUVuY29kaW5nID09PSAncmF3Jykge1xuICAgICAgdGhpcy5idWZmZXIgKz0gdGV4dC5jaGFycztcbiAgICB9IGVsc2UgaWYgKGlzQXR0cikge1xuICAgICAgdGhpcy5idWZmZXIgKz0gZXNjYXBlQXR0clZhbHVlKHRleHQuY2hhcnMpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmJ1ZmZlciArPSBlc2NhcGVUZXh0KHRleHQuY2hhcnMpO1xuICAgIH1cbiAgfVxuXG4gIE11c3RhY2hlU3RhdGVtZW50KG11c3RhY2hlOiBBU1R2MS5NdXN0YWNoZVN0YXRlbWVudCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKG11c3RhY2hlKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IG11c3RhY2hlLmVzY2FwZWQgPyAne3snIDogJ3t7eyc7XG5cbiAgICBpZiAobXVzdGFjaGUuc3RyaXAub3Blbikge1xuICAgICAgdGhpcy5idWZmZXIgKz0gJ34nO1xuICAgIH1cblxuICAgIHRoaXMuRXhwcmVzc2lvbihtdXN0YWNoZS5wYXRoKTtcbiAgICB0aGlzLlBhcmFtcyhtdXN0YWNoZS5wYXJhbXMpO1xuICAgIHRoaXMuSGFzaChtdXN0YWNoZS5oYXNoKTtcblxuICAgIGlmIChtdXN0YWNoZS5zdHJpcC5jbG9zZSkge1xuICAgICAgdGhpcy5idWZmZXIgKz0gJ34nO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IG11c3RhY2hlLmVzY2FwZWQgPyAnfX0nIDogJ319fSc7XG4gIH1cblxuICBCbG9ja1N0YXRlbWVudChibG9jazogQVNUdjEuQmxvY2tTdGF0ZW1lbnQpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5oYW5kbGVkQnlPdmVycmlkZShibG9jaykpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBpZiAoYmxvY2suY2hhaW5lZCkge1xuICAgICAgdGhpcy5idWZmZXIgKz0gYmxvY2suaW52ZXJzZVN0cmlwLm9wZW4gPyAne3t+JyA6ICd7eyc7XG4gICAgICB0aGlzLmJ1ZmZlciArPSAnZWxzZSAnO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLmJ1ZmZlciArPSBibG9jay5vcGVuU3RyaXAub3BlbiA/ICd7e34jJyA6ICd7eyMnO1xuICAgIH1cblxuICAgIHRoaXMuRXhwcmVzc2lvbihibG9jay5wYXRoKTtcbiAgICB0aGlzLlBhcmFtcyhibG9jay5wYXJhbXMpO1xuICAgIHRoaXMuSGFzaChibG9jay5oYXNoKTtcbiAgICBpZiAoYmxvY2sucHJvZ3JhbS5ibG9ja1BhcmFtcy5sZW5ndGgpIHtcbiAgICAgIHRoaXMuQmxvY2tQYXJhbXMoYmxvY2sucHJvZ3JhbS5ibG9ja1BhcmFtcyk7XG4gICAgfVxuXG4gICAgaWYgKGJsb2NrLmNoYWluZWQpIHtcbiAgICAgIHRoaXMuYnVmZmVyICs9IGJsb2NrLmludmVyc2VTdHJpcC5jbG9zZSA/ICd+fX0nIDogJ319JztcbiAgICB9IGVsc2Uge1xuICAgICAgdGhpcy5idWZmZXIgKz0gYmxvY2sub3BlblN0cmlwLmNsb3NlID8gJ359fScgOiAnfX0nO1xuICAgIH1cblxuICAgIHRoaXMuQmxvY2soYmxvY2sucHJvZ3JhbSk7XG5cbiAgICBpZiAoYmxvY2suaW52ZXJzZSkge1xuICAgICAgaWYgKCFibG9jay5pbnZlcnNlLmNoYWluZWQpIHtcbiAgICAgICAgdGhpcy5idWZmZXIgKz0gYmxvY2suaW52ZXJzZVN0cmlwLm9wZW4gPyAne3t+JyA6ICd7eyc7XG4gICAgICAgIHRoaXMuYnVmZmVyICs9ICdlbHNlJztcbiAgICAgICAgdGhpcy5idWZmZXIgKz0gYmxvY2suaW52ZXJzZVN0cmlwLmNsb3NlID8gJ359fScgOiAnfX0nO1xuICAgICAgfVxuXG4gICAgICB0aGlzLkJsb2NrKGJsb2NrLmludmVyc2UpO1xuICAgIH1cblxuICAgIGlmICghYmxvY2suY2hhaW5lZCkge1xuICAgICAgdGhpcy5idWZmZXIgKz0gYmxvY2suY2xvc2VTdHJpcC5vcGVuID8gJ3t7fi8nIDogJ3t7Lyc7XG4gICAgICB0aGlzLkV4cHJlc3Npb24oYmxvY2sucGF0aCk7XG4gICAgICB0aGlzLmJ1ZmZlciArPSBibG9jay5jbG9zZVN0cmlwLmNsb3NlID8gJ359fScgOiAnfX0nO1xuICAgIH1cbiAgfVxuXG4gIEJsb2NrUGFyYW1zKGJsb2NrUGFyYW1zOiBzdHJpbmdbXSk6IHZvaWQge1xuICAgIHRoaXMuYnVmZmVyICs9IGAgYXMgfCR7YmxvY2tQYXJhbXMuam9pbignICcpfXxgO1xuICB9XG5cbiAgUGFydGlhbFN0YXRlbWVudChwYXJ0aWFsOiBBU1R2MS5QYXJ0aWFsU3RhdGVtZW50KTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUocGFydGlhbCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmJ1ZmZlciArPSAne3s+JztcbiAgICB0aGlzLkV4cHJlc3Npb24ocGFydGlhbC5uYW1lKTtcbiAgICB0aGlzLlBhcmFtcyhwYXJ0aWFsLnBhcmFtcyk7XG4gICAgdGhpcy5IYXNoKHBhcnRpYWwuaGFzaCk7XG4gICAgdGhpcy5idWZmZXIgKz0gJ319JztcbiAgfVxuXG4gIENvbmNhdFN0YXRlbWVudChjb25jYXQ6IEFTVHYxLkNvbmNhdFN0YXRlbWVudCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKGNvbmNhdCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmJ1ZmZlciArPSAnXCInO1xuICAgIGNvbmNhdC5wYXJ0cy5mb3JFYWNoKChwYXJ0KSA9PiB7XG4gICAgICBpZiAocGFydC50eXBlID09PSAnVGV4dE5vZGUnKSB7XG4gICAgICAgIHRoaXMuVGV4dE5vZGUocGFydCwgdHJ1ZSk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aGlzLk5vZGUocGFydCk7XG4gICAgICB9XG4gICAgfSk7XG4gICAgdGhpcy5idWZmZXIgKz0gJ1wiJztcbiAgfVxuXG4gIE11c3RhY2hlQ29tbWVudFN0YXRlbWVudChjb21tZW50OiBBU1R2MS5NdXN0YWNoZUNvbW1lbnRTdGF0ZW1lbnQpOiB2b2lkIHtcbiAgICBpZiAodGhpcy5oYW5kbGVkQnlPdmVycmlkZShjb21tZW50KSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IGB7eyEtLSR7Y29tbWVudC52YWx1ZX0tLX19YDtcbiAgfVxuXG4gIEVsZW1lbnRNb2RpZmllclN0YXRlbWVudChtb2Q6IEFTVHYxLkVsZW1lbnRNb2RpZmllclN0YXRlbWVudCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKG1vZCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmJ1ZmZlciArPSAne3snO1xuICAgIHRoaXMuRXhwcmVzc2lvbihtb2QucGF0aCk7XG4gICAgdGhpcy5QYXJhbXMobW9kLnBhcmFtcyk7XG4gICAgdGhpcy5IYXNoKG1vZC5oYXNoKTtcbiAgICB0aGlzLmJ1ZmZlciArPSAnfX0nO1xuICB9XG5cbiAgQ29tbWVudFN0YXRlbWVudChjb21tZW50OiBBU1R2MS5Db21tZW50U3RhdGVtZW50KTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoY29tbWVudCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICB0aGlzLmJ1ZmZlciArPSBgPCEtLSR7Y29tbWVudC52YWx1ZX0tLT5gO1xuICB9XG5cbiAgUGF0aEV4cHJlc3Npb24ocGF0aDogQVNUdjEuUGF0aEV4cHJlc3Npb24pOiB2b2lkIHtcbiAgICBpZiAodGhpcy5oYW5kbGVkQnlPdmVycmlkZShwYXRoKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IHBhdGgub3JpZ2luYWw7XG4gIH1cblxuICBTdWJFeHByZXNzaW9uKHNleHA6IEFTVHYxLlN1YkV4cHJlc3Npb24pOiB2b2lkIHtcbiAgICBpZiAodGhpcy5oYW5kbGVkQnlPdmVycmlkZShzZXhwKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9ICcoJztcbiAgICB0aGlzLkV4cHJlc3Npb24oc2V4cC5wYXRoKTtcbiAgICB0aGlzLlBhcmFtcyhzZXhwLnBhcmFtcyk7XG4gICAgdGhpcy5IYXNoKHNleHAuaGFzaCk7XG4gICAgdGhpcy5idWZmZXIgKz0gJyknO1xuICB9XG5cbiAgUGFyYW1zKHBhcmFtczogQVNUdjEuRXhwcmVzc2lvbltdKTogdm9pZCB7XG4gICAgLy8gVE9ETzogaW1wbGVtZW50IGEgdG9wIGxldmVsIFBhcmFtcyBBU1Qgbm9kZSAoanVzdCBsaWtlIHRoZSBIYXNoIG9iamVjdClcbiAgICAvLyBzbyB0aGF0IHRoaXMgY2FuIGFsc28gYmUgb3ZlcnJpZGRlblxuICAgIGlmIChwYXJhbXMubGVuZ3RoKSB7XG4gICAgICBwYXJhbXMuZm9yRWFjaCgocGFyYW0pID0+IHtcbiAgICAgICAgdGhpcy5idWZmZXIgKz0gJyAnO1xuICAgICAgICB0aGlzLkV4cHJlc3Npb24ocGFyYW0pO1xuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgSGFzaChoYXNoOiBBU1R2MS5IYXNoKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoaGFzaCwgdHJ1ZSkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBoYXNoLnBhaXJzLmZvckVhY2goKHBhaXIpID0+IHtcbiAgICAgIHRoaXMuYnVmZmVyICs9ICcgJztcbiAgICAgIHRoaXMuSGFzaFBhaXIocGFpcik7XG4gICAgfSk7XG4gIH1cblxuICBIYXNoUGFpcihwYWlyOiBBU1R2MS5IYXNoUGFpcik6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKHBhaXIpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5idWZmZXIgKz0gcGFpci5rZXk7XG4gICAgdGhpcy5idWZmZXIgKz0gJz0nO1xuICAgIHRoaXMuTm9kZShwYWlyLnZhbHVlKTtcbiAgfVxuXG4gIFN0cmluZ0xpdGVyYWwoc3RyOiBBU1R2MS5TdHJpbmdMaXRlcmFsKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUoc3RyKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IEpTT04uc3RyaW5naWZ5KHN0ci52YWx1ZSk7XG4gIH1cblxuICBCb29sZWFuTGl0ZXJhbChib29sOiBBU1R2MS5Cb29sZWFuTGl0ZXJhbCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKGJvb2wpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5idWZmZXIgKz0gYm9vbC52YWx1ZTtcbiAgfVxuXG4gIE51bWJlckxpdGVyYWwobnVtYmVyOiBBU1R2MS5OdW1iZXJMaXRlcmFsKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuaGFuZGxlZEJ5T3ZlcnJpZGUobnVtYmVyKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVmZmVyICs9IG51bWJlci52YWx1ZTtcbiAgfVxuXG4gIFVuZGVmaW5lZExpdGVyYWwobm9kZTogQVNUdjEuVW5kZWZpbmVkTGl0ZXJhbCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKG5vZGUpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5idWZmZXIgKz0gJ3VuZGVmaW5lZCc7XG4gIH1cblxuICBOdWxsTGl0ZXJhbChub2RlOiBBU1R2MS5OdWxsTGl0ZXJhbCk6IHZvaWQge1xuICAgIGlmICh0aGlzLmhhbmRsZWRCeU92ZXJyaWRlKG5vZGUpKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdGhpcy5idWZmZXIgKz0gJ251bGwnO1xuICB9XG5cbiAgcHJpbnQobm9kZTogQVNUdjEuTm9kZSk6IHN0cmluZyB7XG4gICAgbGV0IHsgb3B0aW9ucyB9ID0gdGhpcztcblxuICAgIGlmIChvcHRpb25zLm92ZXJyaWRlKSB7XG4gICAgICBsZXQgcmVzdWx0ID0gb3B0aW9ucy5vdmVycmlkZShub2RlLCBvcHRpb25zKTtcblxuICAgICAgaWYgKHJlc3VsdCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIHJldHVybiByZXN1bHQ7XG4gICAgICB9XG4gICAgfVxuXG4gICAgdGhpcy5idWZmZXIgPSAnJztcbiAgICB0aGlzLk5vZGUobm9kZSk7XG4gICAgcmV0dXJuIHRoaXMuYnVmZmVyO1xuICB9XG59XG4iXSwic291cmNlUm9vdCI6IiJ9