@dollhousemcp/mcp-server 2.0.31 → 2.0.34

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.
Files changed (43) hide show
  1. package/CHANGELOG.md +5 -0
  2. package/data/ensembles/welcome-to-the-dollhouse.md +94 -0
  3. package/data/personas/dollhouse-expert.md +242 -14
  4. package/data/skills/research-to-elements.md +136 -0
  5. package/dist/elements/agents/AgentManager.d.ts +8 -1
  6. package/dist/elements/agents/AgentManager.d.ts.map +1 -1
  7. package/dist/elements/agents/AgentManager.js +50 -10
  8. package/dist/elements/ensembles/EnsembleManager.d.ts +36 -0
  9. package/dist/elements/ensembles/EnsembleManager.d.ts.map +1 -1
  10. package/dist/elements/ensembles/EnsembleManager.js +94 -5
  11. package/dist/elements/skills/Skill.d.ts.map +1 -1
  12. package/dist/elements/skills/Skill.js +2 -2
  13. package/dist/elements/templates/Template.d.ts.map +1 -1
  14. package/dist/elements/templates/Template.js +15 -2
  15. package/dist/elements/templates/TemplateManager.js +3 -3
  16. package/dist/generated/version.d.ts +2 -2
  17. package/dist/generated/version.js +3 -3
  18. package/dist/handlers/element-crud/createElement.d.ts.map +1 -1
  19. package/dist/handlers/element-crud/createElement.js +10 -2
  20. package/dist/handlers/element-crud/editElement.d.ts.map +1 -1
  21. package/dist/handlers/element-crud/editElement.js +61 -5
  22. package/dist/handlers/mcp-aql/MCPAQLHandler.d.ts.map +1 -1
  23. package/dist/handlers/mcp-aql/MCPAQLHandler.js +31 -2
  24. package/dist/handlers/mcp-aql/OperationSchema.d.ts.map +1 -1
  25. package/dist/handlers/mcp-aql/OperationSchema.js +7 -6
  26. package/dist/security/constants.d.ts +1 -0
  27. package/dist/security/constants.d.ts.map +1 -1
  28. package/dist/security/constants.js +2 -1
  29. package/dist/security/secureYamlParser.js +2 -2
  30. package/dist/server/tools/MCPAQLTools.js +21 -5
  31. package/dist/services/validation/AgentElementValidator.d.ts.map +1 -1
  32. package/dist/services/validation/AgentElementValidator.js +3 -2
  33. package/dist/services/validation/GenericElementValidator.d.ts +1 -0
  34. package/dist/services/validation/GenericElementValidator.d.ts.map +1 -1
  35. package/dist/services/validation/GenericElementValidator.js +14 -6
  36. package/dist/web/public/app.js +213 -12
  37. package/dist/web/public/index.html +16 -7
  38. package/dist/web/public/styles.css +229 -30
  39. package/dist/web/routes/permissionRoutes.d.ts.map +1 -1
  40. package/dist/web/routes/permissionRoutes.js +48 -11
  41. package/package.json +21 -5
  42. package/scripts/pretooluse-dollhouse.sh +23 -4
  43. package/server.json +2 -2
@@ -336,11 +336,12 @@ export class GenericElementValidator {
336
336
  if (typeof description !== 'string') {
337
337
  return ValidatorHelpers.fail(["Description must be a string"]);
338
338
  }
339
- const result = this.validationService.validateAndSanitizeInput(description, {
340
- maxLength: SECURITY_LIMITS.MAX_DESCRIPTION_LENGTH,
341
- allowSpaces: true,
342
- fieldType: 'description'
343
- });
339
+ if (description.length > SECURITY_LIMITS.MAX_DESCRIPTION_LENGTH) {
340
+ return ValidatorHelpers.fail([
341
+ `Description exceeds maximum length of ${SECURITY_LIMITS.MAX_DESCRIPTION_LENGTH} characters`
342
+ ]);
343
+ }
344
+ const result = this.sanitizeDescriptionInput(description);
344
345
  if (!result.isValid) {
345
346
  return ValidatorHelpers.fail(result.errors || ['Invalid description']);
346
347
  }
@@ -353,6 +354,13 @@ export class GenericElementValidator {
353
354
  warnings
354
355
  };
355
356
  }
357
+ sanitizeDescriptionInput(description) {
358
+ return this.validationService.validateAndSanitizeInput(description, {
359
+ maxLength: SECURITY_LIMITS.MAX_DESCRIPTION_LENGTH,
360
+ allowSpaces: true,
361
+ fieldType: 'description'
362
+ });
363
+ }
356
364
  /**
357
365
  * Validate element content
358
366
  */
@@ -473,4 +481,4 @@ export class GenericElementValidator {
473
481
  return labels[this.elementType] || this.elementType;
474
482
  }
475
483
  }
476
- //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiR2VuZXJpY0VsZW1lbnRWYWxpZGF0b3IuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvc2VydmljZXMvdmFsaWRhdGlvbi9HZW5lcmljRWxlbWVudFZhbGlkYXRvci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7O0dBU0c7QUFFSCxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFJdkQsT0FBTyxFQUFFLGVBQWUsRUFBRSxNQUFNLDZCQUE2QixDQUFDO0FBQzlELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxtQ0FBbUMsQ0FBQztBQUNwRSxPQUFPLEVBTUwsZ0JBQWdCLEVBQ2pCLE1BQU0sdUJBQXVCLENBQUM7QUFFL0I7O0dBRUc7QUFDSCxNQUFNLE9BQU8sdUJBQXVCO0lBS3RCO0lBQ0E7SUFDQTtJQU5ILFdBQVcsQ0FBYztJQUVsQyxZQUNFLFdBQXdCLEVBQ2QsaUJBQW9DLEVBQ3BDLHdCQUFrRCxFQUNsRCxlQUFnQztRQUZoQyxzQkFBaUIsR0FBakIsaUJBQWlCLENBQW1CO1FBQ3BDLDZCQUF3QixHQUF4Qix3QkFBd0IsQ0FBMEI7UUFDbEQsb0JBQWUsR0FBZixlQUFlLENBQWlCO1FBRTFDLElBQUksQ0FBQyxXQUFXLEdBQUcsV0FBVyxDQUFDO0lBQ2pDLENBQUM7SUFFRDs7Ozs7Ozs7T0FRRztJQUNILEtBQUssQ0FBQyxjQUFjLENBQ2xCLElBQWEsRUFDYixPQUFrQztRQUVsQyxNQUFNLE1BQU0sR0FBYSxFQUFFLENBQUM7UUFDNUIsTUFBTSxRQUFRLEdBQWEsRUFBRSxDQUFDO1FBQzlCLE1BQU0sV0FBVyxHQUFhLEVBQUUsQ0FBQztRQUVqQyxJQUFJLENBQUMsSUFBSSxJQUFJLE9BQU8sSUFBSSxLQUFLLFFBQVEsRUFBRSxDQUFDO1lBQ3RDLE9BQU8sZ0JBQWdCLENBQUMsSUFBSSxDQUFDLENBQUMsZ0NBQWdDLENBQUMsQ0FBQyxDQUFDO1FBQ25FLENBQUM7UUFFRCw0REFB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Q0FBQyxFQUFFLE9BQU87WUFDNUIsQ0FBQyxXQUFXLENBQUMsTUFBTSxDQUFDLEVBQUUsUUFBUTtZQUM5QixDQUFDLFdBQVcsQ0FBQyxRQUFRLENBQUMsRUFBRSxVQUFVO1NBQ25DLENBQUM7UUFDRixPQUFPLE1BQU0sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLElBQUksSUFBSSxDQUFDLFdBQVcsQ0FBQztJQUN0RCxDQUFDO0NBQ0YiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIEdlbmVyaWNFbGVtZW50VmFsaWRhdG9yIC0gRGVmYXVsdCB2YWxpZGF0b3IgaW1wbGVtZW50YXRpb24gZm9yIG1vc3QgZWxlbWVudCB0eXBlc1xuICpcbiAqIFByb3ZpZGVzIHN0YW5kYXJkIHZhbGlkYXRpb24gbG9naWMgdGhhdCB3b3JrcyBmb3IgYW55IGVsZW1lbnQgdHlwZS5cbiAqIFVzZXMgdGhlIGV4aXN0aW5nIFZhbGlkYXRpb25TZXJ2aWNlIGFuZCBUcmlnZ2VyVmFsaWRhdGlvblNlcnZpY2UgZm9yXG4gKiBjb25zaXN0ZW50IHNlY3VyaXR5LWZpcnN0IHZhbGlkYXRpb24gcGF0dGVybnMuXG4gKlxuICogRWxlbWVudCB0eXBlcyB0aGF0IG5lZWQgc3BlY2lhbGl6ZWQgdmFsaWRhdGlvbiAobGlrZSBwZXJzb25hcykgY2FuXG4gKiBleHRlbmQgdGhpcyBjbGFzcyBvciBpbXBsZW1lbnQgRWxlbWVudFZhbGlkYXRvciBkaXJlY3RseS5cbiAqL1xuXG5pbXBvcnQgeyBFbGVtZW50VHlwZSB9IGZyb20gJy4uLy4uL3BvcnRmb2xpby90eXBlcy5qcyc7XG5pbXBvcnQgeyBWYWxpZGF0aW9uU2VydmljZSB9IGZyb20gJy4vVmFsaWRhdGlvblNlcnZpY2UuanMnO1xuaW1wb3J0IHsgVHJpZ2dlclZhbGlkYXRpb25TZXJ2aWNlIH0gZnJvbSAnLi9UcmlnZ2VyVmFsaWRhdGlvblNlcnZpY2UuanMnO1xuaW1wb3J0IHsgTWV0YWRhdGFTZXJ2aWNlIH0gZnJvbSAnLi4vTWV0YWRhdGFTZXJ2aWNlLmpzJztcbmltcG9ydCB7IFNFQ1VSSVRZX0xJTUlUUyB9IGZyb20gJy4uLy4uL3NlY3VyaXR5L2NvbnN0YW50cy5qcyc7XG5pbXBvcnQgeyBJbnB1dE5vcm1hbGl6ZXIgfSBmcm9tICcuLi8uLi9zZWN1cml0eS9JbnB1dE5vcm1hbGl6ZXIuanMnO1xuaW1wb3J0IHtcbiAgRWxlbWVudFZhbGlkYXRvcixcbiAgVmFsaWRhdGlvblJlc3VsdCxcbiAgVmFsaWRhdGlvblJlcG9ydCxcbiAgRWxlbWVudFZhbGlkYXRpb25PcHRpb25zLFxuICBNZXRhZGF0YVZhbGlkYXRpb25PcHRpb25zLFxuICBWYWxpZGF0b3JIZWxwZXJzXG59IGZyb20gJy4vRWxlbWVudFZhbGlkYXRvci5qcyc7XG5cbi8qKlxuICogRGVmYXVsdCB2YWxpZGF0b3IgaW1wbGVtZW50YXRpb24gZm9yIG1vc3QgZWxlbWVudCB0eXBlc1xuICovXG5leHBvcnQgY2xhc3MgR2VuZXJpY0VsZW1lbnRWYWxpZGF0b3IgaW1wbGVtZW50cyBFbGVtZW50VmFsaWRhdG9yIHtcbiAgcmVhZG9ubHkgZWxlbWVudFR5cGU6IEVsZW1lbnRUeXBlO1xuXG4gIGNvbnN0cnVjdG9yKFxuICAgIGVsZW1lbnRUeXBlOiBFbGVtZW50VHlwZSxcbiAgICBwcm90ZWN0ZWQgdmFsaWRhdGlvblNlcnZpY2U6IFZhbGlkYXRpb25TZXJ2aWNlLFxuICAgIHByb3RlY3RlZCB0cmlnZ2VyVmFsaWRhdGlvblNlcnZpY2U6IFRyaWdnZXJWYWxpZGF0aW9uU2VydmljZSxcbiAgICBwcm90ZWN0ZWQgbWV0YWRhdGFTZXJ2aWNlOiBNZXRhZGF0YVNlcnZpY2VcbiAgKSB7XG4gICAgdGhpcy5lbGVtZW50VHlwZSA9IGVsZW1lbnRUeXBlO1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGRhdGEgZm9yIGVsZW1lbnQgY3JlYXRpb25cbiAgICpcbiAgICogQVJDSElURUNUVVJFOiBJbnB1dCBOb3JtYWxpemF0aW9uIGF0IEJvdW5kYXJ5XG4gICAqIFN0ZXAgMTogTm9ybWFsaXplIEFMTCBzdHJpbmcgZmllbGRzIChVbmljb2RlLCBjb25mdXNhYmxlcywgZGlyZWN0aW9uIG92ZXJyaWRlcylcbiAgICogU3RlcCAyOiBWYWxpZGF0ZSB0aGUgbm9ybWFsaXplZCBkYXRhIChmaWVsZCBydWxlcywgbGVuZ3RocywgcGF0dGVybnMpXG4gICAqXG4gICAqIFRoaXMgZW5zdXJlcyB3ZSBjYW4ndCBmb3JnZXQgdG8gbm9ybWFsaXplIGEgZmllbGQgLSBpdCBoYXBwZW5zIG9uY2UgYXQgZW50cnkuXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZUNyZWF0ZShcbiAgICBkYXRhOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBFbGVtZW50VmFsaWRhdGlvbk9wdGlvbnNcbiAgKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PiB7XG4gICAgY29uc3QgZXJyb3JzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHdhcm5pbmdzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHN1Z2dlc3Rpb25zOiBzdHJpbmdbXSA9IFtdO1xuXG4gICAgaWYgKCFkYXRhIHx8IHR5cGVvZiBkYXRhICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0RhdGEgbXVzdCBiZSBhIG5vbi1udWxsIG9iamVjdCddKTtcbiAgICB9XG5cbiAgICAvLyBTVEVQIDE6IE5PUk1BTElaRSBhdCB0aGUgYm91bmRhcnkgKGJlZm9yZSBhbnkgdmFsaWRhdGlvbilcbiAgICBjb25zdCBub3JtYWxpemVkID0gSW5wdXROb3JtYWxpemVyLm5vcm1hbGl6ZShkYXRhKTtcblxuICAgIC8vIEZhaWwgZmFzdCBpZiBoaWdoIG9yIGNyaXRpY2FsIFVuaWNvZGUgaXNzdWVzIGRldGVjdGVkXG4gICAgaWYgKG5vcm1hbGl6ZWQuaGFzSGlnaE9yQ3JpdGljYWxJc3N1ZXMpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwobm9ybWFsaXplZC5lcnJvcnMpO1xuICAgIH1cblxuICAgIC8vIEFkZCBub3JtYWxpemF0aW9uIHdhcm5pbmdzIHRvIHJlc3VsdHNcbiAgICB3YXJuaW5ncy5wdXNoKC4uLm5vcm1hbGl6ZWQud2FybmluZ3MpO1xuXG4gICAgLy8gU1RFUCAyOiBWQUxJREFURSB0aGUgbm9ybWFsaXplZCBkYXRhXG4gICAgY29uc3QgcmVjb3JkID0gbm9ybWFsaXplZC5kYXRhIGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuXG4gICAgLy8gVmFsaWRhdGUgbmFtZVxuICAgIGNvbnN0IG5hbWVSZXN1bHQgPSB0aGlzLnZhbGlkYXRlTmFtZShyZWNvcmQubmFtZSk7XG4gICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgIGVycm9ycy5wdXNoKC4uLm5hbWVSZXN1bHQuZXJyb3JzKTtcbiAgICB9XG4gICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcblxuICAgIC8vIFZhbGlkYXRlIGRlc2NyaXB0aW9uXG4gICAgY29uc3QgZGVzY1Jlc3VsdCA9IHRoaXMudmFsaWRhdGVEZXNjcmlwdGlvbihyZWNvcmQuZGVzY3JpcHRpb24pO1xuICAgIGlmICghZGVzY1Jlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICBlcnJvcnMucHVzaCguLi5kZXNjUmVzdWx0LmVycm9ycyk7XG4gICAgfVxuICAgIHdhcm5pbmdzLnB1c2goLi4uZGVzY1Jlc3VsdC53YXJuaW5ncyk7XG5cbiAgICAvLyBWYWxpZGF0ZSBjb250ZW50IGlmIHByZXNlbnRcbiAgICBpZiAocmVjb3JkLmNvbnRlbnQgIT09IHVuZGVmaW5lZCAmJiAhb3B0aW9ucz8uc2tpcENvbnRlbnRWYWxpZGF0aW9uKSB7XG4gICAgICBjb25zdCBjb250ZW50UmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZUNvbnRlbnQoXG4gICAgICAgIHJlY29yZC5jb250ZW50LFxuICAgICAgICBvcHRpb25zPy5tYXhDb250ZW50TGVuZ3RoXG4gICAgICApO1xuICAgICAgaWYgKCFjb250ZW50UmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4uY29udGVudFJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5jb250ZW50UmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICAvLyBGaXggIzkwODogVmFsaWRhdGUgaW5zdHJ1Y3Rpb25zIGZpZWxkIOKAlCBwcmV2aW91c2x5IG9ubHkgY29udGVudCB3YXMgY2hlY2tlZCxcbiAgICAvLyBhbGxvd2luZyBpbmplY3Rpb24gcGF5bG9hZHMgaW4gaW5zdHJ1Y3Rpb25zIHRvIHJlYWNoIGRpc2sgdW5zY2FubmVkLlxuICAgIGlmIChyZWNvcmQuaW5zdHJ1Y3Rpb25zICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgaW5zdHJSZXN1bHQgPSBhd2FpdCB0aGlzLnZhbGlkYXRlQ29udGVudChcbiAgICAgICAgcmVjb3JkLmluc3RydWN0aW9ucyxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghaW5zdHJSZXN1bHQuaXNWYWxpZCkge1xuICAgICAgICBlcnJvcnMucHVzaCguLi5pbnN0clJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5pbnN0clJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgdHJpZ2dlcnMgaWYgcHJlc2VudFxuICAgIGlmIChyZWNvcmQudHJpZ2dlcnMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgY29uc3QgdHJpZ2dlclJlc3VsdCA9IHRoaXMudmFsaWRhdGVUcmlnZ2VycyhcbiAgICAgICAgcmVjb3JkLnRyaWdnZXJzLFxuICAgICAgICBTdHJpbmcocmVjb3JkLm5hbWUgfHwgJ3Vua25vd24nKVxuICAgICAgKTtcbiAgICAgIGlmICghdHJpZ2dlclJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLnRyaWdnZXJSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4udHJpZ2dlclJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gQWRkIHN1Z2dlc3Rpb25zIGZvciBtaXNzaW5nIG9wdGlvbmFsIGZpZWxkc1xuICAgIGlmICghcmVjb3JkLnRyaWdnZXJzIHx8IChBcnJheS5pc0FycmF5KHJlY29yZC50cmlnZ2VycykgJiYgcmVjb3JkLnRyaWdnZXJzLmxlbmd0aCA9PT0gMCkpIHtcbiAgICAgIHN1Z2dlc3Rpb25zLnB1c2goJ0FkZCB0cmlnZ2VyIGtleXdvcmRzIHRvIGltcHJvdmUgZGlzY292ZXJhYmlsaXR5Jyk7XG4gICAgfVxuICAgIGlmICghcmVjb3JkLmF1dGhvcikge1xuICAgICAgc3VnZ2VzdGlvbnMucHVzaCgnQWRkIGFuIGF1dGhvciBmaWVsZCBmb3IgcHJvcGVyIGF0dHJpYnV0aW9uJyk7XG4gICAgfVxuICAgIGlmICghcmVjb3JkLnZlcnNpb24pIHtcbiAgICAgIHN1Z2dlc3Rpb25zLnB1c2goJ0FkZCBhIHZlcnNpb24gbnVtYmVyIGZvciB0cmFja2luZyB1cGRhdGVzJyk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGVycm9ycy5sZW5ndGggPT09IDAsXG4gICAgICBlcnJvcnMsXG4gICAgICB3YXJuaW5ncyxcbiAgICAgIHN1Z2dlc3Rpb25zOiBzdWdnZXN0aW9ucy5sZW5ndGggPiAwID8gc3VnZ2VzdGlvbnMgOiB1bmRlZmluZWRcbiAgICB9O1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGNoYW5nZXMgdG8gYW4gZXhpc3RpbmcgZWxlbWVudFxuICAgKlxuICAgKiBBUkNISVRFQ1RVUkU6IElucHV0IE5vcm1hbGl6YXRpb24gYXQgQm91bmRhcnlcbiAgICogU3RlcCAxOiBOb3JtYWxpemUgQUxMIHN0cmluZyBmaWVsZHMgaW4gY2hhbmdlcyBvYmplY3RcbiAgICogU3RlcCAyOiBWYWxpZGF0ZSB0aGUgbm9ybWFsaXplZCBjaGFuZ2VzXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZUVkaXQoXG4gICAgZWxlbWVudDogdW5rbm93bixcbiAgICBjaGFuZ2VzOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBFbGVtZW50VmFsaWRhdGlvbk9wdGlvbnNcbiAgKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PiB7XG4gICAgY29uc3QgZXJyb3JzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHdhcm5pbmdzOiBzdHJpbmdbXSA9IFtdO1xuXG4gICAgaWYgKCFlbGVtZW50IHx8IHR5cGVvZiBlbGVtZW50ICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0VsZW1lbnQgbXVzdCBiZSBhIG5vbi1udWxsIG9iamVjdCddKTtcbiAgICB9XG5cbiAgICBpZiAoIWNoYW5nZXMgfHwgdHlwZW9mIGNoYW5nZXMgIT09ICdvYmplY3QnKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFsnQ2hhbmdlcyBtdXN0IGJlIGEgbm9uLW51bGwgb2JqZWN0J10pO1xuICAgIH1cblxuICAgIC8vIFNURVAgMTogTk9STUFMSVpFIGNoYW5nZXMgYXQgdGhlIGJvdW5kYXJ5XG4gICAgY29uc3Qgbm9ybWFsaXplZCA9IElucHV0Tm9ybWFsaXplci5ub3JtYWxpemUoY2hhbmdlcyk7XG5cbiAgICAvLyBGYWlsIGZhc3QgaWYgaGlnaCBvciBjcml0aWNhbCBVbmljb2RlIGlzc3VlcyBkZXRlY3RlZFxuICAgIGlmIChub3JtYWxpemVkLmhhc0hpZ2hPckNyaXRpY2FsSXNzdWVzKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKG5vcm1hbGl6ZWQuZXJyb3JzKTtcbiAgICB9XG5cbiAgICAvLyBBZGQgbm9ybWFsaXphdGlvbiB3YXJuaW5ncyB0byByZXN1bHRzXG4gICAgd2FybmluZ3MucHVzaCguLi5ub3JtYWxpemVkLndhcm5pbmdzKTtcblxuICAgIC8vIFNURVAgMjogVkFMSURBVEUgdGhlIG5vcm1hbGl6ZWQgY2hhbmdlc1xuICAgIGNvbnN0IGNoYW5nZVJlY29yZCA9IG5vcm1hbGl6ZWQuZGF0YSBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcblxuICAgIC8vIFZhbGlkYXRlIGVhY2ggY2hhbmdlZCBmaWVsZFxuICAgIGlmIChjaGFuZ2VSZWNvcmQubmFtZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBuYW1lUmVzdWx0ID0gdGhpcy52YWxpZGF0ZU5hbWUoY2hhbmdlUmVjb3JkLm5hbWUpO1xuICAgICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4ubmFtZVJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICBpZiAoY2hhbmdlUmVjb3JkLmRlc2NyaXB0aW9uICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IGRlc2NSZXN1bHQgPSB0aGlzLnZhbGlkYXRlRGVzY3JpcHRpb24oY2hhbmdlUmVjb3JkLmRlc2NyaXB0aW9uKTtcbiAgICAgIGlmICghZGVzY1Jlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLmRlc2NSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4uZGVzY1Jlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgaWYgKGNoYW5nZVJlY29yZC5jb250ZW50ICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgY29udGVudFJlc3VsdCA9IGF3YWl0IHRoaXMudmFsaWRhdGVDb250ZW50KFxuICAgICAgICBjaGFuZ2VSZWNvcmQuY29udGVudCxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghY29udGVudFJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLmNvbnRlbnRSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4uY29udGVudFJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gRml4ICM5MDg6IFZhbGlkYXRlIGluc3RydWN0aW9ucyBvbiBlZGl0IHBhdGggKHNhbWUgZ2FwIGFzIHZhbGlkYXRlQ3JlYXRlKVxuICAgIGlmIChjaGFuZ2VSZWNvcmQuaW5zdHJ1Y3Rpb25zICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgaW5zdHJSZXN1bHQgPSBhd2FpdCB0aGlzLnZhbGlkYXRlQ29udGVudChcbiAgICAgICAgY2hhbmdlUmVjb3JkLmluc3RydWN0aW9ucyxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghaW5zdHJSZXN1bHQuaXNWYWxpZCkge1xuICAgICAgICBlcnJvcnMucHVzaCguLi5pbnN0clJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5pbnN0clJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgaWYgKGNoYW5nZVJlY29yZC50cmlnZ2VycyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBlbGVtZW50UmVjb3JkID0gZWxlbWVudCBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcbiAgICAgIGNvbnN0IHRyaWdnZXJSZXN1bHQgPSB0aGlzLnZhbGlkYXRlVHJpZ2dlcnMoXG4gICAgICAgIGNoYW5nZVJlY29yZC50cmlnZ2VycyxcbiAgICAgICAgU3RyaW5nKGVsZW1lbnRSZWNvcmQubmFtZSB8fCBjaGFuZ2VSZWNvcmQubmFtZSB8fCAndW5rbm93bicpXG4gICAgICApO1xuICAgICAgaWYgKCF0cmlnZ2VyUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4udHJpZ2dlclJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi50cmlnZ2VyUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZXJyb3JzLmxlbmd0aCA9PT0gMCxcbiAgICAgIGVycm9ycyxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBWYWxpZGF0ZSBlbGVtZW50IG1ldGFkYXRhXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZU1ldGFkYXRhKFxuICAgIG1ldGFkYXRhOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBNZXRhZGF0YVZhbGlkYXRpb25PcHRpb25zXG4gICk6IFByb21pc2U8VmFsaWRhdGlvblJlc3VsdD4ge1xuICAgIGNvbnN0IGVycm9yczogc3RyaW5nW10gPSBbXTtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbXTtcblxuICAgIGlmICghbWV0YWRhdGEgfHwgdHlwZW9mIG1ldGFkYXRhICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ01ldGFkYXRhIG11c3QgYmUgYSBub24tbnVsbCBvYmplY3QnXSk7XG4gICAgfVxuXG4gICAgY29uc3QgcmVjb3JkID0gbWV0YWRhdGEgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG5cbiAgICAvLyBDaGVjayByZXF1aXJlZCBmaWVsZHNcbiAgICBjb25zdCByZXF1aXJlZEZpZWxkcyA9IG9wdGlvbnM/LnJlcXVpcmVkRmllbGRzIHx8IFsnbmFtZSddO1xuICAgIGZvciAoY29uc3QgZmllbGQgb2YgcmVxdWlyZWRGaWVsZHMpIHtcbiAgICAgIGlmICghcmVjb3JkW2ZpZWxkXSkge1xuICAgICAgICBlcnJvcnMucHVzaChgUmVxdWlyZWQgZmllbGQgJyR7ZmllbGR9JyBpcyBtaXNzaW5nIG9yIGVtcHR5YCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgZmllbGQgZm9ybWF0c1xuICAgIGlmIChvcHRpb25zPy5mb3JtYXRGaWVsZHMpIHtcbiAgICAgIGZvciAoY29uc3QgW2ZpZWxkLCBwYXR0ZXJuXSBvZiBPYmplY3QuZW50cmllcyhvcHRpb25zLmZvcm1hdEZpZWxkcykpIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSByZWNvcmRbZmllbGRdO1xuICAgICAgICBpZiAodmFsdWUgJiYgdHlwZW9mIHZhbHVlID09PSAnc3RyaW5nJyAmJiAhcGF0dGVybi50ZXN0KHZhbHVlKSkge1xuICAgICAgICAgIGVycm9ycy5wdXNoKGBGaWVsZCAnJHtmaWVsZH0nIGhhcyBpbnZhbGlkIGZvcm1hdGApO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgbWF4IGxlbmd0aHNcbiAgICBpZiAob3B0aW9ucz8ubWF4TGVuZ3Rocykge1xuICAgICAgZm9yIChjb25zdCBbZmllbGQsIG1heExlbmd0aF0gb2YgT2JqZWN0LmVudHJpZXMob3B0aW9ucy5tYXhMZW5ndGhzKSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IHJlY29yZFtmaWVsZF07XG4gICAgICAgIGlmICh2YWx1ZSAmJiB0eXBlb2YgdmFsdWUgPT09ICdzdHJpbmcnICYmIHZhbHVlLmxlbmd0aCA+IG1heExlbmd0aCkge1xuICAgICAgICAgIGVycm9ycy5wdXNoKGBGaWVsZCAnJHtmaWVsZH0nIGV4Y2VlZHMgbWF4aW11bSBsZW5ndGggb2YgJHttYXhMZW5ndGh9IGNoYXJhY3RlcnNgKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIC8vIFN0YW5kYXJkIGZpZWxkIHZhbGlkYXRpb25zXG4gICAgaWYgKHJlY29yZC5uYW1lKSB7XG4gICAgICBjb25zdCBuYW1lUmVzdWx0ID0gdGhpcy52YWxpZGF0ZU5hbWUocmVjb3JkLm5hbWUpO1xuICAgICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4ubmFtZVJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZXJyb3JzLmxlbmd0aCA9PT0gMCxcbiAgICAgIGVycm9ycyxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZW5lcmF0ZSBhIGNvbXByZWhlbnNpdmUgdmFsaWRhdGlvbiByZXBvcnRcbiAgICovXG4gIGFzeW5jIGdlbmVyYXRlUmVwb3J0KGVsZW1lbnQ6IHVua25vd24pOiBQcm9taXNlPFZhbGlkYXRpb25SZXBvcnQ+IHtcbiAgICBjb25zdCBkZXRhaWxzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGxldCBzdGF0dXM6ICdwYXNzJyB8ICdmYWlsJyB8ICd3YXJuaW5nJyA9ICdwYXNzJztcblxuICAgIGlmICghZWxlbWVudCB8fCB0eXBlb2YgZWxlbWVudCAhPT0gJ29iamVjdCcpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIHN0YXR1czogJ2ZhaWwnLFxuICAgICAgICBzdW1tYXJ5OiAnSW52YWxpZCBlbGVtZW50OiBtdXN0IGJlIGEgbm9uLW51bGwgb2JqZWN0JyxcbiAgICAgICAgZGV0YWlsczogWydFbGVtZW50IHZhbGlkYXRpb24gZmFpbGVkIC0gaW52YWxpZCBpbnB1dCB0eXBlJ10sXG4gICAgICAgIHRpbWVzdGFtcDogbmV3IERhdGUoKVxuICAgICAgfTtcbiAgICB9XG5cbiAgICBjb25zdCByZWNvcmQgPSBlbGVtZW50IGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgIGNvbnN0IG1ldGFkYXRhID0gKHJlY29yZC5tZXRhZGF0YSB8fCByZWNvcmQpIGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgIGNvbnN0IGNvbnRlbnQgPSBTdHJpbmcocmVjb3JkLmNvbnRlbnQgfHwgcmVjb3JkLmluc3RydWN0aW9ucyB8fCAnJyk7XG5cbiAgICAvLyBWYWxpZGF0ZSBhbGwgZmllbGRzXG4gICAgY29uc3QgY3JlYXRlUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZUNyZWF0ZSh7XG4gICAgICBuYW1lOiBtZXRhZGF0YS5uYW1lLFxuICAgICAgZGVzY3JpcHRpb246IG1ldGFkYXRhLmRlc2NyaXB0aW9uLFxuICAgICAgY29udGVudCxcbiAgICAgIHRyaWdnZXJzOiBtZXRhZGF0YS50cmlnZ2VycyxcbiAgICAgIGF1dGhvcjogbWV0YWRhdGEuYXV0aG9yLFxuICAgICAgdmVyc2lvbjogbWV0YWRhdGEudmVyc2lvblxuICAgIH0pO1xuXG4gICAgLy8gUHJvY2VzcyB2YWxpZGF0aW9uIHJlc3VsdHNcbiAgICBpZiAoY3JlYXRlUmVzdWx0LmVycm9ycy5sZW5ndGggPiAwKSB7XG4gICAgICBzdGF0dXMgPSAnZmFpbCc7XG4gICAgICBkZXRhaWxzLnB1c2goJ0Vycm9yczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC5lcnJvcnMuZm9yRWFjaCgoZXJyb3IsIGkpID0+IHtcbiAgICAgICAgZGV0YWlscy5wdXNoKGAgICR7aSArIDF9LiAke2Vycm9yfWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgaWYgKGNyZWF0ZVJlc3VsdC53YXJuaW5ncy5sZW5ndGggPiAwKSB7XG4gICAgICBpZiAoc3RhdHVzID09PSAncGFzcycpIHtcbiAgICAgICAgc3RhdHVzID0gJ3dhcm5pbmcnO1xuICAgICAgfVxuICAgICAgZGV0YWlscy5wdXNoKCdXYXJuaW5nczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC53YXJuaW5ncy5mb3JFYWNoKCh3YXJuaW5nLCBpKSA9PiB7XG4gICAgICAgIGRldGFpbHMucHVzaChgICAke2kgKyAxfS4gJHt3YXJuaW5nfWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgaWYgKGNyZWF0ZVJlc3VsdC5zdWdnZXN0aW9ucyAmJiBjcmVhdGVSZXN1bHQuc3VnZ2VzdGlvbnMubGVuZ3RoID4gMCkge1xuICAgICAgZGV0YWlscy5wdXNoKCdTdWdnZXN0aW9uczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC5zdWdnZXN0aW9ucy5mb3JFYWNoKChzdWdnZXN0aW9uLCBpKSA9PiB7XG4gICAgICAgIGRldGFpbHMucHVzaChgICAke2kgKyAxfS4gJHtzdWdnZXN0aW9ufWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgLy8gQ2FsY3VsYXRlIG1ldHJpY3NcbiAgICBjb25zdCB0cmlnZ2VyQ291bnQgPSBBcnJheS5pc0FycmF5KG1ldGFkYXRhLnRyaWdnZXJzKSA/IG1ldGFkYXRhLnRyaWdnZXJzLmxlbmd0aCA6IDA7XG4gICAgY29uc3QgY29udGVudExlbmd0aCA9IGNvbnRlbnQubGVuZ3RoO1xuXG4gICAgLy8gR2VuZXJhdGUgc3VtbWFyeVxuICAgIGxldCBzdW1tYXJ5OiBzdHJpbmc7XG4gICAgaWYgKHN0YXR1cyA9PT0gJ3Bhc3MnKSB7XG4gICAgICBzdW1tYXJ5ID0gYCR7dGhpcy5nZXRFbGVtZW50TGFiZWwoKX0gdmFsaWRhdGlvbiBwYXNzZWQgd2l0aCBubyBpc3N1ZXNgO1xuICAgIH0gZWxzZSBpZiAoc3RhdHVzID09PSAnd2FybmluZycpIHtcbiAgICAgIHN1bW1hcnkgPSBgJHt0aGlzLmdldEVsZW1lbnRMYWJlbCgpfSBpcyB2YWxpZCBidXQgaGFzICR7Y3JlYXRlUmVzdWx0Lndhcm5pbmdzLmxlbmd0aH0gd2FybmluZyhzKWA7XG4gICAgfSBlbHNlIHtcbiAgICAgIHN1bW1hcnkgPSBgJHt0aGlzLmdldEVsZW1lbnRMYWJlbCgpfSB2YWxpZGF0aW9uIGZhaWxlZCB3aXRoICR7Y3JlYXRlUmVzdWx0LmVycm9ycy5sZW5ndGh9IGVycm9yKHMpYDtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgc3RhdHVzLFxuICAgICAgc3VtbWFyeSxcbiAgICAgIGRldGFpbHMsXG4gICAgICB0aW1lc3RhbXA6IG5ldyBEYXRlKCksXG4gICAgICBtZXRyaWNzOiB7XG4gICAgICAgIGNvbnRlbnRMZW5ndGgsXG4gICAgICAgIHRyaWdnZXJDb3VudCxcbiAgICAgICAgcXVhbGl0eVNjb3JlOiB0aGlzLmNhbGN1bGF0ZVF1YWxpdHlTY29yZShtZXRhZGF0YSwgY29udGVudClcbiAgICAgIH1cbiAgICB9O1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGVsZW1lbnQgbmFtZVxuICAgKi9cbiAgcHJvdGVjdGVkIHZhbGlkYXRlTmFtZShuYW1lOiB1bmtub3duKTogVmFsaWRhdGlvblJlc3VsdCB7XG4gICAgaWYgKCFuYW1lIHx8IHR5cGVvZiBuYW1lICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbXCJOYW1lIGlzIHJlcXVpcmVkIGFuZCBtdXN0IGJlIGEgc3RyaW5nXCJdKTtcbiAgICB9XG5cbiAgICBjb25zdCByZXN1bHQgPSB0aGlzLnZhbGlkYXRpb25TZXJ2aWNlLnZhbGlkYXRlQW5kU2FuaXRpemVJbnB1dChuYW1lLCB7XG4gICAgICBtYXhMZW5ndGg6IFNFQ1VSSVRZX0xJTUlUUy5NQVhfTkFNRV9MRU5HVEgsXG4gICAgICBhbGxvd1NwYWNlczogdHJ1ZSxcbiAgICAgIGZpZWxkVHlwZTogJ25hbWUnXG4gICAgfSk7XG5cbiAgICBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKHJlc3VsdC5lcnJvcnMgfHwgWydJbnZhbGlkIG5hbWUnXSk7XG4gICAgfVxuXG4gICAgY29uc3Qgd2FybmluZ3M6IHN0cmluZ1tdID0gW107XG4gICAgaWYgKG5hbWUubGVuZ3RoID4gNTApIHtcbiAgICAgIHdhcm5pbmdzLnB1c2goJ05hbWUgaXMgdmVyeSBsb25nIC0gY29uc2lkZXIgc2hvcnRlbmluZyBmb3IgYmV0dGVyIGRpc3BsYXknKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogdHJ1ZSxcbiAgICAgIGVycm9yczogW10sXG4gICAgICB3YXJuaW5nc1xuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogVmFsaWRhdGUgZWxlbWVudCBkZXNjcmlwdGlvblxuICAgKi9cbiAgcHJvdGVjdGVkIHZhbGlkYXRlRGVzY3JpcHRpb24oZGVzY3JpcHRpb246IHVua25vd24pOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbXTtcblxuICAgIGlmICghZGVzY3JpcHRpb24pIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoW1wiRGVzY3JpcHRpb24gaXMgcmVxdWlyZWRcIl0pO1xuICAgIH1cblxuICAgIGlmICh0eXBlb2YgZGVzY3JpcHRpb24gIT09ICdzdHJpbmcnKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFtcIkRlc2NyaXB0aW9uIG11c3QgYmUgYSBzdHJpbmdcIl0pO1xuICAgIH1cblxuICAgIGNvbnN0IHJlc3VsdCA9IHRoaXMudmFsaWRhdGlvblNlcnZpY2UudmFsaWRhdGVBbmRTYW5pdGl6ZUlucHV0KGRlc2NyaXB0aW9uLCB7XG4gICAgICBtYXhMZW5ndGg6IFNFQ1VSSVRZX0xJTUlUUy5NQVhfREVTQ1JJUFRJT05fTEVOR1RILFxuICAgICAgYWxsb3dTcGFjZXM6IHRydWUsXG4gICAgICBmaWVsZFR5cGU6ICdkZXNjcmlwdGlvbidcbiAgICB9KTtcblxuICAgIGlmICghcmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwocmVzdWx0LmVycm9ycyB8fCBbJ0ludmFsaWQgZGVzY3JpcHRpb24nXSk7XG4gICAgfVxuXG4gICAgaWYgKGRlc2NyaXB0aW9uLmxlbmd0aCA+IDIwMCkge1xuICAgICAgd2FybmluZ3MucHVzaCgnRGVzY3JpcHRpb24gaXMgdmVyeSBsb25nIC0gY29uc2lkZXIga2VlcGluZyBpdCB1bmRlciAyMDAgY2hhcmFjdGVycycpO1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBpc1ZhbGlkOiB0cnVlLFxuICAgICAgZXJyb3JzOiBbXSxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBWYWxpZGF0ZSBlbGVtZW50IGNvbnRlbnRcbiAgICovXG4gIHByb3RlY3RlZCBhc3luYyB2YWxpZGF0ZUNvbnRlbnQoXG4gICAgY29udGVudDogdW5rbm93bixcbiAgICBtYXhMZW5ndGg/OiBudW1iZXJcbiAgKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PiB7XG4gICAgY29uc3Qgd2FybmluZ3M6IHN0cmluZ1tdID0gW107XG4gICAgY29uc3QgbWF4ID0gbWF4TGVuZ3RoIHx8IFNFQ1VSSVRZX0xJTUlUUy5NQVhfQ09OVEVOVF9MRU5HVEg7XG5cbiAgICBpZiAoIWNvbnRlbnQpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoWydDb250ZW50IGlzIHJlcXVpcmVkJ10pO1xuICAgIH1cblxuICAgIGlmICh0eXBlb2YgY29udGVudCAhPT0gJ3N0cmluZycpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoWydDb250ZW50IG11c3QgYmUgYSBzdHJpbmcnXSk7XG4gICAgfVxuXG4gICAgLy8gQ2hlY2sgbWluaW11bSBsZW5ndGhcbiAgICBpZiAoY29udGVudC50cmltKCkubGVuZ3RoIDwgMTApIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoWydDb250ZW50IGlzIHRvbyBzaG9ydCAobWluaW11bSAxMCBjaGFyYWN0ZXJzKSddKTtcbiAgICB9XG5cbiAgICAvLyBVc2UgVmFsaWRhdGlvblNlcnZpY2UgZm9yIGNvbnRlbnQgdmFsaWRhdGlvblxuICAgIGNvbnN0IHJlc3VsdCA9IHRoaXMudmFsaWRhdGlvblNlcnZpY2UudmFsaWRhdGVDb250ZW50KGNvbnRlbnQsIHtcbiAgICAgIG1heExlbmd0aDogbWF4XG4gICAgfSk7XG5cbiAgICBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFxuICAgICAgICByZXN1bHQuZGV0ZWN0ZWRQYXR0ZXJucyB8fCBbJ0NvbnRlbnQgdmFsaWRhdGlvbiBmYWlsZWQnXVxuICAgICAgKTtcbiAgICB9XG5cbiAgICAvLyBDb250ZW50IHF1YWxpdHkgd2FybmluZ3NcbiAgICBpZiAoY29udGVudC5sZW5ndGggPiA1MDAwKSB7XG4gICAgICB3YXJuaW5ncy5wdXNoKCdDb250ZW50IGlzIHZlcnkgbG9uZyAtIGNvbnNpZGVyIGJyZWFraW5nIGl0IGludG8gc2VjdGlvbnMnKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogdHJ1ZSxcbiAgICAgIGVycm9yczogW10sXG4gICAgICB3YXJuaW5nc1xuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogVmFsaWRhdGUgdHJpZ2dlcnMgYXJyYXlcbiAgICovXG4gIHByb3RlY3RlZCB2YWxpZGF0ZVRyaWdnZXJzKHRyaWdnZXJzOiB1bmtub3duLCBlbGVtZW50TmFtZTogc3RyaW5nKTogVmFsaWRhdGlvblJlc3VsdCB7XG4gICAgaWYgKCFBcnJheS5pc0FycmF5KHRyaWdnZXJzKSkge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ1RyaWdnZXJzIG11c3QgYmUgYW4gYXJyYXknXSk7XG4gICAgfVxuXG4gICAgY29uc3QgcmVzdWx0ID0gdGhpcy50cmlnZ2VyVmFsaWRhdGlvblNlcnZpY2UudmFsaWRhdGVUcmlnZ2VycyhcbiAgICAgIHRyaWdnZXJzLFxuICAgICAgdGhpcy5lbGVtZW50VHlwZSxcbiAgICAgIGVsZW1lbnROYW1lXG4gICAgKTtcblxuICAgIGNvbnN0IGVycm9yczogc3RyaW5nW10gPSBbXTtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbLi4ucmVzdWx0Lndhcm5pbmdzXTtcblxuICAgIGlmIChyZXN1bHQuaGFzUmVqZWN0aW9ucykge1xuICAgICAgcmVzdWx0LnJlamVjdGVkVHJpZ2dlcnMuZm9yRWFjaChyZWplY3RlZCA9PiB7XG4gICAgICAgIHdhcm5pbmdzLnB1c2goYFRyaWdnZXIgXCIke3JlamVjdGVkLm9yaWdpbmFsfVwiIHJlamVjdGVkOiAke3JlamVjdGVkLnJlYXNvbn1gKTtcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBpc1ZhbGlkOiBlcnJvcnMubGVuZ3RoID09PSAwLFxuICAgICAgZXJyb3JzLFxuICAgICAgd2FybmluZ3NcbiAgICB9O1xuICB9XG5cbiAgLyoqXG4gICAqIENhbGN1bGF0ZSBhIHF1YWxpdHkgc2NvcmUgZm9yIHRoZSBlbGVtZW50ICgwLTEwMClcbiAgICovXG4gIHByb3RlY3RlZCBjYWxjdWxhdGVRdWFsaXR5U2NvcmUoXG4gICAgbWV0YWRhdGE6IFJlY29yZDxzdHJpbmcsIHVua25vd24+LFxuICAgIGNvbnRlbnQ6IHN0cmluZ1xuICApOiBudW1iZXIge1xuICAgIGxldCBzY29yZSA9IDA7XG5cbiAgICAvLyBOYW1lIHF1YWxpdHkgKDAtMTUgcG9pbnRzKVxuICAgIGlmIChtZXRhZGF0YS5uYW1lICYmIHR5cGVvZiBtZXRhZGF0YS5uYW1lID09PSAnc3RyaW5nJykge1xuICAgICAgc2NvcmUgKz0gMTA7XG4gICAgICBpZiAobWV0YWRhdGEubmFtZS5sZW5ndGggPj0gMyAmJiBtZXRhZGF0YS5uYW1lLmxlbmd0aCA8PSA1MCkge1xuICAgICAgICBzY29yZSArPSA1O1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIERlc2NyaXB0aW9uIHF1YWxpdHkgKDAtMTUgcG9pbnRzKVxuICAgIGlmIChtZXRhZGF0YS5kZXNjcmlwdGlvbiAmJiB0eXBlb2YgbWV0YWRhdGEuZGVzY3JpcHRpb24gPT09ICdzdHJpbmcnKSB7XG4gICAgICBzY29yZSArPSAxMDtcbiAgICAgIGNvbnN0IGRlc2MgPSBtZXRhZGF0YS5kZXNjcmlwdGlvbiBhcyBzdHJpbmc7XG4gICAgICBpZiAoZGVzYy5sZW5ndGggPj0gMjAgJiYgZGVzYy5sZW5ndGggPD0gMjAwKSB7XG4gICAgICAgIHNjb3JlICs9IDU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gQ29udGVudCBxdWFsaXR5ICgwLTMwIHBvaW50cylcbiAgICBpZiAoY29udGVudCkge1xuICAgICAgc2NvcmUgKz0gMTU7XG4gICAgICBpZiAoY29udGVudC5sZW5ndGggPj0gNTApIHtcbiAgICAgICAgc2NvcmUgKz0gMTA7XG4gICAgICB9XG4gICAgICBpZiAoY29udGVudC5sZW5ndGggPD0gNTAwMCkge1xuICAgICAgICBzY29yZSArPSA1O1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIE1ldGFkYXRhIGNvbXBsZXRlbmVzcyAoMC0yMCBwb2ludHMpXG4gICAgaWYgKG1ldGFkYXRhLmF1dGhvcikgc2NvcmUgKz0gNTtcbiAgICBpZiAobWV0YWRhdGEudmVyc2lvbikgc2NvcmUgKz0gNTtcbiAgICBpZiAobWV0YWRhdGEuY2F0ZWdvcnkpIHNjb3JlICs9IDU7XG4gICAgaWYgKG1ldGFkYXRhLmNyZWF0ZWQpIHNjb3JlICs9IDU7XG5cbiAgICAvLyBUcmlnZ2VycyAoMC0yMCBwb2ludHMpXG4gICAgaWYgKEFycmF5LmlzQXJyYXkobWV0YWRhdGEudHJpZ2dlcnMpKSB7XG4gICAgICBjb25zdCB0cmlnZ2VycyA9IG1ldGFkYXRhLnRyaWdnZXJzIGFzIHVua25vd25bXTtcbiAgICAgIGlmICh0cmlnZ2Vycy5sZW5ndGggPiAwKSBzY29yZSArPSAxMDtcbiAgICAgIGlmICh0cmlnZ2Vycy5sZW5ndGggPj0gMykgc2NvcmUgKz0gNTtcbiAgICAgIGlmICh0cmlnZ2Vycy5sZW5ndGggPD0gMTApIHNjb3JlICs9IDU7XG4gICAgfVxuXG4gICAgcmV0dXJuIE1hdGgubWluKDEwMCwgc2NvcmUpO1xuICB9XG5cbiAgLyoqXG4gICAqIEdldCBodW1hbi1yZWFkYWJsZSBsYWJlbCBmb3IgdGhpcyBlbGVtZW50IHR5cGVcbiAgICovXG4gIHByb3RlY3RlZCBnZXRFbGVtZW50TGFiZWwoKTogc3RyaW5nIHtcbiAgICBjb25zdCBsYWJlbHM6IFJlY29yZDxFbGVtZW50VHlwZSwgc3RyaW5nPiA9IHtcbiAgICAgIFtFbGVtZW50VHlwZS5QRVJTT05BXTogJ1BlcnNvbmEnLFxuICAgICAgW0VsZW1lbnRUeXBlLlNLSUxMXTogJ1NraWxsJyxcbiAgICAgIFtFbGVtZW50VHlwZS5URU1QTEFURV06ICdUZW1wbGF0ZScsXG4gICAgICBbRWxlbWVudFR5cGUuQUdFTlRdOiAnQWdlbnQnLFxuICAgICAgW0VsZW1lbnRUeXBlLk1FTU9SWV06ICdNZW1vcnknLFxuICAgICAgW0VsZW1lbnRUeXBlLkVOU0VNQkxFXTogJ0Vuc2VtYmxlJ1xuICAgIH07XG4gICAgcmV0dXJuIGxhYmVsc1t0aGlzLmVsZW1lbnRUeXBlXSB8fCB0aGlzLmVsZW1lbnRUeXBlO1xuICB9XG59XG4iXX0=
484
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiR2VuZXJpY0VsZW1lbnRWYWxpZGF0b3IuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9zcmMvc2VydmljZXMvdmFsaWRhdGlvbi9HZW5lcmljRWxlbWVudFZhbGlkYXRvci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7O0dBU0c7QUFFSCxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFJdkQsT0FBTyxFQUFFLGVBQWUsRUFBRSxNQUFNLDZCQUE2QixDQUFDO0FBQzlELE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxtQ0FBbUMsQ0FBQztBQUNwRSxPQUFPLEVBTUwsZ0JBQWdCLEVBQ2pCLE1BQU0sdUJBQXVCLENBQUM7QUFFL0I7O0dBRUc7QUFDSCxNQUFNLE9BQU8sdUJBQXVCO0lBS3RCO0lBQ0E7SUFDQTtJQU5ILFdBQVcsQ0FBYztJQUVsQyxZQUNFLFdBQXdCLEVBQ2QsaUJBQW9DLEVBQ3BDLHdCQUFrRCxFQUNsRCxlQUFnQztRQUZoQyxzQkFBaUIsR0FBakIsaUJBQWlCLENBQW1CO1FBQ3BDLDZCQUF3QixHQUF4Qix3QkFBd0IsQ0FBMEI7UUFDbEQsb0JBQWUsR0FBZixlQUFlLENBQWlCO1FBRTFDLElBQUksQ0FBQyxXQUFXLEdBQUcsV0FBVyxDQUFDO0lBQ2pDLENBQUM7SUFFRDs7Ozs7Ozs7T0FRRztJQUNILEtBQUssQ0FBQyxjQUFjLENBQ2xCLElBQWEsRUFDYixPQUFrQztRQUVsQyxNQUFNLE1BQU0sR0FBYSxFQUFFLENBQUM7UUFDNUIsTUFBTSxRQUFRLEdBQWEsRUFBRSxDQUFDO1FBQzlCLE1BQU0sV0FBVyxHQUFhLEVBQUUsQ0FBQztRQUVqQyxJQUFJLENBQUMsSUFBSSxJQUFJLE9BQU8sSUFBSSxLQUFLLFFBQVEsRUFBRSxDQUFDO1lBQ3RDLE9BQU8sZ0JBQWdCLENBQUMsSUFBSSxDQUFDLENBQUMsZ0NBQWdDLENBQUMsQ0FBQyxDQUFDO1FBQ25FLENBQUM7UUFFRCw0REFB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LENBQUMsR0FBRyxFQUFFLEtBQUssQ0FBQyxDQUFDO0lBQzlCLENBQUM7SUFFRDs7T0FFRztJQUNPLGVBQWU7UUFDdkIsTUFBTSxNQUFNLEdBQWdDO1lBQzFDLENBQUMsV0FBVyxDQUFDLE9BQU8sQ0FBQyxFQUFFLFNBQVM7WUFDaEMsQ0FBQyxXQUFXLENBQUMsS0FBSyxDQUFDLEVBQUUsT0FBTztZQUM1QixDQUFDLFdBQVcsQ0FBQyxRQUFRLENBQUMsRUFBRSxVQUFVO1lBQ2xDLENBQUMsV0FBVyxDQUFDLEtBQUssQ0FBQyxFQUFFLE9BQU87WUFDNUIsQ0FBQyxXQUFXLENBQUMsTUFBTSxDQUFDLEVBQUUsUUFBUTtZQUM5QixDQUFDLFdBQVcsQ0FBQyxRQUFRLENBQUMsRUFBRSxVQUFVO1NBQ25DLENBQUM7UUFDRixPQUFPLE1BQU0sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLElBQUksSUFBSSxDQUFDLFdBQVcsQ0FBQztJQUN0RCxDQUFDO0NBQ0YiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIEdlbmVyaWNFbGVtZW50VmFsaWRhdG9yIC0gRGVmYXVsdCB2YWxpZGF0b3IgaW1wbGVtZW50YXRpb24gZm9yIG1vc3QgZWxlbWVudCB0eXBlc1xuICpcbiAqIFByb3ZpZGVzIHN0YW5kYXJkIHZhbGlkYXRpb24gbG9naWMgdGhhdCB3b3JrcyBmb3IgYW55IGVsZW1lbnQgdHlwZS5cbiAqIFVzZXMgdGhlIGV4aXN0aW5nIFZhbGlkYXRpb25TZXJ2aWNlIGFuZCBUcmlnZ2VyVmFsaWRhdGlvblNlcnZpY2UgZm9yXG4gKiBjb25zaXN0ZW50IHNlY3VyaXR5LWZpcnN0IHZhbGlkYXRpb24gcGF0dGVybnMuXG4gKlxuICogRWxlbWVudCB0eXBlcyB0aGF0IG5lZWQgc3BlY2lhbGl6ZWQgdmFsaWRhdGlvbiAobGlrZSBwZXJzb25hcykgY2FuXG4gKiBleHRlbmQgdGhpcyBjbGFzcyBvciBpbXBsZW1lbnQgRWxlbWVudFZhbGlkYXRvciBkaXJlY3RseS5cbiAqL1xuXG5pbXBvcnQgeyBFbGVtZW50VHlwZSB9IGZyb20gJy4uLy4uL3BvcnRmb2xpby90eXBlcy5qcyc7XG5pbXBvcnQgeyBWYWxpZGF0aW9uU2VydmljZSwgdHlwZSBWYWxpZGF0aW9uUmVzdWx0IGFzIElucHV0VmFsaWRhdGlvblJlc3VsdCB9IGZyb20gJy4vVmFsaWRhdGlvblNlcnZpY2UuanMnO1xuaW1wb3J0IHsgVHJpZ2dlclZhbGlkYXRpb25TZXJ2aWNlIH0gZnJvbSAnLi9UcmlnZ2VyVmFsaWRhdGlvblNlcnZpY2UuanMnO1xuaW1wb3J0IHsgTWV0YWRhdGFTZXJ2aWNlIH0gZnJvbSAnLi4vTWV0YWRhdGFTZXJ2aWNlLmpzJztcbmltcG9ydCB7IFNFQ1VSSVRZX0xJTUlUUyB9IGZyb20gJy4uLy4uL3NlY3VyaXR5L2NvbnN0YW50cy5qcyc7XG5pbXBvcnQgeyBJbnB1dE5vcm1hbGl6ZXIgfSBmcm9tICcuLi8uLi9zZWN1cml0eS9JbnB1dE5vcm1hbGl6ZXIuanMnO1xuaW1wb3J0IHtcbiAgRWxlbWVudFZhbGlkYXRvcixcbiAgVmFsaWRhdGlvblJlc3VsdCxcbiAgVmFsaWRhdGlvblJlcG9ydCxcbiAgRWxlbWVudFZhbGlkYXRpb25PcHRpb25zLFxuICBNZXRhZGF0YVZhbGlkYXRpb25PcHRpb25zLFxuICBWYWxpZGF0b3JIZWxwZXJzXG59IGZyb20gJy4vRWxlbWVudFZhbGlkYXRvci5qcyc7XG5cbi8qKlxuICogRGVmYXVsdCB2YWxpZGF0b3IgaW1wbGVtZW50YXRpb24gZm9yIG1vc3QgZWxlbWVudCB0eXBlc1xuICovXG5leHBvcnQgY2xhc3MgR2VuZXJpY0VsZW1lbnRWYWxpZGF0b3IgaW1wbGVtZW50cyBFbGVtZW50VmFsaWRhdG9yIHtcbiAgcmVhZG9ubHkgZWxlbWVudFR5cGU6IEVsZW1lbnRUeXBlO1xuXG4gIGNvbnN0cnVjdG9yKFxuICAgIGVsZW1lbnRUeXBlOiBFbGVtZW50VHlwZSxcbiAgICBwcm90ZWN0ZWQgdmFsaWRhdGlvblNlcnZpY2U6IFZhbGlkYXRpb25TZXJ2aWNlLFxuICAgIHByb3RlY3RlZCB0cmlnZ2VyVmFsaWRhdGlvblNlcnZpY2U6IFRyaWdnZXJWYWxpZGF0aW9uU2VydmljZSxcbiAgICBwcm90ZWN0ZWQgbWV0YWRhdGFTZXJ2aWNlOiBNZXRhZGF0YVNlcnZpY2VcbiAgKSB7XG4gICAgdGhpcy5lbGVtZW50VHlwZSA9IGVsZW1lbnRUeXBlO1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGRhdGEgZm9yIGVsZW1lbnQgY3JlYXRpb25cbiAgICpcbiAgICogQVJDSElURUNUVVJFOiBJbnB1dCBOb3JtYWxpemF0aW9uIGF0IEJvdW5kYXJ5XG4gICAqIFN0ZXAgMTogTm9ybWFsaXplIEFMTCBzdHJpbmcgZmllbGRzIChVbmljb2RlLCBjb25mdXNhYmxlcywgZGlyZWN0aW9uIG92ZXJyaWRlcylcbiAgICogU3RlcCAyOiBWYWxpZGF0ZSB0aGUgbm9ybWFsaXplZCBkYXRhIChmaWVsZCBydWxlcywgbGVuZ3RocywgcGF0dGVybnMpXG4gICAqXG4gICAqIFRoaXMgZW5zdXJlcyB3ZSBjYW4ndCBmb3JnZXQgdG8gbm9ybWFsaXplIGEgZmllbGQgLSBpdCBoYXBwZW5zIG9uY2UgYXQgZW50cnkuXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZUNyZWF0ZShcbiAgICBkYXRhOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBFbGVtZW50VmFsaWRhdGlvbk9wdGlvbnNcbiAgKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PiB7XG4gICAgY29uc3QgZXJyb3JzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHdhcm5pbmdzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHN1Z2dlc3Rpb25zOiBzdHJpbmdbXSA9IFtdO1xuXG4gICAgaWYgKCFkYXRhIHx8IHR5cGVvZiBkYXRhICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0RhdGEgbXVzdCBiZSBhIG5vbi1udWxsIG9iamVjdCddKTtcbiAgICB9XG5cbiAgICAvLyBTVEVQIDE6IE5PUk1BTElaRSBhdCB0aGUgYm91bmRhcnkgKGJlZm9yZSBhbnkgdmFsaWRhdGlvbilcbiAgICBjb25zdCBub3JtYWxpemVkID0gSW5wdXROb3JtYWxpemVyLm5vcm1hbGl6ZShkYXRhKTtcblxuICAgIC8vIEZhaWwgZmFzdCBpZiBoaWdoIG9yIGNyaXRpY2FsIFVuaWNvZGUgaXNzdWVzIGRldGVjdGVkXG4gICAgaWYgKG5vcm1hbGl6ZWQuaGFzSGlnaE9yQ3JpdGljYWxJc3N1ZXMpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwobm9ybWFsaXplZC5lcnJvcnMpO1xuICAgIH1cblxuICAgIC8vIEFkZCBub3JtYWxpemF0aW9uIHdhcm5pbmdzIHRvIHJlc3VsdHNcbiAgICB3YXJuaW5ncy5wdXNoKC4uLm5vcm1hbGl6ZWQud2FybmluZ3MpO1xuXG4gICAgLy8gU1RFUCAyOiBWQUxJREFURSB0aGUgbm9ybWFsaXplZCBkYXRhXG4gICAgY29uc3QgcmVjb3JkID0gbm9ybWFsaXplZC5kYXRhIGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuXG4gICAgLy8gVmFsaWRhdGUgbmFtZVxuICAgIGNvbnN0IG5hbWVSZXN1bHQgPSB0aGlzLnZhbGlkYXRlTmFtZShyZWNvcmQubmFtZSk7XG4gICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgIGVycm9ycy5wdXNoKC4uLm5hbWVSZXN1bHQuZXJyb3JzKTtcbiAgICB9XG4gICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcblxuICAgIC8vIFZhbGlkYXRlIGRlc2NyaXB0aW9uXG4gICAgY29uc3QgZGVzY1Jlc3VsdCA9IHRoaXMudmFsaWRhdGVEZXNjcmlwdGlvbihyZWNvcmQuZGVzY3JpcHRpb24pO1xuICAgIGlmICghZGVzY1Jlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICBlcnJvcnMucHVzaCguLi5kZXNjUmVzdWx0LmVycm9ycyk7XG4gICAgfVxuICAgIHdhcm5pbmdzLnB1c2goLi4uZGVzY1Jlc3VsdC53YXJuaW5ncyk7XG5cbiAgICAvLyBWYWxpZGF0ZSBjb250ZW50IGlmIHByZXNlbnRcbiAgICBpZiAocmVjb3JkLmNvbnRlbnQgIT09IHVuZGVmaW5lZCAmJiAhb3B0aW9ucz8uc2tpcENvbnRlbnRWYWxpZGF0aW9uKSB7XG4gICAgICBjb25zdCBjb250ZW50UmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZUNvbnRlbnQoXG4gICAgICAgIHJlY29yZC5jb250ZW50LFxuICAgICAgICBvcHRpb25zPy5tYXhDb250ZW50TGVuZ3RoXG4gICAgICApO1xuICAgICAgaWYgKCFjb250ZW50UmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4uY29udGVudFJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5jb250ZW50UmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICAvLyBGaXggIzkwODogVmFsaWRhdGUgaW5zdHJ1Y3Rpb25zIGZpZWxkIOKAlCBwcmV2aW91c2x5IG9ubHkgY29udGVudCB3YXMgY2hlY2tlZCxcbiAgICAvLyBhbGxvd2luZyBpbmplY3Rpb24gcGF5bG9hZHMgaW4gaW5zdHJ1Y3Rpb25zIHRvIHJlYWNoIGRpc2sgdW5zY2FubmVkLlxuICAgIGlmIChyZWNvcmQuaW5zdHJ1Y3Rpb25zICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgaW5zdHJSZXN1bHQgPSBhd2FpdCB0aGlzLnZhbGlkYXRlQ29udGVudChcbiAgICAgICAgcmVjb3JkLmluc3RydWN0aW9ucyxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghaW5zdHJSZXN1bHQuaXNWYWxpZCkge1xuICAgICAgICBlcnJvcnMucHVzaCguLi5pbnN0clJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5pbnN0clJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgdHJpZ2dlcnMgaWYgcHJlc2VudFxuICAgIGlmIChyZWNvcmQudHJpZ2dlcnMgIT09IHVuZGVmaW5lZCkge1xuICAgICAgY29uc3QgdHJpZ2dlclJlc3VsdCA9IHRoaXMudmFsaWRhdGVUcmlnZ2VycyhcbiAgICAgICAgcmVjb3JkLnRyaWdnZXJzLFxuICAgICAgICBTdHJpbmcocmVjb3JkLm5hbWUgfHwgJ3Vua25vd24nKVxuICAgICAgKTtcbiAgICAgIGlmICghdHJpZ2dlclJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLnRyaWdnZXJSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4udHJpZ2dlclJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gQWRkIHN1Z2dlc3Rpb25zIGZvciBtaXNzaW5nIG9wdGlvbmFsIGZpZWxkc1xuICAgIGlmICghcmVjb3JkLnRyaWdnZXJzIHx8IChBcnJheS5pc0FycmF5KHJlY29yZC50cmlnZ2VycykgJiYgcmVjb3JkLnRyaWdnZXJzLmxlbmd0aCA9PT0gMCkpIHtcbiAgICAgIHN1Z2dlc3Rpb25zLnB1c2goJ0FkZCB0cmlnZ2VyIGtleXdvcmRzIHRvIGltcHJvdmUgZGlzY292ZXJhYmlsaXR5Jyk7XG4gICAgfVxuICAgIGlmICghcmVjb3JkLmF1dGhvcikge1xuICAgICAgc3VnZ2VzdGlvbnMucHVzaCgnQWRkIGFuIGF1dGhvciBmaWVsZCBmb3IgcHJvcGVyIGF0dHJpYnV0aW9uJyk7XG4gICAgfVxuICAgIGlmICghcmVjb3JkLnZlcnNpb24pIHtcbiAgICAgIHN1Z2dlc3Rpb25zLnB1c2goJ0FkZCBhIHZlcnNpb24gbnVtYmVyIGZvciB0cmFja2luZyB1cGRhdGVzJyk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGVycm9ycy5sZW5ndGggPT09IDAsXG4gICAgICBlcnJvcnMsXG4gICAgICB3YXJuaW5ncyxcbiAgICAgIHN1Z2dlc3Rpb25zOiBzdWdnZXN0aW9ucy5sZW5ndGggPiAwID8gc3VnZ2VzdGlvbnMgOiB1bmRlZmluZWRcbiAgICB9O1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGNoYW5nZXMgdG8gYW4gZXhpc3RpbmcgZWxlbWVudFxuICAgKlxuICAgKiBBUkNISVRFQ1RVUkU6IElucHV0IE5vcm1hbGl6YXRpb24gYXQgQm91bmRhcnlcbiAgICogU3RlcCAxOiBOb3JtYWxpemUgQUxMIHN0cmluZyBmaWVsZHMgaW4gY2hhbmdlcyBvYmplY3RcbiAgICogU3RlcCAyOiBWYWxpZGF0ZSB0aGUgbm9ybWFsaXplZCBjaGFuZ2VzXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZUVkaXQoXG4gICAgZWxlbWVudDogdW5rbm93bixcbiAgICBjaGFuZ2VzOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBFbGVtZW50VmFsaWRhdGlvbk9wdGlvbnNcbiAgKTogUHJvbWlzZTxWYWxpZGF0aW9uUmVzdWx0PiB7XG4gICAgY29uc3QgZXJyb3JzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHdhcm5pbmdzOiBzdHJpbmdbXSA9IFtdO1xuXG4gICAgaWYgKCFlbGVtZW50IHx8IHR5cGVvZiBlbGVtZW50ICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0VsZW1lbnQgbXVzdCBiZSBhIG5vbi1udWxsIG9iamVjdCddKTtcbiAgICB9XG5cbiAgICBpZiAoIWNoYW5nZXMgfHwgdHlwZW9mIGNoYW5nZXMgIT09ICdvYmplY3QnKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFsnQ2hhbmdlcyBtdXN0IGJlIGEgbm9uLW51bGwgb2JqZWN0J10pO1xuICAgIH1cblxuICAgIC8vIFNURVAgMTogTk9STUFMSVpFIGNoYW5nZXMgYXQgdGhlIGJvdW5kYXJ5XG4gICAgY29uc3Qgbm9ybWFsaXplZCA9IElucHV0Tm9ybWFsaXplci5ub3JtYWxpemUoY2hhbmdlcyk7XG5cbiAgICAvLyBGYWlsIGZhc3QgaWYgaGlnaCBvciBjcml0aWNhbCBVbmljb2RlIGlzc3VlcyBkZXRlY3RlZFxuICAgIGlmIChub3JtYWxpemVkLmhhc0hpZ2hPckNyaXRpY2FsSXNzdWVzKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKG5vcm1hbGl6ZWQuZXJyb3JzKTtcbiAgICB9XG5cbiAgICAvLyBBZGQgbm9ybWFsaXphdGlvbiB3YXJuaW5ncyB0byByZXN1bHRzXG4gICAgd2FybmluZ3MucHVzaCguLi5ub3JtYWxpemVkLndhcm5pbmdzKTtcblxuICAgIC8vIFNURVAgMjogVkFMSURBVEUgdGhlIG5vcm1hbGl6ZWQgY2hhbmdlc1xuICAgIGNvbnN0IGNoYW5nZVJlY29yZCA9IG5vcm1hbGl6ZWQuZGF0YSBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcblxuICAgIC8vIFZhbGlkYXRlIGVhY2ggY2hhbmdlZCBmaWVsZFxuICAgIGlmIChjaGFuZ2VSZWNvcmQubmFtZSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBuYW1lUmVzdWx0ID0gdGhpcy52YWxpZGF0ZU5hbWUoY2hhbmdlUmVjb3JkLm5hbWUpO1xuICAgICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4ubmFtZVJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICBpZiAoY2hhbmdlUmVjb3JkLmRlc2NyaXB0aW9uICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IGRlc2NSZXN1bHQgPSB0aGlzLnZhbGlkYXRlRGVzY3JpcHRpb24oY2hhbmdlUmVjb3JkLmRlc2NyaXB0aW9uKTtcbiAgICAgIGlmICghZGVzY1Jlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLmRlc2NSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4uZGVzY1Jlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgaWYgKGNoYW5nZVJlY29yZC5jb250ZW50ICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgY29udGVudFJlc3VsdCA9IGF3YWl0IHRoaXMudmFsaWRhdGVDb250ZW50KFxuICAgICAgICBjaGFuZ2VSZWNvcmQuY29udGVudCxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghY29udGVudFJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICAgIGVycm9ycy5wdXNoKC4uLmNvbnRlbnRSZXN1bHQuZXJyb3JzKTtcbiAgICAgIH1cbiAgICAgIHdhcm5pbmdzLnB1c2goLi4uY29udGVudFJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgLy8gRml4ICM5MDg6IFZhbGlkYXRlIGluc3RydWN0aW9ucyBvbiBlZGl0IHBhdGggKHNhbWUgZ2FwIGFzIHZhbGlkYXRlQ3JlYXRlKVxuICAgIGlmIChjaGFuZ2VSZWNvcmQuaW5zdHJ1Y3Rpb25zICE9PSB1bmRlZmluZWQgJiYgIW9wdGlvbnM/LnNraXBDb250ZW50VmFsaWRhdGlvbikge1xuICAgICAgY29uc3QgaW5zdHJSZXN1bHQgPSBhd2FpdCB0aGlzLnZhbGlkYXRlQ29udGVudChcbiAgICAgICAgY2hhbmdlUmVjb3JkLmluc3RydWN0aW9ucyxcbiAgICAgICAgb3B0aW9ucz8ubWF4Q29udGVudExlbmd0aFxuICAgICAgKTtcbiAgICAgIGlmICghaW5zdHJSZXN1bHQuaXNWYWxpZCkge1xuICAgICAgICBlcnJvcnMucHVzaCguLi5pbnN0clJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5pbnN0clJlc3VsdC53YXJuaW5ncyk7XG4gICAgfVxuXG4gICAgaWYgKGNoYW5nZVJlY29yZC50cmlnZ2VycyAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBlbGVtZW50UmVjb3JkID0gZWxlbWVudCBhcyBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcbiAgICAgIGNvbnN0IHRyaWdnZXJSZXN1bHQgPSB0aGlzLnZhbGlkYXRlVHJpZ2dlcnMoXG4gICAgICAgIGNoYW5nZVJlY29yZC50cmlnZ2VycyxcbiAgICAgICAgU3RyaW5nKGVsZW1lbnRSZWNvcmQubmFtZSB8fCBjaGFuZ2VSZWNvcmQubmFtZSB8fCAndW5rbm93bicpXG4gICAgICApO1xuICAgICAgaWYgKCF0cmlnZ2VyUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4udHJpZ2dlclJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi50cmlnZ2VyUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZXJyb3JzLmxlbmd0aCA9PT0gMCxcbiAgICAgIGVycm9ycyxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBWYWxpZGF0ZSBlbGVtZW50IG1ldGFkYXRhXG4gICAqL1xuICBhc3luYyB2YWxpZGF0ZU1ldGFkYXRhKFxuICAgIG1ldGFkYXRhOiB1bmtub3duLFxuICAgIG9wdGlvbnM/OiBNZXRhZGF0YVZhbGlkYXRpb25PcHRpb25zXG4gICk6IFByb21pc2U8VmFsaWRhdGlvblJlc3VsdD4ge1xuICAgIGNvbnN0IGVycm9yczogc3RyaW5nW10gPSBbXTtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbXTtcblxuICAgIGlmICghbWV0YWRhdGEgfHwgdHlwZW9mIG1ldGFkYXRhICE9PSAnb2JqZWN0Jykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ01ldGFkYXRhIG11c3QgYmUgYSBub24tbnVsbCBvYmplY3QnXSk7XG4gICAgfVxuXG4gICAgY29uc3QgcmVjb3JkID0gbWV0YWRhdGEgYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj47XG5cbiAgICAvLyBDaGVjayByZXF1aXJlZCBmaWVsZHNcbiAgICBjb25zdCByZXF1aXJlZEZpZWxkcyA9IG9wdGlvbnM/LnJlcXVpcmVkRmllbGRzIHx8IFsnbmFtZSddO1xuICAgIGZvciAoY29uc3QgZmllbGQgb2YgcmVxdWlyZWRGaWVsZHMpIHtcbiAgICAgIGlmICghcmVjb3JkW2ZpZWxkXSkge1xuICAgICAgICBlcnJvcnMucHVzaChgUmVxdWlyZWQgZmllbGQgJyR7ZmllbGR9JyBpcyBtaXNzaW5nIG9yIGVtcHR5YCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgZmllbGQgZm9ybWF0c1xuICAgIGlmIChvcHRpb25zPy5mb3JtYXRGaWVsZHMpIHtcbiAgICAgIGZvciAoY29uc3QgW2ZpZWxkLCBwYXR0ZXJuXSBvZiBPYmplY3QuZW50cmllcyhvcHRpb25zLmZvcm1hdEZpZWxkcykpIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSByZWNvcmRbZmllbGRdO1xuICAgICAgICBpZiAodmFsdWUgJiYgdHlwZW9mIHZhbHVlID09PSAnc3RyaW5nJyAmJiAhcGF0dGVybi50ZXN0KHZhbHVlKSkge1xuICAgICAgICAgIGVycm9ycy5wdXNoKGBGaWVsZCAnJHtmaWVsZH0nIGhhcyBpbnZhbGlkIGZvcm1hdGApO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gVmFsaWRhdGUgbWF4IGxlbmd0aHNcbiAgICBpZiAob3B0aW9ucz8ubWF4TGVuZ3Rocykge1xuICAgICAgZm9yIChjb25zdCBbZmllbGQsIG1heExlbmd0aF0gb2YgT2JqZWN0LmVudHJpZXMob3B0aW9ucy5tYXhMZW5ndGhzKSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IHJlY29yZFtmaWVsZF07XG4gICAgICAgIGlmICh2YWx1ZSAmJiB0eXBlb2YgdmFsdWUgPT09ICdzdHJpbmcnICYmIHZhbHVlLmxlbmd0aCA+IG1heExlbmd0aCkge1xuICAgICAgICAgIGVycm9ycy5wdXNoKGBGaWVsZCAnJHtmaWVsZH0nIGV4Y2VlZHMgbWF4aW11bSBsZW5ndGggb2YgJHttYXhMZW5ndGh9IGNoYXJhY3RlcnNgKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIC8vIFN0YW5kYXJkIGZpZWxkIHZhbGlkYXRpb25zXG4gICAgaWYgKHJlY29yZC5uYW1lKSB7XG4gICAgICBjb25zdCBuYW1lUmVzdWx0ID0gdGhpcy52YWxpZGF0ZU5hbWUocmVjb3JkLm5hbWUpO1xuICAgICAgaWYgKCFuYW1lUmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgICAgZXJyb3JzLnB1c2goLi4ubmFtZVJlc3VsdC5lcnJvcnMpO1xuICAgICAgfVxuICAgICAgd2FybmluZ3MucHVzaCguLi5uYW1lUmVzdWx0Lndhcm5pbmdzKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogZXJyb3JzLmxlbmd0aCA9PT0gMCxcbiAgICAgIGVycm9ycyxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBHZW5lcmF0ZSBhIGNvbXByZWhlbnNpdmUgdmFsaWRhdGlvbiByZXBvcnRcbiAgICovXG4gIGFzeW5jIGdlbmVyYXRlUmVwb3J0KGVsZW1lbnQ6IHVua25vd24pOiBQcm9taXNlPFZhbGlkYXRpb25SZXBvcnQ+IHtcbiAgICBjb25zdCBkZXRhaWxzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGxldCBzdGF0dXM6ICdwYXNzJyB8ICdmYWlsJyB8ICd3YXJuaW5nJyA9ICdwYXNzJztcblxuICAgIGlmICghZWxlbWVudCB8fCB0eXBlb2YgZWxlbWVudCAhPT0gJ29iamVjdCcpIHtcbiAgICAgIHJldHVybiB7XG4gICAgICAgIHN0YXR1czogJ2ZhaWwnLFxuICAgICAgICBzdW1tYXJ5OiAnSW52YWxpZCBlbGVtZW50OiBtdXN0IGJlIGEgbm9uLW51bGwgb2JqZWN0JyxcbiAgICAgICAgZGV0YWlsczogWydFbGVtZW50IHZhbGlkYXRpb24gZmFpbGVkIC0gaW52YWxpZCBpbnB1dCB0eXBlJ10sXG4gICAgICAgIHRpbWVzdGFtcDogbmV3IERhdGUoKVxuICAgICAgfTtcbiAgICB9XG5cbiAgICBjb25zdCByZWNvcmQgPSBlbGVtZW50IGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgIGNvbnN0IG1ldGFkYXRhID0gKHJlY29yZC5tZXRhZGF0YSB8fCByZWNvcmQpIGFzIFJlY29yZDxzdHJpbmcsIHVua25vd24+O1xuICAgIGNvbnN0IGNvbnRlbnQgPSBTdHJpbmcocmVjb3JkLmNvbnRlbnQgfHwgcmVjb3JkLmluc3RydWN0aW9ucyB8fCAnJyk7XG5cbiAgICAvLyBWYWxpZGF0ZSBhbGwgZmllbGRzXG4gICAgY29uc3QgY3JlYXRlUmVzdWx0ID0gYXdhaXQgdGhpcy52YWxpZGF0ZUNyZWF0ZSh7XG4gICAgICBuYW1lOiBtZXRhZGF0YS5uYW1lLFxuICAgICAgZGVzY3JpcHRpb246IG1ldGFkYXRhLmRlc2NyaXB0aW9uLFxuICAgICAgY29udGVudCxcbiAgICAgIHRyaWdnZXJzOiBtZXRhZGF0YS50cmlnZ2VycyxcbiAgICAgIGF1dGhvcjogbWV0YWRhdGEuYXV0aG9yLFxuICAgICAgdmVyc2lvbjogbWV0YWRhdGEudmVyc2lvblxuICAgIH0pO1xuXG4gICAgLy8gUHJvY2VzcyB2YWxpZGF0aW9uIHJlc3VsdHNcbiAgICBpZiAoY3JlYXRlUmVzdWx0LmVycm9ycy5sZW5ndGggPiAwKSB7XG4gICAgICBzdGF0dXMgPSAnZmFpbCc7XG4gICAgICBkZXRhaWxzLnB1c2goJ0Vycm9yczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC5lcnJvcnMuZm9yRWFjaCgoZXJyb3IsIGkpID0+IHtcbiAgICAgICAgZGV0YWlscy5wdXNoKGAgICR7aSArIDF9LiAke2Vycm9yfWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgaWYgKGNyZWF0ZVJlc3VsdC53YXJuaW5ncy5sZW5ndGggPiAwKSB7XG4gICAgICBpZiAoc3RhdHVzID09PSAncGFzcycpIHtcbiAgICAgICAgc3RhdHVzID0gJ3dhcm5pbmcnO1xuICAgICAgfVxuICAgICAgZGV0YWlscy5wdXNoKCdXYXJuaW5nczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC53YXJuaW5ncy5mb3JFYWNoKCh3YXJuaW5nLCBpKSA9PiB7XG4gICAgICAgIGRldGFpbHMucHVzaChgICAke2kgKyAxfS4gJHt3YXJuaW5nfWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgaWYgKGNyZWF0ZVJlc3VsdC5zdWdnZXN0aW9ucyAmJiBjcmVhdGVSZXN1bHQuc3VnZ2VzdGlvbnMubGVuZ3RoID4gMCkge1xuICAgICAgZGV0YWlscy5wdXNoKCdTdWdnZXN0aW9uczonKTtcbiAgICAgIGNyZWF0ZVJlc3VsdC5zdWdnZXN0aW9ucy5mb3JFYWNoKChzdWdnZXN0aW9uLCBpKSA9PiB7XG4gICAgICAgIGRldGFpbHMucHVzaChgICAke2kgKyAxfS4gJHtzdWdnZXN0aW9ufWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgLy8gQ2FsY3VsYXRlIG1ldHJpY3NcbiAgICBjb25zdCB0cmlnZ2VyQ291bnQgPSBBcnJheS5pc0FycmF5KG1ldGFkYXRhLnRyaWdnZXJzKSA/IG1ldGFkYXRhLnRyaWdnZXJzLmxlbmd0aCA6IDA7XG4gICAgY29uc3QgY29udGVudExlbmd0aCA9IGNvbnRlbnQubGVuZ3RoO1xuXG4gICAgLy8gR2VuZXJhdGUgc3VtbWFyeVxuICAgIGxldCBzdW1tYXJ5OiBzdHJpbmc7XG4gICAgaWYgKHN0YXR1cyA9PT0gJ3Bhc3MnKSB7XG4gICAgICBzdW1tYXJ5ID0gYCR7dGhpcy5nZXRFbGVtZW50TGFiZWwoKX0gdmFsaWRhdGlvbiBwYXNzZWQgd2l0aCBubyBpc3N1ZXNgO1xuICAgIH0gZWxzZSBpZiAoc3RhdHVzID09PSAnd2FybmluZycpIHtcbiAgICAgIHN1bW1hcnkgPSBgJHt0aGlzLmdldEVsZW1lbnRMYWJlbCgpfSBpcyB2YWxpZCBidXQgaGFzICR7Y3JlYXRlUmVzdWx0Lndhcm5pbmdzLmxlbmd0aH0gd2FybmluZyhzKWA7XG4gICAgfSBlbHNlIHtcbiAgICAgIHN1bW1hcnkgPSBgJHt0aGlzLmdldEVsZW1lbnRMYWJlbCgpfSB2YWxpZGF0aW9uIGZhaWxlZCB3aXRoICR7Y3JlYXRlUmVzdWx0LmVycm9ycy5sZW5ndGh9IGVycm9yKHMpYDtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgc3RhdHVzLFxuICAgICAgc3VtbWFyeSxcbiAgICAgIGRldGFpbHMsXG4gICAgICB0aW1lc3RhbXA6IG5ldyBEYXRlKCksXG4gICAgICBtZXRyaWNzOiB7XG4gICAgICAgIGNvbnRlbnRMZW5ndGgsXG4gICAgICAgIHRyaWdnZXJDb3VudCxcbiAgICAgICAgcXVhbGl0eVNjb3JlOiB0aGlzLmNhbGN1bGF0ZVF1YWxpdHlTY29yZShtZXRhZGF0YSwgY29udGVudClcbiAgICAgIH1cbiAgICB9O1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGVsZW1lbnQgbmFtZVxuICAgKi9cbiAgcHJvdGVjdGVkIHZhbGlkYXRlTmFtZShuYW1lOiB1bmtub3duKTogVmFsaWRhdGlvblJlc3VsdCB7XG4gICAgaWYgKCFuYW1lIHx8IHR5cGVvZiBuYW1lICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbXCJOYW1lIGlzIHJlcXVpcmVkIGFuZCBtdXN0IGJlIGEgc3RyaW5nXCJdKTtcbiAgICB9XG5cbiAgICBjb25zdCByZXN1bHQgPSB0aGlzLnZhbGlkYXRpb25TZXJ2aWNlLnZhbGlkYXRlQW5kU2FuaXRpemVJbnB1dChuYW1lLCB7XG4gICAgICBtYXhMZW5ndGg6IFNFQ1VSSVRZX0xJTUlUUy5NQVhfTkFNRV9MRU5HVEgsXG4gICAgICBhbGxvd1NwYWNlczogdHJ1ZSxcbiAgICAgIGZpZWxkVHlwZTogJ25hbWUnXG4gICAgfSk7XG5cbiAgICBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKHJlc3VsdC5lcnJvcnMgfHwgWydJbnZhbGlkIG5hbWUnXSk7XG4gICAgfVxuXG4gICAgY29uc3Qgd2FybmluZ3M6IHN0cmluZ1tdID0gW107XG4gICAgaWYgKG5hbWUubGVuZ3RoID4gNTApIHtcbiAgICAgIHdhcm5pbmdzLnB1c2goJ05hbWUgaXMgdmVyeSBsb25nIC0gY29uc2lkZXIgc2hvcnRlbmluZyBmb3IgYmV0dGVyIGRpc3BsYXknKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogdHJ1ZSxcbiAgICAgIGVycm9yczogW10sXG4gICAgICB3YXJuaW5nc1xuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogVmFsaWRhdGUgZWxlbWVudCBkZXNjcmlwdGlvblxuICAgKi9cbiAgcHJvdGVjdGVkIHZhbGlkYXRlRGVzY3JpcHRpb24oZGVzY3JpcHRpb246IHVua25vd24pOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbXTtcblxuICAgIGlmICghZGVzY3JpcHRpb24pIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoW1wiRGVzY3JpcHRpb24gaXMgcmVxdWlyZWRcIl0pO1xuICAgIH1cblxuICAgIGlmICh0eXBlb2YgZGVzY3JpcHRpb24gIT09ICdzdHJpbmcnKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFtcIkRlc2NyaXB0aW9uIG11c3QgYmUgYSBzdHJpbmdcIl0pO1xuICAgIH1cblxuICAgIGlmIChkZXNjcmlwdGlvbi5sZW5ndGggPiBTRUNVUklUWV9MSU1JVFMuTUFYX0RFU0NSSVBUSU9OX0xFTkdUSCkge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbXG4gICAgICAgIGBEZXNjcmlwdGlvbiBleGNlZWRzIG1heGltdW0gbGVuZ3RoIG9mICR7U0VDVVJJVFlfTElNSVRTLk1BWF9ERVNDUklQVElPTl9MRU5HVEh9IGNoYXJhY3RlcnNgXG4gICAgICBdKTtcbiAgICB9XG5cbiAgICBjb25zdCByZXN1bHQgPSB0aGlzLnNhbml0aXplRGVzY3JpcHRpb25JbnB1dChkZXNjcmlwdGlvbik7XG5cbiAgICBpZiAoIXJlc3VsdC5pc1ZhbGlkKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKHJlc3VsdC5lcnJvcnMgfHwgWydJbnZhbGlkIGRlc2NyaXB0aW9uJ10pO1xuICAgIH1cblxuICAgIGlmIChkZXNjcmlwdGlvbi5sZW5ndGggPiAyMDApIHtcbiAgICAgIHdhcm5pbmdzLnB1c2goJ0Rlc2NyaXB0aW9uIGlzIHZlcnkgbG9uZyAtIGNvbnNpZGVyIGtlZXBpbmcgaXQgdW5kZXIgMjAwIGNoYXJhY3RlcnMnKTtcbiAgICB9XG5cbiAgICByZXR1cm4ge1xuICAgICAgaXNWYWxpZDogdHJ1ZSxcbiAgICAgIGVycm9yczogW10sXG4gICAgICB3YXJuaW5nc1xuICAgIH07XG4gIH1cblxuICBwcml2YXRlIHNhbml0aXplRGVzY3JpcHRpb25JbnB1dChkZXNjcmlwdGlvbjogc3RyaW5nKTogSW5wdXRWYWxpZGF0aW9uUmVzdWx0IHtcbiAgICByZXR1cm4gdGhpcy52YWxpZGF0aW9uU2VydmljZS52YWxpZGF0ZUFuZFNhbml0aXplSW5wdXQoZGVzY3JpcHRpb24sIHtcbiAgICAgIG1heExlbmd0aDogU0VDVVJJVFlfTElNSVRTLk1BWF9ERVNDUklQVElPTl9MRU5HVEgsXG4gICAgICBhbGxvd1NwYWNlczogdHJ1ZSxcbiAgICAgIGZpZWxkVHlwZTogJ2Rlc2NyaXB0aW9uJ1xuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIFZhbGlkYXRlIGVsZW1lbnQgY29udGVudFxuICAgKi9cbiAgcHJvdGVjdGVkIGFzeW5jIHZhbGlkYXRlQ29udGVudChcbiAgICBjb250ZW50OiB1bmtub3duLFxuICAgIG1heExlbmd0aD86IG51bWJlclxuICApOiBQcm9taXNlPFZhbGlkYXRpb25SZXN1bHQ+IHtcbiAgICBjb25zdCB3YXJuaW5nczogc3RyaW5nW10gPSBbXTtcbiAgICBjb25zdCBtYXggPSBtYXhMZW5ndGggfHwgU0VDVVJJVFlfTElNSVRTLk1BWF9DT05URU5UX0xFTkdUSDtcblxuICAgIGlmICghY29udGVudCkge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0NvbnRlbnQgaXMgcmVxdWlyZWQnXSk7XG4gICAgfVxuXG4gICAgaWYgKHR5cGVvZiBjb250ZW50ICE9PSAnc3RyaW5nJykge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0NvbnRlbnQgbXVzdCBiZSBhIHN0cmluZyddKTtcbiAgICB9XG5cbiAgICAvLyBDaGVjayBtaW5pbXVtIGxlbmd0aFxuICAgIGlmIChjb250ZW50LnRyaW0oKS5sZW5ndGggPCAxMCkge1xuICAgICAgcmV0dXJuIFZhbGlkYXRvckhlbHBlcnMuZmFpbChbJ0NvbnRlbnQgaXMgdG9vIHNob3J0IChtaW5pbXVtIDEwIGNoYXJhY3RlcnMpJ10pO1xuICAgIH1cblxuICAgIC8vIFVzZSBWYWxpZGF0aW9uU2VydmljZSBmb3IgY29udGVudCB2YWxpZGF0aW9uXG4gICAgY29uc3QgcmVzdWx0ID0gdGhpcy52YWxpZGF0aW9uU2VydmljZS52YWxpZGF0ZUNvbnRlbnQoY29udGVudCwge1xuICAgICAgbWF4TGVuZ3RoOiBtYXhcbiAgICB9KTtcblxuICAgIGlmICghcmVzdWx0LmlzVmFsaWQpIHtcbiAgICAgIHJldHVybiBWYWxpZGF0b3JIZWxwZXJzLmZhaWwoXG4gICAgICAgIHJlc3VsdC5kZXRlY3RlZFBhdHRlcm5zIHx8IFsnQ29udGVudCB2YWxpZGF0aW9uIGZhaWxlZCddXG4gICAgICApO1xuICAgIH1cblxuICAgIC8vIENvbnRlbnQgcXVhbGl0eSB3YXJuaW5nc1xuICAgIGlmIChjb250ZW50Lmxlbmd0aCA+IDUwMDApIHtcbiAgICAgIHdhcm5pbmdzLnB1c2goJ0NvbnRlbnQgaXMgdmVyeSBsb25nIC0gY29uc2lkZXIgYnJlYWtpbmcgaXQgaW50byBzZWN0aW9ucycpO1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBpc1ZhbGlkOiB0cnVlLFxuICAgICAgZXJyb3JzOiBbXSxcbiAgICAgIHdhcm5pbmdzXG4gICAgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiBWYWxpZGF0ZSB0cmlnZ2VycyBhcnJheVxuICAgKi9cbiAgcHJvdGVjdGVkIHZhbGlkYXRlVHJpZ2dlcnModHJpZ2dlcnM6IHVua25vd24sIGVsZW1lbnROYW1lOiBzdHJpbmcpOiBWYWxpZGF0aW9uUmVzdWx0IHtcbiAgICBpZiAoIUFycmF5LmlzQXJyYXkodHJpZ2dlcnMpKSB7XG4gICAgICByZXR1cm4gVmFsaWRhdG9ySGVscGVycy5mYWlsKFsnVHJpZ2dlcnMgbXVzdCBiZSBhbiBhcnJheSddKTtcbiAgICB9XG5cbiAgICBjb25zdCByZXN1bHQgPSB0aGlzLnRyaWdnZXJWYWxpZGF0aW9uU2VydmljZS52YWxpZGF0ZVRyaWdnZXJzKFxuICAgICAgdHJpZ2dlcnMsXG4gICAgICB0aGlzLmVsZW1lbnRUeXBlLFxuICAgICAgZWxlbWVudE5hbWVcbiAgICApO1xuXG4gICAgY29uc3QgZXJyb3JzOiBzdHJpbmdbXSA9IFtdO1xuICAgIGNvbnN0IHdhcm5pbmdzOiBzdHJpbmdbXSA9IFsuLi5yZXN1bHQud2FybmluZ3NdO1xuXG4gICAgaWYgKHJlc3VsdC5oYXNSZWplY3Rpb25zKSB7XG4gICAgICByZXN1bHQucmVqZWN0ZWRUcmlnZ2Vycy5mb3JFYWNoKHJlamVjdGVkID0+IHtcbiAgICAgICAgd2FybmluZ3MucHVzaChgVHJpZ2dlciBcIiR7cmVqZWN0ZWQub3JpZ2luYWx9XCIgcmVqZWN0ZWQ6ICR7cmVqZWN0ZWQucmVhc29ufWApO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgcmV0dXJuIHtcbiAgICAgIGlzVmFsaWQ6IGVycm9ycy5sZW5ndGggPT09IDAsXG4gICAgICBlcnJvcnMsXG4gICAgICB3YXJuaW5nc1xuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogQ2FsY3VsYXRlIGEgcXVhbGl0eSBzY29yZSBmb3IgdGhlIGVsZW1lbnQgKDAtMTAwKVxuICAgKi9cbiAgcHJvdGVjdGVkIGNhbGN1bGF0ZVF1YWxpdHlTY29yZShcbiAgICBtZXRhZGF0YTogUmVjb3JkPHN0cmluZywgdW5rbm93bj4sXG4gICAgY29udGVudDogc3RyaW5nXG4gICk6IG51bWJlciB7XG4gICAgbGV0IHNjb3JlID0gMDtcblxuICAgIC8vIE5hbWUgcXVhbGl0eSAoMC0xNSBwb2ludHMpXG4gICAgaWYgKG1ldGFkYXRhLm5hbWUgJiYgdHlwZW9mIG1ldGFkYXRhLm5hbWUgPT09ICdzdHJpbmcnKSB7XG4gICAgICBzY29yZSArPSAxMDtcbiAgICAgIGlmIChtZXRhZGF0YS5uYW1lLmxlbmd0aCA+PSAzICYmIG1ldGFkYXRhLm5hbWUubGVuZ3RoIDw9IDUwKSB7XG4gICAgICAgIHNjb3JlICs9IDU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gRGVzY3JpcHRpb24gcXVhbGl0eSAoMC0xNSBwb2ludHMpXG4gICAgaWYgKG1ldGFkYXRhLmRlc2NyaXB0aW9uICYmIHR5cGVvZiBtZXRhZGF0YS5kZXNjcmlwdGlvbiA9PT0gJ3N0cmluZycpIHtcbiAgICAgIHNjb3JlICs9IDEwO1xuICAgICAgY29uc3QgZGVzYyA9IG1ldGFkYXRhLmRlc2NyaXB0aW9uIGFzIHN0cmluZztcbiAgICAgIGlmIChkZXNjLmxlbmd0aCA+PSAyMCAmJiBkZXNjLmxlbmd0aCA8PSAyMDApIHtcbiAgICAgICAgc2NvcmUgKz0gNTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvLyBDb250ZW50IHF1YWxpdHkgKDAtMzAgcG9pbnRzKVxuICAgIGlmIChjb250ZW50KSB7XG4gICAgICBzY29yZSArPSAxNTtcbiAgICAgIGlmIChjb250ZW50Lmxlbmd0aCA+PSA1MCkge1xuICAgICAgICBzY29yZSArPSAxMDtcbiAgICAgIH1cbiAgICAgIGlmIChjb250ZW50Lmxlbmd0aCA8PSA1MDAwKSB7XG4gICAgICAgIHNjb3JlICs9IDU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gTWV0YWRhdGEgY29tcGxldGVuZXNzICgwLTIwIHBvaW50cylcbiAgICBpZiAobWV0YWRhdGEuYXV0aG9yKSBzY29yZSArPSA1O1xuICAgIGlmIChtZXRhZGF0YS52ZXJzaW9uKSBzY29yZSArPSA1O1xuICAgIGlmIChtZXRhZGF0YS5jYXRlZ29yeSkgc2NvcmUgKz0gNTtcbiAgICBpZiAobWV0YWRhdGEuY3JlYXRlZCkgc2NvcmUgKz0gNTtcblxuICAgIC8vIFRyaWdnZXJzICgwLTIwIHBvaW50cylcbiAgICBpZiAoQXJyYXkuaXNBcnJheShtZXRhZGF0YS50cmlnZ2VycykpIHtcbiAgICAgIGNvbnN0IHRyaWdnZXJzID0gbWV0YWRhdGEudHJpZ2dlcnMgYXMgdW5rbm93bltdO1xuICAgICAgaWYgKHRyaWdnZXJzLmxlbmd0aCA+IDApIHNjb3JlICs9IDEwO1xuICAgICAgaWYgKHRyaWdnZXJzLmxlbmd0aCA+PSAzKSBzY29yZSArPSA1O1xuICAgICAgaWYgKHRyaWdnZXJzLmxlbmd0aCA8PSAxMCkgc2NvcmUgKz0gNTtcbiAgICB9XG5cbiAgICByZXR1cm4gTWF0aC5taW4oMTAwLCBzY29yZSk7XG4gIH1cblxuICAvKipcbiAgICogR2V0IGh1bWFuLXJlYWRhYmxlIGxhYmVsIGZvciB0aGlzIGVsZW1lbnQgdHlwZVxuICAgKi9cbiAgcHJvdGVjdGVkIGdldEVsZW1lbnRMYWJlbCgpOiBzdHJpbmcge1xuICAgIGNvbnN0IGxhYmVsczogUmVjb3JkPEVsZW1lbnRUeXBlLCBzdHJpbmc+ID0ge1xuICAgICAgW0VsZW1lbnRUeXBlLlBFUlNPTkFdOiAnUGVyc29uYScsXG4gICAgICBbRWxlbWVudFR5cGUuU0tJTExdOiAnU2tpbGwnLFxuICAgICAgW0VsZW1lbnRUeXBlLlRFTVBMQVRFXTogJ1RlbXBsYXRlJyxcbiAgICAgIFtFbGVtZW50VHlwZS5BR0VOVF06ICdBZ2VudCcsXG4gICAgICBbRWxlbWVudFR5cGUuTUVNT1JZXTogJ01lbW9yeScsXG4gICAgICBbRWxlbWVudFR5cGUuRU5TRU1CTEVdOiAnRW5zZW1ibGUnXG4gICAgfTtcbiAgICByZXR1cm4gbGFiZWxzW3RoaXMuZWxlbWVudFR5cGVdIHx8IHRoaXMuZWxlbWVudFR5cGU7XG4gIH1cbn1cbiJdfQ==
@@ -2006,6 +2006,9 @@ globalThis.DollhouseConsoleUI.clearBanner = function(bannerId) {
2006
2006
 
2007
2007
  // ── Tab switching ─────────────────────────────────────────────────────────
2008
2008
  const consoleTabs = document.getElementById('console-tabs');
2009
+ const headerNavRow = document.querySelector('.header-nav-row');
2010
+ const consoleTabMenuToggle = document.getElementById('console-tab-menu-toggle');
2011
+ const consoleTabMenu = document.getElementById('console-tab-menu');
2009
2012
  const tabInits = { logs: false, metrics: false, permissions: false, security: false };
2010
2013
 
2011
2014
  const TAB_KEY = 'dollhousemcp-active-tab';
@@ -2090,8 +2093,157 @@ globalThis.DollhouseConsoleUI.clearBanner = function(bannerId) {
2090
2093
  p.hidden = p.id !== 'tab-' + tabName;
2091
2094
  p.classList.toggle('active', p.id === 'tab-' + tabName);
2092
2095
  });
2096
+ syncConsoleTabMenuSelection();
2097
+ closeConsoleTabMenu();
2098
+ scheduleConsoleTabOverflowCheck();
2093
2099
  };
2094
2100
 
2101
+ function renderConsoleTabMenu() {
2102
+ if (!consoleTabs || !consoleTabMenu) return;
2103
+ consoleTabMenu.innerHTML = '';
2104
+ consoleTabs.querySelectorAll('.console-tab').forEach((btn) => {
2105
+ const item = document.createElement('button');
2106
+ item.type = 'button';
2107
+ item.className = 'console-tab-menu-item';
2108
+ item.dataset.tab = btn.dataset.tab || '';
2109
+ item.setAttribute('role', 'menuitem');
2110
+ item.textContent = btn.textContent || '';
2111
+ if (btn.classList.contains('active')) item.classList.add('active');
2112
+ consoleTabMenu.appendChild(item);
2113
+ });
2114
+ }
2115
+
2116
+ function syncConsoleTabMenuSelection() {
2117
+ if (!consoleTabs || !consoleTabMenu) return;
2118
+ const activeTab = consoleTabs.querySelector('.console-tab.active')?.dataset.tab || '';
2119
+ consoleTabMenu.querySelectorAll('.console-tab-menu-item').forEach((item) => {
2120
+ item.classList.toggle('active', item.dataset.tab === activeTab);
2121
+ });
2122
+ }
2123
+
2124
+ function closeConsoleTabMenu() {
2125
+ if (!consoleTabMenu || !consoleTabMenuToggle) return;
2126
+ consoleTabMenu.hidden = true;
2127
+ consoleTabMenuToggle.setAttribute('aria-expanded', 'false');
2128
+ }
2129
+
2130
+ function getConsoleTabMenuItems() {
2131
+ if (!consoleTabMenu) return [];
2132
+ return Array.from(consoleTabMenu.querySelectorAll('.console-tab-menu-item'));
2133
+ }
2134
+
2135
+ function openConsoleTabMenu(focusTarget) {
2136
+ if (!consoleTabMenu || !consoleTabMenuToggle) return;
2137
+ consoleTabMenu.hidden = false;
2138
+ consoleTabMenuToggle.setAttribute('aria-expanded', 'true');
2139
+
2140
+ if (!focusTarget) return;
2141
+
2142
+ const items = getConsoleTabMenuItems();
2143
+ if (!items.length) return;
2144
+ const focusItem = (index) => {
2145
+ const boundedIndex = Math.max(0, Math.min(index, items.length - 1));
2146
+ items[boundedIndex].focus();
2147
+ };
2148
+
2149
+ if (focusTarget === 'first') {
2150
+ focusItem(0);
2151
+ return;
2152
+ }
2153
+
2154
+ if (focusTarget === 'last') {
2155
+ focusItem(items.length - 1);
2156
+ return;
2157
+ }
2158
+
2159
+ const activeIndex = Math.max(items.findIndex((item) => item.classList.contains('active')), 0);
2160
+ focusItem(activeIndex);
2161
+ }
2162
+
2163
+ function moveConsoleTabMenuFocus(step, origin) {
2164
+ const items = getConsoleTabMenuItems();
2165
+ if (!items.length) return;
2166
+
2167
+ const currentIndex = origin instanceof Element
2168
+ ? items.findIndex((item) => item === origin || item.contains(origin))
2169
+ : -1;
2170
+ const activeIndex = Math.max(items.findIndex((item) => item.classList.contains('active')), 0);
2171
+ const baseIndex = currentIndex >= 0 ? currentIndex : activeIndex;
2172
+ const nextIndex = (baseIndex + step + items.length) % items.length;
2173
+ items[nextIndex].focus();
2174
+ }
2175
+
2176
+ function handleConsoleTabMenuToggleKeydown(event) {
2177
+ if (event.key === 'ArrowDown') {
2178
+ event.preventDefault();
2179
+ openConsoleTabMenu('first');
2180
+ } else if (event.key === 'ArrowUp') {
2181
+ event.preventDefault();
2182
+ openConsoleTabMenu('last');
2183
+ }
2184
+ }
2185
+
2186
+ function handleConsoleTabMenuKeydown(event) {
2187
+ switch (event.key) {
2188
+ case 'ArrowDown':
2189
+ event.preventDefault();
2190
+ moveConsoleTabMenuFocus(1, event.target);
2191
+ break;
2192
+ case 'ArrowUp':
2193
+ event.preventDefault();
2194
+ moveConsoleTabMenuFocus(-1, event.target);
2195
+ break;
2196
+ case 'Home':
2197
+ event.preventDefault();
2198
+ getConsoleTabMenuItems()[0]?.focus();
2199
+ break;
2200
+ case 'End': {
2201
+ event.preventDefault();
2202
+ const items = getConsoleTabMenuItems();
2203
+ items.at(-1)?.focus();
2204
+ break;
2205
+ }
2206
+ case 'Escape':
2207
+ event.preventDefault();
2208
+ closeConsoleTabMenu();
2209
+ consoleTabMenuToggle?.focus();
2210
+ break;
2211
+ default:
2212
+ break;
2213
+ }
2214
+ }
2215
+
2216
+ function tabsNeedOverflowMenu() {
2217
+ if (!consoleTabs) return false;
2218
+ const buttons = Array.from(consoleTabs.querySelectorAll('.console-tab'));
2219
+ if (buttons.length < 2) return false;
2220
+ const firstTop = buttons[0].offsetTop;
2221
+ return buttons.some((btn) => btn.offsetTop !== firstTop);
2222
+ }
2223
+
2224
+ let consoleTabOverflowFrame = 0;
2225
+ function updateConsoleTabOverflow() {
2226
+ if (!consoleTabs || !headerNavRow || !consoleTabMenuToggle) return;
2227
+ headerNavRow.classList.remove('header-nav-row--collapsed');
2228
+ consoleTabMenuToggle.hidden = true;
2229
+ const shouldCollapse = tabsNeedOverflowMenu();
2230
+ if (shouldCollapse) {
2231
+ headerNavRow.classList.add('header-nav-row--collapsed');
2232
+ consoleTabMenuToggle.hidden = false;
2233
+ }
2234
+ if (!shouldCollapse) {
2235
+ closeConsoleTabMenu();
2236
+ }
2237
+ }
2238
+
2239
+ function scheduleConsoleTabOverflowCheck() {
2240
+ if (consoleTabOverflowFrame) cancelAnimationFrame(consoleTabOverflowFrame);
2241
+ consoleTabOverflowFrame = requestAnimationFrame(() => {
2242
+ consoleTabOverflowFrame = 0;
2243
+ updateConsoleTabOverflow();
2244
+ });
2245
+ }
2246
+
2095
2247
  /**
2096
2248
  * Parse the URL hash into tab name and query parameters.
2097
2249
  * Supports fragment-query pattern: #tab?key=value&key=value
@@ -2208,26 +2360,41 @@ globalThis.DollhouseConsoleUI.clearBanner = function(bannerId) {
2208
2360
  return false;
2209
2361
  }
2210
2362
 
2211
- if (!applyHashTab()) {
2363
+ function restoreInitialConsoleTab() {
2212
2364
  // Version check takes priority over saved tab — upgraders must see Setup
2213
2365
  // regardless of whether they have a saved tab from their previous session.
2214
2366
  if (localStorage.getItem(SETUP_SEEN_KEY) === currentServerVersion) {
2215
2367
  const savedTab = localStorage.getItem(TAB_KEY);
2216
- if (savedTab) {
2217
- switchToTab(savedTab);
2218
- lazyInitTab(savedTab, tabInits);
2219
- }
2220
- } else {
2221
- localStorage.setItem(SETUP_SEEN_KEY, currentServerVersion);
2222
- switchToTab('setup');
2368
+ if (!savedTab) return;
2369
+ switchToTab(savedTab);
2370
+ lazyInitTab(savedTab, tabInits);
2371
+ return;
2223
2372
  }
2373
+
2374
+ localStorage.setItem(SETUP_SEEN_KEY, currentServerVersion);
2375
+ switchToTab('setup');
2376
+ }
2377
+
2378
+ function initializeConsoleTabs() {
2379
+ if (applyHashTab()) return;
2380
+ restoreInitialConsoleTab();
2224
2381
  }
2225
2382
 
2226
- // Handle hash changes for deep-linking (e.g., open_logs operation)
2227
- globalThis.addEventListener('hashchange', () => applyHashTab());
2383
+ function registerConsoleTabObservers() {
2384
+ globalThis.addEventListener('hashchange', () => applyHashTab());
2385
+ renderConsoleTabMenu();
2386
+ syncConsoleTabMenuSelection();
2387
+ scheduleConsoleTabOverflowCheck();
2388
+ globalThis.addEventListener('resize', scheduleConsoleTabOverflowCheck);
2389
+
2390
+ if (typeof ResizeObserver !== 'function' || !headerNavRow) return;
2228
2391
 
2229
- if (consoleTabs) {
2230
- consoleTabs.addEventListener('click', (e) => {
2392
+ const tabOverflowObserver = new ResizeObserver(() => scheduleConsoleTabOverflowCheck());
2393
+ tabOverflowObserver.observe(headerNavRow);
2394
+ }
2395
+
2396
+ function registerConsoleTabInteractions() {
2397
+ consoleTabs?.addEventListener('click', (e) => {
2231
2398
  const btn = e.target.closest('.console-tab');
2232
2399
  if (!btn) return;
2233
2400
  const tab = btn.dataset.tab;
@@ -2238,8 +2405,42 @@ globalThis.DollhouseConsoleUI.clearBanner = function(bannerId) {
2238
2405
 
2239
2406
  lazyInitTab(tab, tabInits);
2240
2407
  });
2408
+
2409
+ consoleTabMenuToggle?.addEventListener('click', () => {
2410
+ if (!consoleTabMenu) return;
2411
+ if (consoleTabMenu.hidden) {
2412
+ openConsoleTabMenu();
2413
+ return;
2414
+ }
2415
+
2416
+ closeConsoleTabMenu();
2417
+ });
2418
+
2419
+ consoleTabMenuToggle?.addEventListener('keydown', handleConsoleTabMenuToggleKeydown);
2420
+ consoleTabMenu?.addEventListener('keydown', handleConsoleTabMenuKeydown);
2421
+ consoleTabMenu?.addEventListener('click', (e) => {
2422
+ const btn = e.target.closest('.console-tab-menu-item');
2423
+ const tab = btn?.dataset.tab;
2424
+ if (!tab) return;
2425
+ switchToTab(tab);
2426
+ localStorage.setItem(TAB_KEY, tab);
2427
+ lazyInitTab(tab, tabInits);
2428
+ });
2429
+
2430
+ globalThis.addEventListener('click', (e) => {
2431
+ if (!consoleTabMenu || !consoleTabMenuToggle) return;
2432
+ if (consoleTabMenu.hidden) return;
2433
+ const target = e.target;
2434
+ if (!(target instanceof Element)) return;
2435
+ if (consoleTabMenu.contains(target) || consoleTabMenuToggle.contains(target)) return;
2436
+ closeConsoleTabMenu();
2437
+ });
2241
2438
  }
2242
2439
 
2440
+ initializeConsoleTabs();
2441
+ registerConsoleTabObservers();
2442
+ registerConsoleTabInteractions();
2443
+
2243
2444
  function lazyInitTab(tab, tabInits, params) {
2244
2445
  const dc = globalThis.DollhouseConsole;
2245
2446
  const module = dc?.[tab];
@@ -43,7 +43,14 @@
43
43
  <p class="site-tagline">Management Console</p>
44
44
  </div>
45
45
  </div>
46
- <div class="header-right">
46
+ <div class="header-controls">
47
+ <div class="site-stats" id="stats" aria-live="polite"></div>
48
+ <button class="theme-toggle" id="theme-toggle" type="button" aria-label="Switch to dark mode" title="Switch to dark mode">
49
+ <span class="theme-toggle-icon" id="theme-toggle-icon" aria-hidden="true">&#9790;</span>
50
+ <span class="sr-only" id="theme-toggle-label">Switch to dark mode</span>
51
+ </button>
52
+ </div>
53
+ <div class="header-nav-row">
47
54
  <nav class="console-tabs" id="console-tabs" aria-label="Console tabs">
48
55
  <button class="console-tab" data-tab="setup">Setup</button>
49
56
  <button class="console-tab" data-tab="security">Auth</button>
@@ -52,12 +59,14 @@
52
59
  <button class="console-tab" data-tab="permissions">Permissions</button>
53
60
  <button class="console-tab active" data-tab="portfolio">Portfolio</button>
54
61
  </nav>
62
+ <div class="console-tab-menu-shell" id="console-tab-menu-shell">
63
+ <button class="console-tab-menu-toggle" id="console-tab-menu-toggle" type="button" hidden aria-haspopup="menu" aria-expanded="false" aria-controls="console-tab-menu">
64
+ <span class="console-tab-menu-icon" aria-hidden="true">&#9776;</span>
65
+ <span class="console-tab-menu-label">Menu</span>
66
+ </button>
67
+ <div class="console-tab-menu" id="console-tab-menu" role="menu" aria-orientation="vertical" hidden></div>
68
+ </div>
55
69
  <div class="session-indicator" id="session-indicator" title="Active sessions"></div>
56
- <div class="site-stats" id="stats" aria-live="polite"></div>
57
- <button class="theme-toggle" id="theme-toggle" type="button" aria-label="Switch to dark mode" title="Switch to dark mode">
58
- <span class="theme-toggle-icon" id="theme-toggle-icon" aria-hidden="true">&#9790;</span>
59
- <span class="sr-only" id="theme-toggle-label">Switch to dark mode</span>
60
- </button>
61
70
  </div>
62
71
  </header>
63
72
 
@@ -572,7 +581,7 @@ npm install @dollhousemcp/mcp-server</code></pre>
572
581
  <a href="https://github.com/DollhouseMCP/mcp-server" class="footer-link">GitHub Repository</a>
573
582
  <a href="./collection-index.json" class="footer-link">JSON API</a>
574
583
  <a href="https://dollhousemcp.com" class="footer-link">DollhouseMCP</a>
575
- <span class="footer-version" id="footer-version"></span>
584
+ <span class="footer-version" id="footer-version" aria-live="polite" aria-atomic="true"></span>
576
585
  <span class="footer-updated" id="footer-updated"></span>
577
586
  <span class="footer-copyright">&copy; 2026 DollhouseMCP</span>
578
587
  </div>