From 770bfd29654adfe438e2043f3ea41e862350e04a Mon Sep 17 00:00:00 2001 From: lowlighter <22963968+lowlighter@users.noreply.github.com> Date: Fri, 6 Nov 2020 21:40:24 +0100 Subject: [PATCH] Update definitions --- .github/workflows/build.yml | 9 + README.md | 27 +- action/dist/index.js | 94582 +--------------------------------- package-lock.json | 223 +- package.json | 2 +- 5 files changed, 180 insertions(+), 94663 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 7b47d2aa..1b202cdb 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -160,3 +160,12 @@ jobs: plugins_errors_fatal: yes dryrun: yes + - name: Gists plugin + uses: lowlighter/metrics@master + with: + token: ${{ secrets.METRICS_TOKEN }} + base: "" + repositories: 1 + plugin_gists: yes + plugins_errors_fatal: yes + dryrun: yes diff --git a/README.md b/README.md index 281d3d2b..8763cbd8 100644 --- a/README.md +++ b/README.md @@ -14,9 +14,9 @@ But there's more with [plugins](https://github.com/lowlighter/metrics/tree/maste | **Most used languages plugin** | **Follow-up plugin** | **Coding Habits plugin** | |[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.languages.svg)|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.followup.svg)|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.habits.svg)| | **Repositories traffic plugin** | **Lines of code plugin** | **Recent posts plugin** | -|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.traffic.svg)|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.lines.svg)| [](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.posts.svg) | -| **Isometric calendar plugin** | | -|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.isocalendar.svg) | More to come soon ! | +|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.traffic.svg)|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.lines.svg)| [](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.posts.svg)| +| **Isometric calendar plugin** | **Gists metrics** | | +|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.isocalendar.svg)|[](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.gists.svg)| More to come soon ! | | Classic template | Terminal template | | | :----------------: | :----------------: | :----------------: | @@ -677,6 +677,27 @@ Add the following to your workflow : +#### 🎫 Gists + +The *gists* plugin allows you to display [gists](https://gist.github.com) metrics. + +![Gists plugin](https://github.com/lowlighter/lowlighter/blob/master/metrics.plugin.gists.svg) + +
+💬 About + +It will consume an additional GitHub request per gist fetched. + +Add the following to your workflow : +```yaml +- uses: lowlighter/metrics@latest + with: + # ... other options + plugin_gists: yes +``` + +
+ #### ⏭️ Selfskip The *selfskip* plugin allows you to count out all commits tagged with `[Skip GitHub Action]` you authored on your personal repository from your reported commit counts. diff --git a/action/dist/index.js b/action/dist/index.js index 24d32b6d..582c49a1 100644 --- a/action/dist/index.js +++ b/action/dist/index.js @@ -1,238 +1,25 @@ -module.exports = -/******/ (() => { // webpackBootstrap -/******/ var __webpack_modules__ = ({ - -/***/ 3709: -/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => { - -"use strict"; -// ESM COMPAT FLAG -__webpack_require__.r(__webpack_exports__); - -// NAMESPACE OBJECT: E:\Users\lecoq\Documents\GitHub\gitstats\src\setup.mjs -var E_Users_lecoq_Documents_GitHub_gitstats_src_setup_namespaceObject = {}; -__webpack_require__.r(E_Users_lecoq_Documents_GitHub_gitstats_src_setup_namespaceObject); -__webpack_require__.d(E_Users_lecoq_Documents_GitHub_gitstats_src_setup_namespaceObject, { - "default": () => E_Users_lecoq_Documents_GitHub_gitstats_src_setup -}); - -// NAMESPACE OBJECT: E:\Users\lecoq\Documents\GitHub\gitstats\src\metrics.mjs -var E_Users_lecoq_Documents_GitHub_gitstats_src_metrics_namespaceObject = {}; -__webpack_require__.r(E_Users_lecoq_Documents_GitHub_gitstats_src_metrics_namespaceObject); -__webpack_require__.d(E_Users_lecoq_Documents_GitHub_gitstats_src_metrics_namespaceObject, { - "default": () => metrics -}); - -// EXTERNAL MODULE: external "fs" -var external_fs_ = __webpack_require__(35747); -var external_fs_default = /*#__PURE__*/__webpack_require__.n(external_fs_); - -// EXTERNAL MODULE: external "path" -var external_path_ = __webpack_require__(85622); -var external_path_default = /*#__PURE__*/__webpack_require__.n(external_path_); - -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\setup.mjs -//Imports - - - -/** Setup */ - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_setup({log = true} = {}) { - - //Init - const logger = log ? console.debug : () => null - logger(`metrics/setup > setup`) - const templates = "src/templates" - const conf = { - templates:{}, - settings:{}, - statics:__webpack_require__.ab + "html", - node_modules:external_path_default().resolve("node_modules"), - } - - //Load settings - logger(`metrics/setup > load settings.json`) - if (external_fs_default().existsSync(__webpack_require__.ab + "settings.json")) { - conf.settings = JSON.parse(`${await external_fs_default().promises.readFile(external_path_default().resolve("settings.json"))}`) - logger(`metrics/setup > load settings.json > success`) - } - else - logger(`metrics/setup > load settings.json > (missing)`) - if (!conf.settings.templates) - conf.settings.templates = {default:"classic", enabled:[]} - if (!conf.settings.plugins) - conf.settings.plugins = {} - conf.settings.plugins.base = {parts:["header", "activity", "community", "repositories", "metadata"]} - if (conf.settings.debug) - logger(conf.settings) - - //Load package settings - logger(`metrics/setup > load package.json`) - if (external_fs_default().existsSync(__webpack_require__.ab + "package.json")) { - conf.package = JSON.parse(`${await external_fs_default().promises.readFile(external_path_default().resolve("package.json"))}`) - logger(`metrics/setup > load package.json > success`) - } - else { - logger(`metrics/setup > load package.json > (missing)`) - conf.package = {version:"2.3.0", author:"lowlighter"} - } - - //Load templates - if (external_fs_default().existsSync(__webpack_require__.ab + "templates")) { - for (const name of await external_fs_default().promises.readdir(templates)) { - //Cache templates - if (/.*[.]mjs$/.test(name)) - continue - logger(`metrics/setup > load template [${name}]`) - const files = [ - `${templates}/${name}/query.graphql`, - `${templates}/${name}/image.svg`, - `${templates}/${name}/style.css`, - `${templates}/${name}/fonts.css`, - ] - const [query, image, style, fonts] = await Promise.all(files.map(async file => `${await external_fs_default().promises.readFile(external_path_default().resolve(file))}`)) - conf.templates[name] = {query, image, style, fonts} - logger(`metrics/setup > load template [${name}] > success`) - //Debug - if (conf.settings.debug) { - Object.defineProperty(conf.templates, name, { - get() { - logger(`metrics/setup > reload template [${name}]`) - const [query, image, style, fonts] = files.map(file => `${external_fs_default().readFileSync(external_path_default().resolve(file))}`) - logger(`metrics/setup > reload template [${name}] > success`) - return {query, image, style, fonts} +module.exports=(()=>{var _Mathhypot=Math.hypot,_Mathacos=Math.acos,_Mathtan=Math.tan,_Mathasin=Math.asin,_Mathsin=Math.sin,_Mathcos=Math.cos,_MathPI=Math.PI,_Mathsqrt=Math.sqrt,_NumberisInteger=Number.isInteger,_NumberPOSITIVE_INFINITY=Number.POSITIVE_INFINITY,_NumberNEGATIVE_INFINITY=Number.NEGATIVE_INFINITY,_NumberMAX_SAFE_INTEGER=Number.MAX_SAFE_INTEGER,_Stringprototype=String.prototype,_Mathround=Math.round,_StringfromCharCode=String.fromCharCode,_Mathabs=Math.abs,_Mathpow=Math.pow,_Mathceil=Math.ceil,_Mathfloor=Math.floor,_Mathmax=Math.max,_Mathmin=Math.min;function __webpack_require__(e){if(__webpack_module_cache__[e])return __webpack_module_cache__[e].exports;var t=__webpack_module_cache__[e]={exports:{}},r=!0;try{__webpack_modules__[e].call(t.exports,t,t.exports,__webpack_require__),r=!1}finally{r&&delete __webpack_module_cache__[e]}return t.exports}var __webpack_modules__={27584:(e,t,r)=>{"use strict";async function n({log:e=!0}={}){const t=e?console.debug:()=>null;t(`metrics/setup > setup`);const n="src/templates",a={templates:{},settings:{},statics:r.ab+"html",node_modules:h.resolve("node_modules")};if(t(`metrics/setup > load settings.json`),g.existsSync(r.ab+"settings.json")?(a.settings=JSON.parse(`${await g.promises.readFile(h.resolve("settings.json"))}`),t(`metrics/setup > load settings.json > success`)):t(`metrics/setup > load settings.json > (missing)`),a.settings.templates||(a.settings.templates={default:"classic",enabled:[]}),a.settings.plugins||(a.settings.plugins={}),a.settings.plugins.base={parts:["header","activity","community","repositories","metadata"]},a.settings.debug&&t(a.settings),t(`metrics/setup > load package.json`),g.existsSync(r.ab+"package.json")?(a.package=JSON.parse(`${await g.promises.readFile(h.resolve("package.json"))}`),t(`metrics/setup > load package.json > success`)):(t(`metrics/setup > load package.json > (missing)`),a.package={version:"2.4.0",author:"lowlighter"}),g.existsSync(r.ab+"templates"))for(const e of await g.promises.readdir(n)){if(/.*[.]mjs$/.test(e))continue;t(`metrics/setup > load template [${e}]`);const r=[`${n}/${e}/query.graphql`,`${n}/${e}/image.svg`,`${n}/${e}/style.css`,`${n}/${e}/fonts.css`],[o,i,s,l]=await Promise.all(r.map(async e=>`${await g.promises.readFile(h.resolve(e))}`));a.templates[e]={query:o,image:i,style:s,fonts:l},t(`metrics/setup > load template [${e}] > success`),a.settings.debug&&Object.defineProperty(a.templates,e,{get(){t(`metrics/setup > reload template [${e}]`);const[n,a,o,i]=r.map(e=>`${g.readFileSync(h.resolve(e))}`);return t(`metrics/setup > reload template [${e}] > success`),{query:n,image:a,style:o,fonts:i}}})}else t(`metrics/setup > load templates from build`),a.templates=JSON.parse(Buffer.from(`eyJjbGFzc2ljIjp7InF1ZXJ5IjoicXVlcnkgTWV0cmljcyB7XHJcbiAgdXNlcihsb2dpbjogJGxvZ2luKSB7XHJcbiAgICBkYXRhYmFzZUlkXHJcbiAgICBuYW1lXHJcbiAgICBsb2dpblxyXG4gICAgY3JlYXRlZEF0XHJcbiAgICBhdmF0YXJVcmxcclxuICAgIHdlYnNpdGVVcmxcclxuICAgIGdpc3RzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgcmVwb3NpdG9yaWVzKGxhc3Q6ICRyZXBvc2l0b3JpZXMsIGlzRm9yazogZmFsc2UsIG93bmVyQWZmaWxpYXRpb25zOiBPV05FUikge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICAgIHRvdGFsRGlza1VzYWdlXHJcbiAgICAgIG5vZGVzIHtcclxuICAgICAgICBuYW1lXHJcbiAgICAgICAgd2F0Y2hlcnMge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBzdGFyZ2F6ZXJzIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgbGFuZ3VhZ2VzKGZpcnN0OiA0KSB7XHJcbiAgICAgICAgICBlZGdlcyB7XHJcbiAgICAgICAgICAgIHNpemVcclxuICAgICAgICAgICAgbm9kZSB7XHJcbiAgICAgICAgICAgICAgY29sb3JcclxuICAgICAgICAgICAgICBuYW1lXHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgIH1cclxuICAgICAgICB9XHJcbiAgICAgICAgaXNzdWVzX29wZW46IGlzc3VlcyhzdGF0ZXM6IE9QRU4pIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgaXNzdWVzX2Nsb3NlZDogaXNzdWVzKHN0YXRlczogQ0xPU0VEKSB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHByX29wZW46IHB1bGxSZXF1ZXN0cyhzdGF0ZXM6IE9QRU4pIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgcHJfbWVyZ2VkOiBwdWxsUmVxdWVzdHMoc3RhdGVzOiBNRVJHRUQpIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgcmVsZWFzZXMge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBmb3JrQ291bnRcclxuICAgICAgICBsaWNlbnNlSW5mbyB7XHJcbiAgICAgICAgICBzcGR4SWRcclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIHBhY2thZ2VzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3RhcnJlZFJlcG9zaXRvcmllcyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHdhdGNoaW5nIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3BvbnNvcnNoaXBzQXNTcG9uc29yIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3BvbnNvcnNoaXBzQXNNYWludGFpbmVyIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgY29udHJpYnV0aW9uc0NvbGxlY3Rpb24ge1xyXG4gICAgICB0b3RhbFJlcG9zaXRvcmllc1dpdGhDb250cmlidXRlZENvbW1pdHNcclxuICAgICAgdG90YWxDb21taXRDb250cmlidXRpb25zXHJcbiAgICAgIHJlc3RyaWN0ZWRDb250cmlidXRpb25zQ291bnRcclxuICAgICAgdG90YWxJc3N1ZUNvbnRyaWJ1dGlvbnNcclxuICAgICAgdG90YWxQdWxsUmVxdWVzdENvbnRyaWJ1dGlvbnNcclxuICAgICAgdG90YWxQdWxsUmVxdWVzdFJldmlld0NvbnRyaWJ1dGlvbnNcclxuICAgIH1cclxuICAgIGNhbGVuZGFyOmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uKGZyb206ICRjYWxlbmRhci5mcm9tLCB0bzogJGNhbGVuZGFyLnRvKSB7XHJcbiAgICAgIGNvbnRyaWJ1dGlvbkNhbGVuZGFyIHtcclxuICAgICAgICB3ZWVrcyB7XHJcbiAgICAgICAgICBjb250cmlidXRpb25EYXlzIHtcclxuICAgICAgICAgICAgY29sb3JcclxuICAgICAgICAgIH1cclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIHJlcG9zaXRvcmllc0NvbnRyaWJ1dGVkVG8ge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBmb2xsb3dlcnMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBmb2xsb3dpbmcge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBpc3N1ZUNvbW1lbnRzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgb3JnYW5pemF0aW9ucyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICB9XHJcbn1cclxuIiwiaW1hZ2UiOiI8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB3aWR0aD1cIjQ4MFwiIGhlaWdodD1cIjwlPSAxMlxyXG4gICsgKCEhYmFzZS5oZWFkZXIpKjgwXHJcbiAgKyAoISFiYXNlLm1ldGFkYXRhKSozOFxyXG4gICsgKCghIWJhc2UuYWN0aXZpdHkpfHwoISFiYXNlLmNvbW11bml0eSkpKjEyOFxyXG4gICsgKCEhYmFzZS5yZXBvc2l0b3JpZXMpKjEwOFxyXG4gICsgKCghIWJhc2UucmVwb3NpdG9yaWVzKSooKCEhY29tcHV0ZWQucGx1Z2lucy50cmFmZmljKXx8KCEhY29tcHV0ZWQucGx1Z2lucy5saW5lcykpKSoxNlxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cCkqNjhcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkKSoxMjZcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzKSo2OFxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMpKjk2XHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLm11c2ljKSo2NCArIChjb21wdXRlZC5wbHVnaW5zLm11c2ljID8gY29tcHV0ZWQucGx1Z2lucy5tdXNpYy50cmFja3MgPyAxNCtNYXRoLm1heCgwLCBjb21wdXRlZC5wbHVnaW5zLm11c2ljLnRyYWNrcy5sZW5ndGgtMSkqMzYgOiAwIDogMClcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMucG9zdHMpKjY0ICsgKGNvbXB1dGVkLnBsdWdpbnMucG9zdHMgPyBjb21wdXRlZC5wbHVnaW5zLnBvc3RzLnBvc3RzID8gTWF0aC5tYXgoMCwgY29tcHV0ZWQucGx1Z2lucy5wb3N0cy5wb3N0cy5sZW5ndGgpKjQwIDogMCA6IDApXHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyKSoxODBcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMpKjY4XHJcbiAgKyBNYXRoLm1heCgwLCAoKCghIWJhc2UubWV0YWRhdGEpKyghIWJhc2UuaGVhZGVyKSsoKCEhYmFzZS5hY3Rpdml0eSl8fCghIWJhc2UuY29tbXVuaXR5KSkrKCEhYmFzZS5yZXBvc2l0b3JpZXMpKygoISFjb21wdXRlZC5wbHVnaW5zLmhhYml0cykpKyghIWNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkKSsoISFjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcykrKCEhY29tcHV0ZWQucGx1Z2lucy5tdXNpYykrKCEhY29tcHV0ZWQucGx1Z2lucy5wb3N0cykrKCEhY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhcikrKCEhY29tcHV0ZWQucGx1Z2lucy5naXN0cykpLTEpKSo0XHJcbiU+XCI+XHJcblxyXG4gIDxkZWZzPjxzdHlsZT48JT0gZm9udHMgJT48L3N0eWxlPjwvZGVmcz5cclxuXHJcbiAgPHN0eWxlPlxyXG4gICAgPCU9IHN0eWxlICU+XHJcbiAgPC9zdHlsZT5cclxuXHJcbiAgPGZvcmVpZ25PYmplY3QgeD1cIjBcIiB5PVwiMFwiIHdpZHRoPVwiMTAwJVwiIGhlaWdodD1cIjEwMCVcIj5cclxuICAgIDxkaXYgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sXCIgeG1sbnM6eGxpbms9XCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rXCI+XHJcblxyXG4gICAgICA8JSBpZiAoYmFzZS5oZWFkZXIpIHsgJT5cclxuICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgIDxoMSBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgIDxpbWcgY2xhc3M9XCJhdmF0YXJcIiBzcmM9XCJkYXRhOmltYWdlL3BuZztiYXNlNjQsPCU9IGNvbXB1dGVkLmF2YXRhciAlPlwiIHdpZHRoPVwiMjBcIiBoZWlnaHQ9XCIyMFwiIC8+XHJcbiAgICAgICAgICAgIDxzcGFuPjwlPSB1c2VyLm5hbWUgfHwgdXNlci5sb2dpbiAlPjwvc3Bhbj5cclxuICAgICAgICAgIDwvaDE+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwicm93XCI+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNSA4YTYuNSA2LjUgMCAxMTEzIDAgNi41IDYuNSAwIDAxLTEzIDB6TTggMGE4IDggMCAxMDAgMTZBOCA4IDAgMDA4IDB6bS41IDQuNzVhLjc1Ljc1IDAgMDAtMS41IDB2My41YS43NS43NSAwIDAwLjQ3MS42OTZsMi41IDFhLjc1Ljc1IDAgMDAuNTU3LTEuMzkyTDguNSA3Ljc0MlY0Ljc1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIEpvaW5lZCBHaXRIdWIgPCU9IGNvbXB1dGVkLnJlZ2lzdHJhdGlvbiAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTUuNSAzLjVhMiAyIDAgMTAwIDQgMiAyIDAgMDAwLTR6TTIgNS41YTMuNSAzLjUgMCAxMTUuODk4IDIuNTQ5IDUuNTA3IDUuNTA3IDAgMDEzLjAzNCA0LjA4NC43NS43NSAwIDExLTEuNDgyLjIzNSA0LjAwMSA0LjAwMSAwIDAwLTcuOSAwIC43NS43NSAwIDAxLTEuNDgyLS4yMzZBNS41MDcgNS41MDcgMCAwMTMuMTAyIDguMDUgMy40OSAzLjQ5IDAgMDEyIDUuNXpNMTEgNGEuNzUuNzUgMCAxMDAgMS41IDEuNSAxLjUgMCAwMS42NjYgMi44NDQuNzUuNzUgMCAwMC0uNDE2LjY3MnYuMzUyYS43NS43NSAwIDAwLjU3NC43M2MxLjIuMjg5IDIuMTYyIDEuMiAyLjUyMiAyLjM3MmEuNzUuNzUgMCAxMDEuNDM0LS40NCA1LjAxIDUuMDEgMCAwMC0yLjU2LTMuMDEyQTMgMyAwIDAwMTEgNHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICBGb2xsb3dlZCBieSA8JT0gdXNlci5mb2xsb3dlcnMudG90YWxDb3VudCAlPiB1c2VyPCU9IHModXNlci5mb2xsb3dlcnMudG90YWxDb3VudCkgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgY2FsZW5kYXJcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgPCU9IGNvbXB1dGVkLmNhbGVuZGFyLmxlbmd0aCoxNSAlPiAxMVwiIHdpZHRoPVwiPCU9IGNvbXB1dGVkLmNhbGVuZGFyLmxlbmd0aCoxNSAlPlwiIGhlaWdodD1cIjE2XCI+XHJcbiAgICAgICAgICAgICAgICAgIDxnPlxyXG4gICAgICAgICAgICAgICAgICAgIDwlIGZvciAoY29uc3QgW3gsIHtjb2xvcn1dIG9mIE9iamVjdC5lbnRyaWVzKGNvbXB1dGVkLmNhbGVuZGFyKSkgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPHJlY3QgY2xhc3M9XCJkYXlcIiB4PVwiPCU9IHgqMTUgJT5cIiB5PVwiMFwiIHdpZHRoPVwiMTFcIiBoZWlnaHQ9XCIxMVwiIGZpbGw9XCI8JT0gY29sb3IgJT5cIiByeD1cIjJcIiByeT1cIjJcIiAvPlxyXG4gICAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgICAgPC9nPlxyXG4gICAgICAgICAgICAgICAgPC9zdmc+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMSAyLjVBMi41IDIuNSAwIDAxMy41IDBoOC43NWEuNzUuNzUgMCAwMS43NS43NXYzLjVhLjc1Ljc1IDAgMDEtMS41IDBWMS41aC04YTEgMSAwIDAwLTEgMXY2LjcwOEEyLjQ5MiAyLjQ5MiAwIDAxMy41IDloMy4yNWEuNzUuNzUgMCAwMTAgMS41SDMuNWExIDEgMCAxMDAgMmg1Ljc1YS43NS43NSAwIDAxMCAxLjVIMy41QTIuNSAyLjUgMCAwMTEgMTEuNXYtOXptMTMuMjMgNy43OWEuNzUuNzUgMCAwMDEuMDYtMS4wNmwtMi41MDUtMi41MDVhLjc1Ljc1IDAgMDAtMS4wNiAwTDkuMjIgOS4yMjlhLjc1Ljc1IDAgMDAxLjA2IDEuMDYxbDEuMjI1LTEuMjI0djYuMTg0YS43NS43NSAwIDAwMS41IDBWOS4wNjZsMS4yMjQgMS4yMjR6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgQ29udHJpYnV0ZWQgdG8gPCU9IHVzZXIucmVwb3NpdG9yaWVzQ29udHJpYnV0ZWRUby50b3RhbENvdW50ICU+IHJlcG9zaXRvcjwlPSBzKHVzZXIucmVwb3NpdG9yaWVzQ29udHJpYnV0ZWRUby50b3RhbENvdW50LCBcInlcIikgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICA8JSB9ICU+XHJcblxyXG4gICAgICA8ZGl2IGNsYXNzPVwicm93XCI+XHJcbiAgICAgICAgPCUgaWYgKGJhc2UuYWN0aXZpdHkpIHsgJT5cclxuICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjUgMS43NWEuNzUuNzUgMCAwMC0xLjUgMHYxMi41YzAgLjQxNC4zMzYuNzUuNzUuNzVoMTQuNWEuNzUuNzUgMCAwMDAtMS41SDEuNVYxLjc1em0xNC4yOCAyLjUzYS43NS43NSAwIDAwLTEuMDYtMS4wNkwxMCA3Ljk0IDcuNTMgNS40N2EuNzUuNzUgMCAwMC0xLjA2IDBMMy4yMiA4LjcyYS43NS43NSAwIDAwMS4wNiAxLjA2TDcgNy4wNmwyLjQ3IDIuNDdhLjc1Ljc1IDAgMDAxLjA2IDBsNS4yNS01LjI1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICBBY3Rpdml0eVxyXG4gICAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMTAuNSA3Ljc1YTIuNSAyLjUgMCAxMS01IDAgMi41IDIuNSAwIDAxNSAwem0xLjQzLjc1YTQuMDAyIDQuMDAyIDAgMDEtNy44NiAwSC43NWEuNzUuNzUgMCAxMTAtMS41aDMuMzJhNC4wMDEgNC4wMDEgMCAwMTcuODYgMGgzLjMyYS43NS43NSAwIDExMCAxLjVoLTMuMzJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5jb21taXRzICU+IENvbW1pdDwlPSBzKGNvbXB1dGVkLmNvbW1pdHMpICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi41IDEuNzVhLjI1LjI1IDAgMDEuMjUtLjI1aDguNWEuMjUuMjUgMCAwMS4yNS4yNXY3LjczNmEuNzUuNzUgMCAxMDEuNSAwVjEuNzVBMS43NSAxLjc1IDAgMDAxMS4yNSAwaC04LjVBMS43NSAxLjc1IDAgMDAxIDEuNzV2MTEuNWMwIC45NjYuNzg0IDEuNzUgMS43NSAxLjc1aDMuMTdhLjc1Ljc1IDAgMDAwLTEuNUgyLjc1YS4yNS4yNSAwIDAxLS4yNS0uMjVWMS43NXpNNC43NSA0YS43NS43NSAwIDAwMCAxLjVoNC41YS43NS43NSAwIDAwMC0xLjVoLTQuNXpNNCA3Ljc1QS43NS43NSAwIDAxNC43NSA3aDJhLjc1Ljc1IDAgMDEwIDEuNWgtMkEuNzUuNzUgMCAwMTQgNy43NXptMTEuNzc0IDMuNTM3YS43NS43NSAwIDAwLTEuMDQ4LTEuMDc0TDEwLjcgMTQuMTQ1IDkuMjgxIDEyLjcyYS43NS43NSAwIDAwLTEuMDYyIDEuMDU4bDEuOTQzIDEuOTVhLjc1Ljc1IDAgMDAxLjA1NS4wMDhsNC41NTctNC40NXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgPCU9IHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxQdWxsUmVxdWVzdFJldmlld0NvbnRyaWJ1dGlvbnMgJT4gUHVsbCByZXF1ZXN0PCU9IHModXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0UmV2aWV3Q29udHJpYnV0aW9ucykgJT4gcmV2aWV3ZWRcclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk03LjE3NyAzLjA3M0w5LjU3My42NzdBLjI1LjI1IDAgMDExMCAuODU0djQuNzkyYS4yNS4yNSAwIDAxLS40MjcuMTc3TDcuMTc3IDMuNDI3YS4yNS4yNSAwIDAxMC0uMzU0ek0zLjc1IDIuNWEuNzUuNzUgMCAxMDAgMS41Ljc1Ljc1IDAgMDAwLTEuNXptLTIuMjUuNzVhMi4yNSAyLjI1IDAgMTEzIDIuMTIydjUuMjU2YTIuMjUxIDIuMjUxIDAgMTEtMS41IDBWNS4zNzJBMi4yNSAyLjI1IDAgMDExLjUgMy4yNXpNMTEgMi41aC0xVjRoMWExIDEgMCAwMTEgMXY1LjYyOGEyLjI1MSAyLjI1MSAwIDEwMS41IDBWNUEyLjUgMi41IDAgMDAxMSAyLjV6bTEgMTAuMjVhLjc1Ljc1IDAgMTExLjUgMCAuNzUuNzUgMCAwMS0xLjUgMHpNMy43NSAxMmEuNzUuNzUgMCAxMDAgMS41Ljc1Ljc1IDAgMDAwLTEuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgPCU9IHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxQdWxsUmVxdWVzdENvbnRyaWJ1dGlvbnMgJT4gUHVsbCByZXF1ZXN0PCU9IHModXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0Q29udHJpYnV0aW9ucykgJT4gb3BlbmVkXHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNOCAxLjVhNi41IDYuNSAwIDEwMCAxMyA2LjUgNi41IDAgMDAwLTEzek0wIDhhOCA4IDAgMTExNiAwQTggOCAwIDAxMCA4em05IDNhMSAxIDAgMTEtMiAwIDEgMSAwIDAxMiAwem0tLjI1LTYuMjVhLjc1Ljc1IDAgMDAtMS41IDB2My41YS43NS43NSAwIDAwMS41IDB2LTMuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgPCU9IHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxJc3N1ZUNvbnRyaWJ1dGlvbnMgJT4gSXNzdWU8JT0gcyh1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsSXNzdWVDb250cmlidXRpb25zKSAlPiBvcGVuZWRcclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjc1IDIuNWEuMjUuMjUgMCAwMC0uMjUuMjV2Ny41YzAgLjEzOC4xMTIuMjUuMjUuMjVoMmEuNzUuNzUgMCAwMS43NS43NXYyLjE5bDIuNzItMi43MmEuNzUuNzUgMCAwMS41My0uMjJoNC41YS4yNS4yNSAwIDAwLjI1LS4yNXYtNy41YS4yNS4yNSAwIDAwLS4yNS0uMjVIMi43NXpNMSAyLjc1QzEgMS43ODQgMS43ODQgMSAyLjc1IDFoMTAuNWMuOTY2IDAgMS43NS43ODQgMS43NSAxLjc1djcuNUExLjc1IDEuNzUgMCAwMTEzLjI1IDEySDkuMDZsLTIuNTczIDIuNTczQTEuNDU3IDEuNDU3IDAgMDE0IDEzLjU0M1YxMkgyLjc1QTEuNzUgMS43NSAwIDAxMSAxMC4yNXYtNy41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci5pc3N1ZUNvbW1lbnRzLnRvdGFsQ291bnQgJT4gaXNzdWUgY29tbWVudDwlPSBzKHVzZXIuaXNzdWVDb21tZW50cy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgPCUgaWYgKGJhc2UuY29tbXVuaXR5KSB7ICU+XHJcbiAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgPGgyIGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMS43NSAwQTEuNzUgMS43NSAwIDAwMCAxLjc1djEyLjVDMCAxNS4yMTYuNzg0IDE2IDEuNzUgMTZoMTIuNUExLjc1IDEuNzUgMCAwMDE2IDE0LjI1VjEuNzVBMS43NSAxLjc1IDAgMDAxNC4yNSAwSDEuNzV6TTEuNSAxLjc1YS4yNS4yNSAwIDAxLjI1LS4yNWgxMi41YS4yNS4yNSAwIDAxLjI1LjI1djEyLjVhLjI1LjI1IDAgMDEtLjI1LjI1SDEuNzVhLjI1LjI1IDAgMDEtLjI1LS4yNVYxLjc1ek0xMS43NSAzYS43NS43NSAwIDAwLS43NS43NXY3LjVhLjc1Ljc1IDAgMDAxLjUgMHYtNy41YS43NS43NSAwIDAwLS43NS0uNzV6bS04LjI1Ljc1YS43NS43NSAwIDAxMS41IDB2NS41YS43NS43NSAwIDAxLTEuNSAwdi01LjV6TTggM2EuNzUuNzUgMCAwMC0uNzUuNzV2My41YS43NS43NSAwIDAwMS41IDB2LTMuNUEuNzUuNzUgMCAwMDggM3pcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgQ29tbXVuaXR5IHN0YXRzXHJcbiAgICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjUgMTQuMjVjMCAuMTM4LjExMi4yNS4yNS4yNUg0di0xLjI1YS43NS43NSAwIDAxLjc1LS43NWgyLjVhLjc1Ljc1IDAgMDEuNzUuNzV2MS4yNWgyLjI1YS4yNS4yNSAwIDAwLjI1LS4yNVYxLjc1YS4yNS4yNSAwIDAwLS4yNS0uMjVoLTguNWEuMjUuMjUgMCAwMC0uMjUuMjV2MTIuNXpNMS43NSAxNkExLjc1IDEuNzUgMCAwMTAgMTQuMjVWMS43NUMwIC43ODQuNzg0IDAgMS43NSAwaDguNUMxMS4yMTYgMCAxMiAuNzg0IDEyIDEuNzV2MTIuNWMwIC4wODUtLjAwNi4xNjgtLjAxOC4yNWgyLjI2OGEuMjUuMjUgMCAwMC4yNS0uMjVWOC4yODVhLjI1LjI1IDAgMDAtLjExMS0uMjA4bC0xLjA1NS0uNzAzYS43NS43NSAwIDExLjgzMi0xLjI0OGwxLjA1NS43MDNjLjQ4Ny4zMjUuNzc5Ljg3MS43NzkgMS40NTZ2NS45NjVBMS43NSAxLjc1IDAgMDExNC4yNSAxNmgtMy41YS43NS43NSAwIDAxLS4xOTctLjAyNmMtLjA5OS4wMTctLjIuMDI2LS4zMDMuMDI2aC0zYS43NS43NSAwIDAxLS43NS0uNzVWMTRoLTF2MS4yNWEuNzUuNzUgMCAwMS0uNzUuNzVoLTN6TTMgMy43NUEuNzUuNzUgMCAwMTMuNzUgM2guNWEuNzUuNzUgMCAwMTAgMS41aC0uNUEuNzUuNzUgMCAwMTMgMy43NXpNMy43NSA2YS43NS43NSAwIDAwMCAxLjVoLjVhLjc1Ljc1IDAgMDAwLTEuNWgtLjV6TTMgOS43NUEuNzUuNzUgMCAwMTMuNzUgOWguNWEuNzUuNzUgMCAwMTAgMS41aC0uNUEuNzUuNzUgMCAwMTMgOS43NXpNNy43NSA5YS43NS43NSAwIDAwMCAxLjVoLjVhLjc1Ljc1IDAgMDAwLTEuNWgtLjV6TTcgNi43NUEuNzUuNzUgMCAwMTcuNzUgNmguNWEuNzUuNzUgMCAwMTAgMS41aC0uNUEuNzUuNzUgMCAwMTcgNi43NXpNNy43NSAzYS43NS43NSAwIDAwMCAxLjVoLjVhLjc1Ljc1IDAgMDAwLTEuNWgtLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIE1lbWJlciBvZiA8JT0gdXNlci5vcmdhbml6YXRpb25zLnRvdGFsQ291bnQgJT4gb3JnYW5pemF0aW9uPCU9IHModXNlci5vcmdhbml6YXRpb25zLnRvdGFsQ291bnQpICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNS41IDMuNWEyIDIgMCAxMDAgNCAyIDIgMCAwMDAtNHpNMiA1LjVhMy41IDMuNSAwIDExNS44OTggMi41NDkgNS41MDcgNS41MDcgMCAwMTMuMDM0IDQuMDg0Ljc1Ljc1IDAgMTEtMS40ODIuMjM1IDQuMDAxIDQuMDAxIDAgMDAtNy45IDAgLjc1Ljc1IDAgMDEtMS40ODItLjIzNkE1LjUwNyA1LjUwNyAwIDAxMy4xMDIgOC4wNSAzLjQ5IDMuNDkgMCAwMTIgNS41ek0xMSA0YS43NS43NSAwIDEwMCAxLjUgMS41IDEuNSAwIDAxLjY2NiAyLjg0NC43NS43NSAwIDAwLS40MTYuNjcydi4zNTJhLjc1Ljc1IDAgMDAuNTc0LjczYzEuMi4yODkgMi4xNjIgMS4yIDIuNTIyIDIuMzcyYS43NS43NSAwIDEwMS40MzQtLjQ0IDUuMDEgNS4wMSAwIDAwLTIuNTYtMy4wMTJBMyAzIDAgMDAxMSA0elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICBGb2xsb3dpbmcgPCU9IHVzZXIuZm9sbG93aW5nLnRvdGFsQ291bnQgJT4gdXNlcjwlPSBzKHVzZXIuZm9sbG93ZXJzLnRvdGFsQ291bnQpICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC4yNSAyLjVjLTEuMzM2IDAtMi43NSAxLjE2NC0yLjc1IDMgMCAyLjE1IDEuNTggNC4xNDQgMy4zNjUgNS42ODJBMjAuNTY1IDIwLjU2NSAwIDAwOCAxMy4zOTNhMjAuNTYxIDIwLjU2MSAwIDAwMy4xMzUtMi4yMTFDMTIuOTIgOS42NDQgMTQuNSA3LjY1IDE0LjUgNS41YzAtMS44MzYtMS40MTQtMy0yLjc1LTMtMS4zNzMgMC0yLjYwOS45ODYtMy4wMjkgMi40NTZhLjc1Ljc1IDAgMDEtMS40NDIgMEM2Ljg1OSAzLjQ4NiA1LjYyMyAyLjUgNC4yNSAyLjV6TTggMTQuMjVsLS4zNDUuNjY2LS4wMDItLjAwMS0uMDA2LS4wMDMtLjAxOC0uMDFhNy42NDMgNy42NDMgMCAwMS0uMzEtLjE3IDIyLjA3NSAyMi4wNzUgMCAwMS0zLjQzNC0yLjQxNEMyLjA0NSAxMC43MzEgMCA4LjM1IDAgNS41IDAgMi44MzYgMi4wODYgMSA0LjI1IDEgNS43OTcgMSA3LjE1MyAxLjgwMiA4IDMuMDIgOC44NDcgMS44MDIgMTAuMjAzIDEgMTEuNzUgMSAxMy45MTQgMSAxNiAyLjgzNiAxNiA1LjVjMCAyLjg1LTIuMDQ1IDUuMjMxLTMuODg1IDYuODE4YTIyLjA4IDIyLjA4IDAgMDEtMy43NDQgMi41ODRsLS4wMTguMDEtLjAwNi4wMDNoLS4wMDJMOCAxNC4yNXptMCAwbC4zNDUuNjY2YS43NTIuNzUyIDAgMDEtLjY5IDBMOCAxNC4yNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgU3BvbnNvcmluZyA8JT0gdXNlci5zcG9uc29yc2hpcHNBc1Nwb25zb3IudG90YWxDb3VudCAlPiByZXBvc2l0b3I8JT0gcyh1c2VyLnNwb25zb3JzaGlwc0FzU3BvbnNvci50b3RhbENvdW50LCBcInlcIikgJT5cclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04IC4yNWEuNzUuNzUgMCAwMS42NzMuNDE4bDEuODgyIDMuODE1IDQuMjEuNjEyYS43NS43NSAwIDAxLjQxNiAxLjI3OWwtMy4wNDYgMi45Ny43MTkgNC4xOTJhLjc1Ljc1IDAgMDEtMS4wODguNzkxTDggMTIuMzQ3bC0zLjc2NiAxLjk4YS43NS43NSAwIDAxLTEuMDg4LS43OWwuNzItNC4xOTRMLjgxOCA2LjM3NGEuNzUuNzUgMCAwMS40MTYtMS4yOGw0LjIxLS42MTFMNy4zMjcuNjY4QS43NS43NSAwIDAxOCAuMjV6bTAgMi40NDVMNi42MTUgNS41YS43NS43NSAwIDAxLS41NjQuNDFsLTMuMDk3LjQ1IDIuMjQgMi4xODRhLjc1Ljc1IDAgMDEuMjE2LjY2NGwtLjUyOCAzLjA4NCAyLjc2OS0xLjQ1NmEuNzUuNzUgMCAwMS42OTggMGwyLjc3IDEuNDU2LS41My0zLjA4NGEuNzUuNzUgMCAwMS4yMTYtLjY2NGwyLjI0LTIuMTgzLTMuMDk2LS40NWEuNzUuNzUgMCAwMS0uNTY0LS40MUw4IDIuNjk0di4wMDF6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIFN0YXJyZWQgPCU9IHVzZXIuc3RhcnJlZFJlcG9zaXRvcmllcy50b3RhbENvdW50ICU+IHJlcG9zaXRvcjwlPSBzKHVzZXIuc3RhcnJlZFJlcG9zaXRvcmllcy50b3RhbENvdW50LCBcInlcIikgJT5cclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjY3OSA3LjkzMmMuNDEyLS42MjEgMS4yNDItMS43NSAyLjM2Ni0yLjcxN0M1LjE3NSA0LjI0MiA2LjUyNyAzLjUgOCAzLjVjMS40NzMgMCAyLjgyNC43NDIgMy45NTUgMS43MTUgMS4xMjQuOTY3IDEuOTU0IDIuMDk2IDIuMzY2IDIuNzE3YS4xMTkuMTE5IDAgMDEwIC4xMzZjLS40MTIuNjIxLTEuMjQyIDEuNzUtMi4zNjYgMi43MTdDMTAuODI1IDExLjc1OCA5LjQ3MyAxMi41IDggMTIuNWMtMS40NzMgMC0yLjgyNC0uNzQyLTMuOTU1LTEuNzE1QzIuOTIgOS44MTggMi4wOSA4LjY5IDEuNjc5IDguMDY4YS4xMTkuMTE5IDAgMDEwLS4xMzZ6TTggMmMtMS45ODEgMC0zLjY3Ljk5Mi00LjkzMyAyLjA3OEMxLjc5NyA1LjE2OS44OCA2LjQyMy40MyA3LjFhMS42MTkgMS42MTkgMCAwMDAgMS43OThjLjQ1LjY3OCAxLjM2NyAxLjkzMiAyLjYzNyAzLjAyNEM0LjMyOSAxMy4wMDggNi4wMTkgMTQgOCAxNGMxLjk4MSAwIDMuNjctLjk5MiA0LjkzMy0yLjA3OCAxLjI3LTEuMDkxIDIuMTg3LTIuMzQ1IDIuNjM3LTMuMDIzYTEuNjE5IDEuNjE5IDAgMDAwLTEuNzk4Yy0uNDUtLjY3OC0xLjM2Ny0xLjkzMi0yLjYzNy0zLjAyM0MxMS42NzEgMi45OTIgOS45ODEgMiA4IDJ6bTAgOGEyIDIgMCAxMDAtNCAyIDIgMCAwMDAgNHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgV2F0Y2hpbmcgPCU9IHVzZXIud2F0Y2hpbmcudG90YWxDb3VudCAlPiByZXBvc2l0b3I8JT0gcyh1c2VyLndhdGNoaW5nLnRvdGFsQ291bnQsIFwieVwiKSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICA8JSB9ICU+XHJcbiAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgPCUgaWYgKGJhc2UucmVwb3NpdG9yaWVzKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMiAyLjVBMi41IDIuNSAwIDAxNC41IDBoOC43NWEuNzUuNzUgMCAwMS43NS43NXYxMi41YS43NS43NSAwIDAxLS43NS43NWgtMi41YS43NS43NSAwIDExMC0xLjVoMS43NXYtMmgtOGExIDEgMCAwMC0uNzE0IDEuNy43NS43NSAwIDAxLTEuMDcyIDEuMDVBMi40OTUgMi40OTUgMCAwMTIgMTEuNXYtOXptMTAuNS0xVjloLThjLS4zNTYgMC0uNjk0LjA3NC0xIC4yMDhWMi41YTEgMSAwIDAxMS0xaDh6TTUgMTIuMjV2My4yNWEuMjUuMjUgMCAwMC40LjJsMS40NS0xLjA4N2EuMjUuMjUgMCAwMS4zIDBMOC42IDE1LjdhLjI1LjI1IDAgMDAuNC0uMnYtMy4yNWEuMjUuMjUgMCAwMC0uMjUtLjI1aC0zLjVhLjI1LjI1IDAgMDAtLjI1LjI1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgPCU9IHVzZXIucmVwb3NpdG9yaWVzLnRvdGFsQ291bnQgJT4gUmVwb3NpdG9yPCU9IHModXNlci5yZXBvc2l0b3JpZXMudG90YWxDb3VudCwgXCJ5XCIpICU+XHJcbiAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04Ljc1Ljc1YS43NS43NSAwIDAwLTEuNSAwVjJoLS45ODRjLS4zMDUgMC0uNjA0LjA4LS44NjkuMjNsLTEuMjg4LjczN0EuMjUuMjUgMCAwMTMuOTg0IDNIMS43NWEuNzUuNzUgMCAwMDAgMS41aC40MjhMLjA2NiA5LjE5MmEuNzUuNzUgMCAwMC4xNTQuODM4bC41My0uNTMtLjUzLjUzdi4wMDFsLjAwMi4wMDIuMDAyLjAwMi4wMDYuMDA2LjAxNi4wMTUuMDQ1LjA0YTMuNTE0IDMuNTE0IDAgMDAuNjg2LjQ1QTQuNDkyIDQuNDkyIDAgMDAzIDExYy44OCAwIDEuNTU2LS4yMiAyLjAyMy0uNDU0YTMuNTE1IDMuNTE1IDAgMDAuNjg2LS40NWwuMDQ1LS4wNC4wMTYtLjAxNS4wMDYtLjAwNi4wMDItLjAwMi4wMDEtLjAwMkw1LjI1IDkuNWwuNTMuNTNhLjc1Ljc1IDAgMDAuMTU0LS44MzhMMy44MjIgNC41aC4xNjJjLjMwNSAwIC42MDQtLjA4Ljg2OS0uMjNsMS4yODktLjczN2EuMjUuMjUgMCAwMS4xMjQtLjAzM2guOTg0VjEzaC0yLjVhLjc1Ljc1IDAgMDAwIDEuNWg2LjVhLjc1Ljc1IDAgMDAwLTEuNWgtMi41VjMuNWguOTg0YS4yNS4yNSAwIDAxLjEyNC4wMzNsMS4yOS43MzZjLjI2NC4xNTIuNTYzLjIzMS44NjguMjMxaC4xNjJsLTIuMTEyIDQuNjkyYS43NS43NSAwIDAwLjE1NC44MzhsLjUzLS41My0uNTMuNTN2LjAwMWwuMDAyLjAwMi4wMDIuMDAyLjAwNi4wMDYuMDE2LjAxNS4wNDUuMDRhMy41MTcgMy41MTcgMCAwMC42ODYuNDVBNC40OTIgNC40OTIgMCAwMDEzIDExYy44OCAwIDEuNTU2LS4yMiAyLjAyMy0uNDU0YTMuNTEyIDMuNTEyIDAgMDAuNjg2LS40NWwuMDQ1LS4wNC4wMS0uMDEuMDA2LS4wMDUuMDA2LS4wMDYuMDAyLS4wMDIuMDAxLS4wMDItLjUyOS0uNTMxLjUzLjUzYS43NS43NSAwIDAwLjE1NC0uODM4TDEzLjgyMyA0LjVoLjQyN2EuNzUuNzUgMCAwMDAtMS41aC0yLjIzNGEuMjUuMjUgMCAwMS0uMTI0LS4wMzNsLTEuMjktLjczNkExLjc1IDEuNzUgMCAwMDkuNzM1IDJIOC43NVYuNzV6TTEuNjk1IDkuMjI3Yy4yODUuMTM1LjcxOC4yNzMgMS4zMDUuMjczczEuMDItLjEzOCAxLjMwNS0uMjczTDMgNi4zMjdsLTEuMzA1IDIuOXptMTAgMGMuMjg1LjEzNS43MTguMjczIDEuMzA1LjI3M3MxLjAyLS4xMzggMS4zMDUtLjI3M0wxMyA2LjMyN2wtMS4zMDUgMi45elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5saWNlbnNlcy5mYXZvcml0ZS5sZW5ndGgpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgUHJlZmVyIDwlPSBjb21wdXRlZC5saWNlbnNlcy5mYXZvcml0ZSAlPiBsaWNlbnNlXHJcbiAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICBObyBsaWNlbnNlIHByZWZlcmVuY2VcclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjUgNy43NzVWMi43NWEuMjUuMjUgMCAwMS4yNS0uMjVoNS4wMjVhLjI1LjI1IDAgMDEuMTc3LjA3M2w2LjI1IDYuMjVhLjI1LjI1IDAgMDEwIC4zNTRsLTUuMDI1IDUuMDI1YS4yNS4yNSAwIDAxLS4zNTQgMGwtNi4yNS02LjI1YS4yNS4yNSAwIDAxLS4wNzMtLjE3N3ptLTEuNSAwVjIuNzVDMSAxLjc4NCAxLjc4NCAxIDIuNzUgMWg1LjAyNWMuNDY0IDAgLjkxLjE4NCAxLjIzOC41MTNsNi4yNSA2LjI1YTEuNzUgMS43NSAwIDAxMCAyLjQ3NGwtNS4wMjYgNS4wMjZhMS43NSAxLjc1IDAgMDEtMi40NzQgMGwtNi4yNS02LjI1QTEuNzUgMS43NSAwIDAxMSA3Ljc3NXpNNiA1YTEgMSAwIDEwMCAyIDEgMSAwIDAwMC0yelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5yZXBvc2l0b3JpZXMucmVsZWFzZXMgJT4gUmVsZWFzZTwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy5yZWxlYXNlcykgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04Ljg3OC4zOTJhMS43NSAxLjc1IDAgMDAtMS43NTYgMGwtNS4yNSAzLjA0NUExLjc1IDEuNzUgMCAwMDEgNC45NTF2Ni4wOThjMCAuNjI0LjMzMiAxLjIuODcyIDEuNTE0bDUuMjUgMy4wNDVhMS43NSAxLjc1IDAgMDAxLjc1NiAwbDUuMjUtMy4wNDVjLjU0LS4zMTMuODcyLS44OS44NzItMS41MTRWNC45NTFjMC0uNjI0LS4zMzItMS4yLS44NzItMS41MTRMOC44NzguMzkyek03Ljg3NSAxLjY5YS4yNS4yNSAwIDAxLjI1IDBsNC42MyAyLjY4NUw4IDcuMTMzIDMuMjQ1IDQuMzc1bDQuNjMtMi42ODV6TTIuNSA1LjY3N3Y1LjM3MmMwIC4wOS4wNDcuMTcxLjEyNS4yMTZsNC42MjUgMi42ODNWOC40MzJMMi41IDUuNjc3em02LjI1IDguMjcxbDQuNjI1LTIuNjgzYS4yNS4yNSAwIDAwLjEyNS0uMjE2VjUuNjc3TDguNzUgOC40MzJ2NS41MTZ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgPCU9IHVzZXIucGFja2FnZXMudG90YWxDb3VudCAlPiBQYWNrYWdlPCU9IHModXNlci5wYWNrYWdlcy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjUgMy41YzAtLjEzMy4wNTgtLjMxOC4yODItLjU1LjIyNy0uMjM3LjU5Mi0uNDg0IDEuMS0uNzA4QzQuODk5IDEuNzk1IDYuMzU0IDEuNSA4IDEuNWMxLjY0NyAwIDMuMTAyLjI5NSA0LjExNy43NDIuNTEuMjI0Ljg3NC40NyAxLjEwMS43MDcuMjI0LjIzMy4yODIuNDE4LjI4Mi41NTEgMCAuMTMzLS4wNTguMzE4LS4yODIuNTUtLjIyNy4yMzctLjU5Mi40ODQtMS4xLjcwOEMxMS4xMDEgNS4yMDUgOS42NDYgNS41IDggNS41Yy0xLjY0NyAwLTMuMTAyLS4yOTUtNC4xMTctLjc0Mi0uNTEtLjIyNC0uODc0LS40Ny0xLjEwMS0uNzA3LS4yMjQtLjIzMy0uMjgyLS40MTgtLjI4Mi0uNTUxek0xIDMuNWMwLS42MjYuMjkyLTEuMTY1LjctMS41OS40MDYtLjQyMi45NTYtLjc2NyAxLjU3OS0xLjA0MUM0LjUyNS4zMiA2LjE5NSAwIDggMGMxLjgwNSAwIDMuNDc1LjMyIDQuNzIyLjg2OS42MjIuMjc0IDEuMTcyLjYyIDEuNTc4IDEuMDQuNDA4LjQyNi43Ljk2NS43IDEuNTkxdjljMCAuNjI2LS4yOTIgMS4xNjUtLjcgMS41OS0uNDA2LjQyMi0uOTU2Ljc2Ny0xLjU3OSAxLjA0MUMxMS40NzYgMTUuNjggOS44MDYgMTYgOCAxNmMtMS44MDUgMC0zLjQ3NS0uMzItNC43MjEtLjg2OS0uNjIzLS4yNzQtMS4xNzMtLjYyLTEuNTc5LTEuMDQtLjQwOC0uNDI2LS43LS45NjUtLjctMS41OTF2LTl6TTIuNSA4VjUuNzI0Yy4yNDEuMTUuNTAzLjI4Ni43NzkuNDA3QzQuNTI1IDYuNjggNi4xOTUgNyA4IDdjMS44MDUgMCAzLjQ3NS0uMzIgNC43MjItLjg2OS4yNzUtLjEyMS41MzctLjI1Ny43NzgtLjQwN1Y4YzAgLjEzMy0uMDU4LjMxOC0uMjgyLjU1LS4yMjcuMjM3LS41OTIuNDg0LTEuMS43MDhDMTEuMTAxIDkuNzA1IDkuNjQ2IDEwIDggMTBjLTEuNjQ3IDAtMy4xMDItLjI5NS00LjExNy0uNzQyLS41MS0uMjI0LS44NzQtLjQ3LTEuMTAxLS43MDdDMi41NTggOC4zMTggMi41IDguMTMzIDIuNSA4em0wIDIuMjI1VjEyLjVjMCAuMTMzLjA1OC4zMTguMjgyLjU1LjIyNy4yMzcuNTkyLjQ4NCAxLjEuNzA4IDEuMDE2LjQ0NyAyLjQ3MS43NDIgNC4xMTguNzQyIDEuNjQ3IDAgMy4xMDItLjI5NSA0LjExNy0uNzQyLjUxLS4yMjQuODc0LS40NyAxLjEwMS0uNzA3LjIyNC0uMjMzLjI4Mi0uNDE4LjI4Mi0uNTUxdi0yLjI3NWMtLjI0MS4xNS0uNTAzLjI4NS0uNzc4LjQwNi0xLjI0Ny41NDktMi45MTcuODY5LTQuNzIyLjg2OS0xLjgwNSAwLTMuNDc1LS4zMi00LjcyMS0uODY5YTYuMjM2IDYuMjM2IDAgMDEtLjc3OS0uNDA2elwiLz48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5kaXNrVXNhZ2UgJT4gdXNlZFxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmxpbmVzKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCA8JT0gY29tcHV0ZWQucGx1Z2lucy5saW5lcy5lcnJvciA/ICdlcnJvcicgOiAnJyAlPlwiPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuNzUgMS41YS4yNS4yNSAwIDAwLS4yNS4yNXYxMi41YzAgLjEzOC4xMTIuMjUuMjUuMjVoMTAuNWEuMjUuMjUgMCAwMC4yNS0uMjVWNC42NjRhLjI1LjI1IDAgMDAtLjA3My0uMTc3bC0yLjkxNC0yLjkxNGEuMjUuMjUgMCAwMC0uMTc3LS4wNzNIMi43NXpNMSAxLjc1QzEgLjc4NCAxLjc4NCAwIDIuNzUgMGg3LjU4NmMuNDY0IDAgLjkwOS4xODQgMS4yMzcuNTEzbDIuOTE0IDIuOTE0Yy4zMjkuMzI4LjUxMy43NzMuNTEzIDEuMjM3djkuNTg2QTEuNzUgMS43NSAwIDAxMTMuMjUgMTZIMi43NUExLjc1IDEuNzUgMCAwMTEgMTQuMjVWMS43NXptNyAxLjVhLjc1Ljc1IDAgMDEuNzUuNzV2MS41aDEuNWEuNzUuNzUgMCAwMTAgMS41aC0xLjV2MS41YS43NS43NSAwIDAxLTEuNSAwVjdoLTEuNWEuNzUuNzUgMCAwMTAtMS41aDEuNVY0QS43NS43NSAwIDAxOCAzLjI1em0tMyA4YS43NS43NSAwIDAxLjc1LS43NWg0LjVhLjc1Ljc1IDAgMDEwIDEuNWgtNC41YS43NS43NSAwIDAxLS43NS0uNzV6XCI+PC9wYXRoPjwvc3ZnPiAgICAgICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLmxpbmVzLmVycm9yLm1lc3NhZ2UgJT5cclxuICAgICAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuYWRkZWQgJT4gYWRkZWQsIDwlPSBjb21wdXRlZC5wbHVnaW5zLmxpbmVzLmRlbGV0ZWQgJT4gcmVtb3ZlZFxyXG4gICAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTQuMjUgMi41Yy0xLjMzNiAwLTIuNzUgMS4xNjQtMi43NSAzIDAgMi4xNSAxLjU4IDQuMTQ0IDMuMzY1IDUuNjgyQTIwLjU2NSAyMC41NjUgMCAwMDggMTMuMzkzYTIwLjU2MSAyMC41NjEgMCAwMDMuMTM1LTIuMjExQzEyLjkyIDkuNjQ0IDE0LjUgNy42NSAxNC41IDUuNWMwLTEuODM2LTEuNDE0LTMtMi43NS0zLTEuMzczIDAtMi42MDkuOTg2LTMuMDI5IDIuNDU2YS43NS43NSAwIDAxLTEuNDQyIDBDNi44NTkgMy40ODYgNS42MjMgMi41IDQuMjUgMi41ek04IDE0LjI1bC0uMzQ1LjY2Ni0uMDAyLS4wMDEtLjAwNi0uMDAzLS4wMTgtLjAxYTcuNjQzIDcuNjQzIDAgMDEtLjMxLS4xNyAyMi4wNzUgMjIuMDc1IDAgMDEtMy40MzQtMi40MTRDMi4wNDUgMTAuNzMxIDAgOC4zNSAwIDUuNSAwIDIuODM2IDIuMDg2IDEgNC4yNSAxIDUuNzk3IDEgNy4xNTMgMS44MDIgOCAzLjAyIDguODQ3IDEuODAyIDEwLjIwMyAxIDExLjc1IDEgMTMuOTE0IDEgMTYgMi44MzYgMTYgNS41YzAgMi44NS0yLjA0NSA1LjIzMS0zLjg4NSA2LjgxOGEyMi4wOCAyMi4wOCAwIDAxLTMuNzQ0IDIuNTg0bC0uMDE4LjAxLS4wMDYuMDAzaC0uMDAyTDggMTQuMjV6bTAgMGwuMzQ1LjY2NmEuNzUyLjc1MiAwIDAxLS42OSAwTDggMTQuMjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgPCU9IHVzZXIuc3BvbnNvcnNoaXBzQXNNYWludGFpbmVyLnRvdGFsQ291bnQgJT4gU3BvbnNvcjwlPSBzKHVzZXIuc3BvbnNvcnNoaXBzQXNNYWludGFpbmVyLnRvdGFsQ291bnQpICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNOCAuMjVhLjc1Ljc1IDAgMDEuNjczLjQxOGwxLjg4MiAzLjgxNSA0LjIxLjYxMmEuNzUuNzUgMCAwMS40MTYgMS4yNzlsLTMuMDQ2IDIuOTcuNzE5IDQuMTkyYS43NS43NSAwIDAxLTEuMDg4Ljc5MUw4IDEyLjM0N2wtMy43NjYgMS45OGEuNzUuNzUgMCAwMS0xLjA4OC0uNzlsLjcyLTQuMTk0TC44MTggNi4zNzRhLjc1Ljc1IDAgMDEuNDE2LTEuMjhsNC4yMS0uNjExTDcuMzI3LjY2OEEuNzUuNzUgMCAwMTggLjI1em0wIDIuNDQ1TDYuNjE1IDUuNWEuNzUuNzUgMCAwMS0uNTY0LjQxbC0zLjA5Ny40NSAyLjI0IDIuMTg0YS43NS43NSAwIDAxLjIxNi42NjRsLS41MjggMy4wODQgMi43NjktMS40NTZhLjc1Ljc1IDAgMDEuNjk4IDBsMi43NyAxLjQ1Ni0uNTMtMy4wODRhLjc1Ljc1IDAgMDEuMjE2LS42NjRsMi4yNC0yLjE4My0zLjA5Ni0uNDVhLjc1Ljc1IDAgMDEtLjU2NC0uNDFMOCAyLjY5NHYuMDAxelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5yZXBvc2l0b3JpZXMuc3RhcmdhemVycyAlPiBTdGFyZ2F6ZXI8JT0gcyhjb21wdXRlZC5yZXBvc2l0b3JpZXMuc3RhcmdhemVycykgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk01IDMuMjVhLjc1Ljc1IDAgMTEtMS41IDAgLjc1Ljc1IDAgMDExLjUgMHptMCAyLjEyMmEyLjI1IDIuMjUgMCAxMC0xLjUgMHYuODc4QTIuMjUgMi4yNSAwIDAwNS43NSA4LjVoMS41djIuMTI4YTIuMjUxIDIuMjUxIDAgMTAxLjUgMFY4LjVoMS41YTIuMjUgMi4yNSAwIDAwMi4yNS0yLjI1di0uODc4YTIuMjUgMi4yNSAwIDEwLTEuNSAwdi44NzhhLjc1Ljc1IDAgMDEtLjc1Ljc1aC00LjVBLjc1Ljc1IDAgMDE1IDYuMjV2LS44Nzh6bTMuNzUgNy4zNzhhLjc1Ljc1IDAgMTEtMS41IDAgLjc1Ljc1IDAgMDExLjUgMHptMy04Ljc1YS43NS43NSAwIDEwMC0xLjUuNzUuNzUgMCAwMDAgMS41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5yZXBvc2l0b3JpZXMuZm9ya3MgJT4gRm9yazwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy5mb3JrcykgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjY3OSA3LjkzMmMuNDEyLS42MjEgMS4yNDItMS43NSAyLjM2Ni0yLjcxN0M1LjE3NSA0LjI0MiA2LjUyNyAzLjUgOCAzLjVjMS40NzMgMCAyLjgyNC43NDIgMy45NTUgMS43MTUgMS4xMjQuOTY3IDEuOTU0IDIuMDk2IDIuMzY2IDIuNzE3YS4xMTkuMTE5IDAgMDEwIC4xMzZjLS40MTIuNjIxLTEuMjQyIDEuNzUtMi4zNjYgMi43MTdDMTAuODI1IDExLjc1OCA5LjQ3MyAxMi41IDggMTIuNWMtMS40NzMgMC0yLjgyNC0uNzQyLTMuOTU1LTEuNzE1QzIuOTIgOS44MTggMi4wOSA4LjY5IDEuNjc5IDguMDY4YS4xMTkuMTE5IDAgMDEwLS4xMzZ6TTggMmMtMS45ODEgMC0zLjY3Ljk5Mi00LjkzMyAyLjA3OEMxLjc5NyA1LjE2OS44OCA2LjQyMy40MyA3LjFhMS42MTkgMS42MTkgMCAwMDAgMS43OThjLjQ1LjY3OCAxLjM2NyAxLjkzMiAyLjYzNyAzLjAyNEM0LjMyOSAxMy4wMDggNi4wMTkgMTQgOCAxNGMxLjk4MSAwIDMuNjctLjk5MiA0LjkzMy0yLjA3OCAxLjI3LTEuMDkxIDIuMTg3LTIuMzQ1IDIuNjM3LTMuMDIzYTEuNjE5IDEuNjE5IDAgMDAwLTEuNzk4Yy0uNDUtLjY3OC0xLjM2Ny0xLjkzMi0yLjYzNy0zLjAyM0MxMS42NzEgMi45OTIgOS45ODEgMiA4IDJ6bTAgOGEyIDIgMCAxMDAtNCAyIDIgMCAwMDAgNHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucmVwb3NpdG9yaWVzLndhdGNoZXJzICU+IFdhdGNoZXI8JT0gcyhjb21wdXRlZC5yZXBvc2l0b3JpZXMud2F0Y2hlcnMpICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYykgeyAlPlxyXG4gICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgPCU9IGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy5lcnJvciA/ICdlcnJvcicgOiAnJyAlPlwiPlxyXG4gICAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0wIDEuNzVBLjc1Ljc1IDAgMDEuNzUgMWg0LjI1M2MxLjIyNyAwIDIuMzE3LjU5IDMgMS41MDFBMy43NDQgMy43NDQgMCAwMTExLjAwNiAxaDQuMjQ1YS43NS43NSAwIDAxLjc1Ljc1djEwLjVhLjc1Ljc1IDAgMDEtLjc1Ljc1aC00LjUwN2EyLjI1IDIuMjUgMCAwMC0xLjU5MS42NTlsLS42MjIuNjIxYS43NS43NSAwIDAxLTEuMDYgMGwtLjYyMi0uNjIxQTIuMjUgMi4yNSAwIDAwNS4yNTggMTNILjc1YS43NS43NSAwIDAxLS43NS0uNzVWMS43NXptOC43NTUgM2EyLjI1IDIuMjUgMCAwMTIuMjUtMi4yNUgxNC41djloLTMuNzU3Yy0uNzEgMC0xLjQuMjAxLTEuOTkyLjU3MmwuMDA0LTcuMzIyem0tMS41MDQgNy4zMjRsLjAwNC01LjA3My0uMDAyLTIuMjUzQTIuMjUgMi4yNSAwIDAwNS4wMDMgMi41SDEuNXY5aDMuNzU3YTMuNzUgMy43NSAwIDAxMS45OTQuNTc0elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy50cmFmZmljLmVycm9yKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy50cmFmZmljLmVycm9yLm1lc3NhZ2UgJT5cclxuICAgICAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy52aWV3cy5jb3VudCAlPiB2aWV3PCU9IHMoY29tcHV0ZWQucGx1Z2lucy50cmFmZmljLnZpZXdzLmNvdW50KSAlPiBpbiBsYXN0IHR3byB3ZWVrc1xyXG4gICAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwKSB7ICU+XHJcbiAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG5cclxuICAgICAgICAgIDxzZWN0aW9uIGNsYXNzPVwiY29sdW1uXCI+XHJcbiAgICAgICAgICAgIDxoMz5Jc3N1ZXM8L2gzPlxyXG4gICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGVycm9yXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjM0MyAxMy42NTdBOCA4IDAgMTExMy42NTcgMi4zNDMgOCA4IDAgMDEyLjM0MyAxMy42NTd6TTYuMDMgNC45N2EuNzUuNzUgMCAwMC0xLjA2IDEuMDZMNi45NCA4IDQuOTcgOS45N2EuNzUuNzUgMCAxMDEuMDYgMS4wNkw4IDkuMDZsMS45NyAxLjk3YS43NS43NSAwIDEwMS4wNi0xLjA2TDkuMDYgOGwxLjk3LTEuOTdhLjc1Ljc1IDAgMTAtMS4wNi0xLjA2TDggNi45NCA2LjAzIDQuOTd6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImJhclwiIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB3aWR0aD1cIjIyMFwiIGhlaWdodD1cIjhcIj5cclxuICAgICAgICAgICAgICAgIDxtYXNrIGlkPVwiaXNzdWVzLWJhclwiPlxyXG4gICAgICAgICAgICAgICAgICA8cmVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCIyMjBcIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIndoaXRlXCIgcng9XCI1XCIvPlxyXG4gICAgICAgICAgICAgICAgPC9tYXNrPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjaXNzdWVzLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5pc3N1ZXMuY291bnQgPyAwIDogMjIwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCIjZDFkNWRhXCIvPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjaXNzdWVzLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiNkNzNhNDlcIi8+XHJcbiAgICAgICAgICAgICAgICA8cmVjdCBtYXNrPVwidXJsKCNpc3N1ZXMtYmFyKVwiIHg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiB5PVwiMFwiIHdpZHRoPVwiPCU9ICgxLWNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiMyOGE3NDVcIi8+XHJcbiAgICAgICAgICAgICAgPC9zdmc+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGhvcml6b250YWwgZmlsbC13aWR0aFwiPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGNlbnRlclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbD1cIiNkNzNhNDlcIiBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjUgOGE2LjUgNi41IDAgMDExMC42NS01LjAwMy43NS43NSAwIDAwLjk1OS0xLjE1MyA4IDggMCAxMDIuNTkyIDguMzMuNzUuNzUgMCAxMC0xLjQ0NC0uNDA3QTYuNSA2LjUgMCAwMTEuNSA4ek04IDEyYTEgMSAwIDEwMC0yIDEgMSAwIDAwMCAyem0wLThhLjc1Ljc1IDAgMDEuNzUuNzV2My41YS43NS43NSAwIDExLTEuNSAwdi0zLjVBLjc1Ljc1IDAgMDE4IDR6bTQuNzggNC4yOGwzLTNhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2bC0yLjQ3IDIuNDctLjk3LS45N2EuNzQ5Ljc0OSAwIDEwLTEuMDYgMS4wNmwxLjUgMS41YS43NS43NSAwIDAwMS4wNiAwelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJuby13cmFwXCI+PCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZCAlPiBDbG9zZWQ8L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjZW50ZXJcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGw9XCIjMjhhNzQ1XCIgZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNOCAxLjVhNi41IDYuNSAwIDEwMCAxMyA2LjUgNi41IDAgMDAwLTEzek0wIDhhOCA4IDAgMTExNiAwQTggOCAwIDAxMCA4em05IDNhMSAxIDAgMTEtMiAwIDEgMSAwIDAxMiAwem0tLjI1LTYuMjVhLjc1Ljc1IDAgMDAtMS41IDB2My41YS43NS43NSAwIDAwMS41IDB2LTMuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwibm8td3JhcFwiPjwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5vcGVuICU+IE9wZW48L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG5cclxuICAgICAgICAgIDxzZWN0aW9uIGNsYXNzPVwiY29sdW1uXCI+XHJcbiAgICAgICAgICAgIDxoMz5QdWxsIHJlcXVlc3RzPC9oMz5cclxuICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi4zNDMgMTMuNjU3QTggOCAwIDExMTMuNjU3IDIuMzQzIDggOCAwIDAxMi4zNDMgMTMuNjU3ek02LjAzIDQuOTdhLjc1Ljc1IDAgMDAtMS4wNiAxLjA2TDYuOTQgOCA0Ljk3IDkuOTdhLjc1Ljc1IDAgMTAxLjA2IDEuMDZMOCA5LjA2bDEuOTcgMS45N2EuNzUuNzUgMCAxMDEuMDYtMS4wNkw5LjA2IDhsMS45Ny0xLjk3YS43NS43NSAwIDEwLTEuMDYtMS4wNkw4IDYuOTQgNi4wMyA0Ljk3elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgIDxzdmcgY2xhc3M9XCJiYXJcIiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgd2lkdGg9XCIyMjBcIiBoZWlnaHQ9XCI4XCI+XHJcbiAgICAgICAgICAgICAgICA8bWFzayBpZD1cInByLWJhclwiPlxyXG4gICAgICAgICAgICAgICAgICA8cmVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCIyMjBcIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIndoaXRlXCIgcng9XCI1XCIvPlxyXG4gICAgICAgICAgICAgICAgPC9tYXNrPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjcHItYmFyKVwiIHg9XCIwXCIgeT1cIjBcIiB3aWR0aD1cIjwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLmNvdW50ID8gMCA6IDIyMCAlPlwiIGhlaWdodD1cIjhcIiBmaWxsPVwiI2QxZDVkYVwiLz5cclxuICAgICAgICAgICAgICAgIDxyZWN0IG1hc2s9XCJ1cmwoI3ByLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIubWVyZ2VkL2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIuY291bnQpKjIyMCB8fCAwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCIjNmY0MmMxXCIvPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjcHItYmFyKVwiIHg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIubWVyZ2VkL2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIuY291bnQpKjIyMCB8fCAwICU+XCIgeT1cIjBcIiB3aWR0aD1cIjwlPSAoMS1jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm1lcmdlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLmNvdW50KSoyMjAgfHwgMCAlPlwiIGhlaWdodD1cIjhcIiBmaWxsPVwiIzI4YTc0NVwiLz5cclxuICAgICAgICAgICAgICA8L3N2Zz5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgaG9yaXpvbnRhbCBmaWxsLXdpZHRoXCI+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgY2VudGVyXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsPVwiIzZmNDJjMVwiIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTUgMy4yNTRWMy4yNXYuMDA1YS43NS43NSAwIDExMC0uMDA1di4wMDR6bS40NSAxLjlhMi4yNSAyLjI1IDAgMTAtMS45NS4yMTh2NS4yNTZhMi4yNSAyLjI1IDAgMTAxLjUgMFY3LjEyM0E1LjczNSA1LjczNSAwIDAwOS4yNSA5aDEuMzc4YTIuMjUxIDIuMjUxIDAgMTAwLTEuNUg5LjI1YTQuMjUgNC4yNSAwIDAxLTMuOC0yLjM0NnpNMTIuNzUgOWEuNzUuNzUgMCAxMDAtMS41Ljc1Ljc1IDAgMDAwIDEuNXptLTguNSA0LjVhLjc1Ljc1IDAgMTAwLTEuNS43NS43NSAwIDAwMCAxLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cIm5vLXdyYXBcIj48JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5tZXJnZWQgJT4gTWVyZ2VkPC9zcGFuPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgY2VudGVyXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsPVwiIzI4YTc0NVwiIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTcuMTc3IDMuMDczTDkuNTczLjY3N0EuMjUuMjUgMCAwMTEwIC44NTR2NC43OTJhLjI1LjI1IDAgMDEtLjQyNy4xNzdMNy4xNzcgMy40MjdhLjI1LjI1IDAgMDEwLS4zNTR6TTMuNzUgMi41YS43NS43NSAwIDEwMCAxLjUuNzUuNzUgMCAwMDAtMS41em0tMi4yNS43NWEyLjI1IDIuMjUgMCAxMTMgMi4xMjJ2NS4yNTZhMi4yNTEgMi4yNTEgMCAxMS0xLjUgMFY1LjM3MkEyLjI1IDIuMjUgMCAwMTEuNSAzLjI1ek0xMSAyLjVoLTFWNGgxYTEgMSAwIDAxMSAxdjUuNjI4YTIuMjUxIDIuMjUxIDAgMTAxLjUgMFY1QTIuNSAyLjUgMCAwMDExIDIuNXptMSAxMC4yNWEuNzUuNzUgMCAxMTEuNSAwIC43NS43NSAwIDAxLTEuNSAwek0zLjc1IDEyYS43NS43NSAwIDEwMCAxLjUuNzUuNzUgMCAwMDAtMS41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJuby13cmFwXCI+PCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIub3BlbiAlPiBPcGVuPC9zcGFuPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgIDwvc2VjdGlvbj5cclxuXHJcbiAgICAgICAgPC9kaXY+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcykgeyAlPlxyXG4gICAgICAgIDxzZWN0aW9uIGNsYXNzPVwiY29sdW1uXCI+XHJcbiAgICAgICAgICA8aDM+TW9zdCB1c2VkIGxhbmd1YWdlczwvaDM+XHJcbiAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGVycm9yXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi4zNDMgMTMuNjU3QTggOCAwIDExMTMuNjU3IDIuMzQzIDggOCAwIDAxMi4zNDMgMTMuNjU3ek02LjAzIDQuOTdhLjc1Ljc1IDAgMDAtMS4wNiAxLjA2TDYuOTQgOCA0Ljk3IDkuOTdhLjc1Ljc1IDAgMTAxLjA2IDEuMDZMOCA5LjA2bDEuOTcgMS45N2EuNzUuNzUgMCAxMDEuMDYtMS4wNkw5LjA2IDhsMS45Ny0xLjk3YS43NS43NSAwIDEwLTEuMDYtMS4wNkw4IDYuOTQgNi4wMyA0Ljk3elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgIDxzdmcgY2xhc3M9XCJiYXJcIiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgd2lkdGg9XCI0NjBcIiBoZWlnaHQ9XCI4XCI+XHJcbiAgICAgICAgICAgICAgPG1hc2sgaWQ9XCJsYW5ndWFnZXMtYmFyXCI+XHJcbiAgICAgICAgICAgICAgICA8cmVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI0NjBcIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIndoaXRlXCIgcng9XCI1XCIvPlxyXG4gICAgICAgICAgICAgIDwvbWFzaz5cclxuICAgICAgICAgICAgICA8cmVjdCBtYXNrPVwidXJsKCNsYW5ndWFnZXMtYmFyKVwiIHg9XCIwXCIgeT1cIjBcIiB3aWR0aD1cIjwlPSBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5mYXZvcml0ZXMubGVuZ3RoID8gMCA6IDQ2MCAlPlwiIGhlaWdodD1cIjhcIiBmaWxsPVwiI2QxZDVkYVwiLz5cclxuICAgICAgICAgICAgICA8JSBmb3IgKGNvbnN0IHtuYW1lLCB2YWx1ZSwgY29sb3IsIHh9IG9mIGNvbXB1dGVkLnBsdWdpbnMubGFuZ3VhZ2VzLmZhdm9yaXRlcykgeyAlPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjbGFuZ3VhZ2VzLWJhcilcIiB4PVwiPCU9IHgqNDYwICU+XCIgeT1cIjBcIiB3aWR0aD1cIjwlPSB2YWx1ZSo0NjAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIjwlPSBjb2xvciAlPlwiLz5cclxuICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgIDwvc3ZnPlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgY2VudGVyIGhvcml6b250YWwtd3JhcCBmaWxsLXdpZHRoXCI+XHJcbiAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7bmFtZSwgdmFsdWUsIGNvbG9yfSBvZiBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5mYXZvcml0ZXMpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjZW50ZXIgbm8td3JhcCBsYW5ndWFnZVwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbD1cIjwlPSBjb2xvciAlPlwiIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTggNGE0IDQgMCAxMDAgOCA0IDQgMCAwMDAtOHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDwlPSBuYW1lICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMpIHsgJT5cclxuICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgIDxoMiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjc1IDEuNWEuMjUuMjUgMCAwMC0uMjUuMjV2MTIuNWMwIC4xMzguMTEyLjI1LjI1LjI1aDEyLjVhLjI1LjI1IDAgMDAuMjUtLjI1VjEuNzVhLjI1LjI1IDAgMDAtLjI1LS4yNUgxLjc1ek0wIDEuNzVDMCAuNzg0Ljc4NCAwIDEuNzUgMGgxMi41QzE1LjIxNiAwIDE2IC43ODQgMTYgMS43NXYxMi41QTEuNzUgMS43NSAwIDAxMTQuMjUgMTZIMS43NUExLjc1IDEuNzUgMCAwMTAgMTQuMjVWMS43NXptOS4yMiAzLjcyYS43NS43NSAwIDAwMCAxLjA2TDEwLjY5IDggOS4yMiA5LjQ3YS43NS43NSAwIDEwMS4wNiAxLjA2bDItMmEuNzUuNzUgMCAwMDAtMS4wNmwtMi0yYS43NS43NSAwIDAwLTEuMDYgMHpNNi43OCA2LjUzYS43NS43NSAwIDAwLTEuMDYtMS4wNmwtMiAyYS43NS43NSAwIDAwMCAxLjA2bDIgMmEuNzUuNzUgMCAxMDEuMDYtMS4wNkw1LjMxIDhsMS40Ny0xLjQ3elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMudG90YWxDb3VudCAlPiBHaXN0PCU9IHMoY29tcHV0ZWQucGx1Z2lucy5naXN0cy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgPC9oMj5cclxuICAgICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi4zNDMgMTMuNjU3QTggOCAwIDExMTMuNjU3IDIuMzQzIDggOCAwIDAxMi4zNDMgMTMuNjU3ek02LjAzIDQuOTdhLjc1Ljc1IDAgMDAtMS4wNiAxLjA2TDYuOTQgOCA0Ljk3IDkuOTdhLjc1Ljc1IDAgMTAxLjA2IDEuMDZMOCA5LjA2bDEuOTcgMS45N2EuNzUuNzUgMCAxMDEuMDYtMS4wNkw5LjA2IDhsMS45Ny0xLjk3YS43NS43NSAwIDEwLTEuMDYtMS4wNkw4IDYuOTQgNi4wMyA0Ljk3elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04IC4yNWEuNzUuNzUgMCAwMS42NzMuNDE4bDEuODgyIDMuODE1IDQuMjEuNjEyYS43NS43NSAwIDAxLjQxNiAxLjI3OWwtMy4wNDYgMi45Ny43MTkgNC4xOTJhLjc1Ljc1IDAgMDEtMS4wODguNzkxTDggMTIuMzQ3bC0zLjc2NiAxLjk4YS43NS43NSAwIDAxLTEuMDg4LS43OWwuNzItNC4xOTRMLjgxOCA2LjM3NGEuNzUuNzUgMCAwMS40MTYtMS4yOGw0LjIxLS42MTFMNy4zMjcuNjY4QS43NS43NSAwIDAxOCAuMjV6bTAgMi40NDVMNi42MTUgNS41YS43NS43NSAwIDAxLS41NjQuNDFsLTMuMDk3LjQ1IDIuMjQgMi4xODRhLjc1Ljc1IDAgMDEuMjE2LjY2NGwtLjUyOCAzLjA4NCAyLjc2OS0xLjQ1NmEuNzUuNzUgMCAwMS42OTggMGwyLjc3IDEuNDU2LS41My0zLjA4NGEuNzUuNzUgMCAwMS4yMTYtLjY2NGwyLjI0LTIuMTgzLTMuMDk2LS40NWEuNzUuNzUgMCAwMS0uNTY0LS40MUw4IDIuNjk0di4wMDF6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5naXN0cy5zdGFyZ2F6ZXJzICU+IFN0YXJnYXplcjwlPSBzKGNvbXB1dGVkLnBsdWdpbnMuZ2lzdHMuc3RhcmdhemVycykgJT5cclxuICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNSAzLjI1YS43NS43NSAwIDExLTEuNSAwIC43NS43NSAwIDAxMS41IDB6bTAgMi4xMjJhMi4yNSAyLjI1IDAgMTAtMS41IDB2Ljg3OEEyLjI1IDIuMjUgMCAwMDUuNzUgOC41aDEuNXYyLjEyOGEyLjI1MSAyLjI1MSAwIDEwMS41IDBWOC41aDEuNWEyLjI1IDIuMjUgMCAwMDIuMjUtMi4yNXYtLjg3OGEyLjI1IDIuMjUgMCAxMC0xLjUgMHYuODc4YS43NS43NSAwIDAxLS43NS43NWgtNC41QS43NS43NSAwIDAxNSA2LjI1di0uODc4em0zLjc1IDcuMzc4YS43NS43NSAwIDExLTEuNSAwIC43NS43NSAwIDAxMS41IDB6bTMtOC43NWEuNzUuNzUgMCAxMDAtMS41Ljc1Ljc1IDAgMDAwIDEuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLmdpc3RzLmZvcmtzICU+IEZvcms8JT0gcyhjb21wdXRlZC5wbHVnaW5zLmdpc3RzLmZvcmtzKSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkgeyAlPlxyXG4gICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xNC4wNjQgMGE4Ljc1IDguNzUgMCAwMC02LjE4NyAyLjU2M2wtLjQ1OS40NThjLS4zMTQuMzE0LS42MTYuNjQxLS45MDQuOTc5SDMuMzFhMS43NSAxLjc1IDAgMDAtMS40OS44MzNMLjExIDcuNjA3YS43NS43NSAwIDAwLjQxOCAxLjExbDMuMTAyLjk1NGMuMDM3LjA1MS4wNzkuMS4xMjQuMTQ1bDIuNDI5IDIuNDI4Yy4wNDYuMDQ2LjA5NC4wODguMTQ1LjEyNWwuOTU0IDMuMTAyYS43NS43NSAwIDAwMS4xMS40MThsMi43NzQtMS43MDdhMS43NSAxLjc1IDAgMDAuODMzLTEuNDlWOS40ODVjLjMzOC0uMjg4LjY2NS0uNTkuOTc5LS45MDRsLjQ1OC0uNDU5QTguNzUgOC43NSAwIDAwMTYgMS45MzZWMS43NUExLjc1IDEuNzUgMCAwMDE0LjI1IDBoLS4xODZ6TTEwLjUgMTAuNjI1Yy0uMDg4LjA2LS4xNzcuMTE4LS4yNjYuMTc1bC0yLjM1IDEuNTIxLjU0OCAxLjc4MyAxLjk0OS0xLjJhLjI1LjI1IDAgMDAuMTE5LS4yMTN2LTIuMDY2ek0zLjY3OCA4LjExNkw1LjIgNS43NjZjLjA1OC0uMDkuMTE3LS4xNzguMTc2LS4yNjZIMy4zMDlhLjI1LjI1IDAgMDAtLjIxMy4xMTlsLTEuMiAxLjk1IDEuNzgyLjU0N3ptNS4yNi00LjQ5M0E3LjI1IDcuMjUgMCAwMTE0LjA2MyAxLjVoLjE4NmEuMjUuMjUgMCAwMS4yNS4yNXYuMTg2YTcuMjUgNy4yNSAwIDAxLTIuMTIzIDUuMTI3bC0uNDU5LjQ1OGExNS4yMSAxNS4yMSAwIDAxLTIuNDk5IDIuMDJsLTIuMzE3IDEuNS0yLjE0My0yLjE0MyAxLjUtMi4zMTdhMTUuMjUgMTUuMjUgMCAwMTIuMDItMi41bC40NTgtLjQ1OGguMDAyek0xMiA1YTEgMSAwIDExLTIgMCAxIDEgMCAwMTIgMHptLTguNDQgOS41NmExLjUgMS41IDAgMTAtMi4xMi0yLjEyYy0uNzM0LjczLTEuMDQ3IDIuMzMyLTEuMTUgMy4wMDNhLjIzLjIzIDAgMDAuMjY1LjI2NWMuNjcxLS4xMDMgMi4yNzMtLjQxNiAzLjAwNS0xLjE0OHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgUGFnZVNwZWVkIEluc2lnaHRzXHJcbiAgICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk03Ljc3NSAzLjI3NWEuNzUuNzUgMCAwMDEuMDYgMS4wNmwxLjI1LTEuMjVhMiAyIDAgMTEyLjgzIDIuODNsLTIuNSAyLjVhMiAyIDAgMDEtMi44MyAwIC43NS43NSAwIDAwLTEuMDYgMS4wNiAzLjUgMy41IDAgMDA0Ljk1IDBsMi41LTIuNWEzLjUgMy41IDAgMDAtNC45NS00Ljk1bC0xLjI1IDEuMjV6bS00LjY5IDkuNjRhMiAyIDAgMDEwLTIuODNsMi41LTIuNWEyIDIgMCAwMTIuODMgMCAuNzUuNzUgMCAwMDEuMDYtMS4wNiAzLjUgMy41IDAgMDAtNC45NSAwbC0yLjUgMi41YTMuNSAzLjUgMCAwMDQuOTUgNC45NWwxLjI1LTEuMjVhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2bC0xLjI1IDEuMjVhMiAyIDAgMDEtMi44MyAwelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci53ZWJzaXRlVXJsICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgIDwvZGl2PlxyXG4gICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZC5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjM0MyAxMy42NTdBOCA4IDAgMTExMy42NTcgMi4zNDMgOCA4IDAgMDEyLjM0MyAxMy42NTd6TTYuMDMgNC45N2EuNzUuNzUgMCAwMC0xLjA2IDEuMDZMNi45NCA4IDQuOTcgOS45N2EuNzUuNzUgMCAxMDEuMDYgMS4wNkw4IDkuMDZsMS45NyAxLjk3YS43NS43NSAwIDEwMS4wNi0xLjA2TDkuMDYgOGwxLjk3LTEuOTdhLjc1Ljc1IDAgMTAtMS4wNi0xLjA2TDggNi45NCA2LjAzIDQuOTd6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkLmVycm9yLm1lc3NhZ2UgJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwicm93IGZpbGwtd2lkdGhcIj5cclxuICAgICAgICAgICAgICA8c2VjdGlvbiBjbGFzcz1cImNhdGVnb3JpZXNcIj5cclxuICAgICAgICAgICAgICAgIDwlIGZvciAoY29uc3Qge3Njb3JlLCB0aXRsZX0gb2YgY29tcHV0ZWQucGx1Z2lucy5wYWdlc3BlZWQuc2NvcmVzKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJjYXRlZ29yaWUgY29sdW1uXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxMjAgMTIwXCIgd2lkdGg9XCI1MFwiIGhlaWdodD1cIjUwXCIgY2xhc3M9XCJnYXVnZSA8JT0gIU51bWJlci5pc05hTihzY29yZSkgPyAoc2NvcmUgPj0gMC45ID8gJ2hpZ2gnIDogc2NvcmUgPj0gMC41ID8gJ2F2ZXJhZ2UnIDogJ2xvdycpIDogJycgJT5cIj5cclxuICAgICAgICAgICAgICAgICAgICAgIDxjaXJjbGUgY2xhc3M9XCJnYXVnZS1iYXNlXCIgcj1cIjUzXCIgY3g9XCI2MFwiIGN5PVwiNjBcIj48L2NpcmNsZT5cclxuICAgICAgICAgICAgICAgICAgICAgIDwlIGlmICghTnVtYmVyLmlzTmFOKHNjb3JlKSkgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgICA8Y2lyY2xlIGNsYXNzPVwiZ2F1Z2UtYXJjXCIgdHJhbnNmb3JtPVwicm90YXRlKC05MCA2MCA2MClcIiByPVwiNTNcIiBjeD1cIjYwXCIgY3k9XCI2MFwiIHN0cm9rZS1kYXNoYXJyYXk9XCI8JT0gc2NvcmUgKiAzMjkgJT4gMzI5XCI+PC9jaXJjbGU+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDx0ZXh0IHg9XCI2MFwiIHk9XCI2MFwiIGRvbWluYW50LWJhc2VsaW5lPVwiY2VudHJhbFwiID48JT0gTWF0aC5yb3VuZChzY29yZSoxMDApICU+PC90ZXh0PlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPHRleHQgeD1cIjYwXCIgeT1cIjYwXCIgZG9taW5hbnQtYmFzZWxpbmU9XCJjZW50cmFsXCIgPi08L3RleHQ+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgICAgICAgPC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJ0aXRsZVwiPjwlPSB0aXRsZSAlPjwvc3Bhbj5cclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICA8JSB9ICU+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmhhYml0cykgeyAlPlxyXG4gICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgPGgyIGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTggMS41Yy0yLjM2MyAwLTQgMS42OS00IDMuNzUgMCAuOTg0LjQyNCAxLjYyNS45ODQgMi4zMDRsLjIxNC4yNTNjLjIyMy4yNjQuNDcuNTU2LjY3My44NDguMjg0LjQxMS41MzcuODk2LjYyMSAxLjQ5YS43NS43NSAwIDAxLTEuNDg0LjIxMWMtLjA0LS4yODItLjE2My0uNTQ3LS4zNy0uODQ3YTguNjk1IDguNjk1IDAgMDAtLjU0Mi0uNjhjLS4wODQtLjEtLjE3My0uMjA1LS4yNjgtLjMyQzMuMjAxIDcuNzUgMi41IDYuNzY2IDIuNSA1LjI1IDIuNSAyLjMxIDQuODYzIDAgOCAwczUuNSAyLjMxIDUuNSA1LjI1YzAgMS41MTYtLjcwMSAyLjUtMS4zMjggMy4yNTktLjA5NS4xMTUtLjE4NC4yMi0uMjY4LjMxOS0uMjA3LjI0NS0uMzgzLjQ1My0uNTQxLjY4MS0uMjA4LjMtLjMzLjU2NS0uMzcuODQ3YS43NS43NSAwIDAxLTEuNDg1LS4yMTJjLjA4NC0uNTkzLjMzNy0xLjA3OC42MjEtMS40ODkuMjAzLS4yOTIuNDUtLjU4NC42NzMtLjg0OC4wNzUtLjA4OC4xNDctLjE3My4yMTMtLjI1My41NjEtLjY3OS45ODUtMS4zMi45ODUtMi4zMDQgMC0yLjA2LTEuNjM3LTMuNzUtNC0zLjc1ek02IDE1LjI1YS43NS43NSAwIDAxLjc1LS43NWgyLjVhLjc1Ljc1IDAgMDEwIDEuNWgtMi41YS43NS43NSAwIDAxLS43NS0uNzV6TTUuNzUgMTJhLjc1Ljc1IDAgMDAwIDEuNWg0LjVhLjc1Ljc1IDAgMDAwLTEuNWgtNC41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgQ29kaW5nIGhhYml0c1xyXG4gICAgICAgICAgPC9oMj5cclxuICAgICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzLmVycm9yKSB7ICU+XHJcbiAgICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuMzQzIDEzLjY1N0E4IDggMCAxMTEzLjY1NyAyLjM0MyA4IDggMCAwMTIuMzQzIDEzLjY1N3pNNi4wMyA0Ljk3YS43NS43NSAwIDAwLTEuMDYgMS4wNkw2Ljk0IDggNC45NyA5Ljk3YS43NS43NSAwIDEwMS4wNiAxLjA2TDggOS4wNmwxLjk3IDEuOTdhLjc1Ljc1IDAgMTAxLjA2LTEuMDZMOS4wNiA4bDEuOTctMS45N2EuNzUuNzUgMCAxMC0xLjA2LTEuMDZMOCA2Ljk0IDYuMDMgNC45N3pcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLmhhYml0cy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgPHVsIGNsYXNzPVwiaGFiaXRzXCI+XHJcbiAgICAgICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5oYWJpdHMuaW5kZW50cy5zdHlsZSkgeyAlPlxyXG4gICAgICAgICAgICAgICAgICA8bGk+VXNlIDwlPSBjb21wdXRlZC5wbHVnaW5zLmhhYml0cy5pbmRlbnRzLnN0eWxlICU+IGZvciBpbmRlbnRzPC9saT5cclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgIDwlIGlmICghTnVtYmVyLmlzTmFOKGNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzLmNvbW1pdHMuaG91cikpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGxpPk1vc3RseSBwdXNoIGNvZGUgYXJvdW5kIDwlPSBjb21wdXRlZC5wbHVnaW5zLmhhYml0cy5jb21taXRzLmhvdXIgJT46MDA8L2xpPlxyXG4gICAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICAgIDwvdWw+XHJcbiAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubXVzaWMpIHsgJT5cclxuICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgIDxoMiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjUgOGE2LjUgNi41IDAgMTExMyAwIDYuNSA2LjUgMCAwMS0xMyAwek04IDBhOCA4IDAgMTAwIDE2QTggOCAwIDAwOCAwek02LjM3OSA1LjIyN0EuMjUuMjUgMCAwMDYgNS40NDJ2NS4xMTdhLjI1LjI1IDAgMDAuMzc5LjIxNGw0LjI2NC0yLjU1OWEuMjUuMjUgMCAwMDAtLjQyOEw2LjM3OSA1LjIyN3pcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLm11c2ljLm1vZGUgJT5cclxuICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwicm93IGZpbGwtd2lkdGhcIj5cclxuICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubXVzaWMucHJvdmlkZXIpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi4wMDIgMi43MjVhLjc1Ljc1IDAgMDEuNzk3LS42OTlDOC43OSAyLjQyIDEzLjU4IDcuMjEgMTMuOTc0IDEzLjIwMWEuNzUuNzUgMCAxMS0xLjQ5Ny4wOTggMTAuNTAyIDEwLjUwMiAwIDAwLTkuNzc2LTkuNzc2Ljc1Ljc1IDAgMDEtLjctLjc5OHpNMiAxM2ExIDEgMCAxMTIgMCAxIDEgMCAwMS0yIDB6bS44NC01Ljk1YS43NS43NSAwIDAwLS4xNzkgMS40ODljMi41MDkuMyA0LjUgMi4yOTEgNC44IDQuOGEuNzUuNzUgMCAxMDEuNDktLjE3OEE3LjAwMyA3LjAwMyAwIDAwMi44MzggNy4wNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIEZyb20gPCU9IGNvbXB1dGVkLnBsdWdpbnMubXVzaWMucHJvdmlkZXIgJT5cclxuICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5tdXNpYy5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGVycm9yXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjM0MyAxMy42NTdBOCA4IDAgMTExMy42NTcgMi4zNDMgOCA4IDAgMDEyLjM0MyAxMy42NTd6TTYuMDMgNC45N2EuNzUuNzUgMCAwMC0xLjA2IDEuMDZMNi45NCA4IDQuOTcgOS45N2EuNzUuNzUgMCAxMDEuMDYgMS4wNkw4IDkuMDZsMS45NyAxLjk3YS43NS43NSAwIDEwMS4wNi0xLjA2TDkuMDYgOGwxLjk3LTEuOTdhLjc1Ljc1IDAgMTAtMS4wNi0xLjA2TDggNi45NCA2LjAzIDQuOTd6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5tdXNpYy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubXVzaWMudHJhY2tzLmxlbmd0aCkgeyAlPlxyXG4gICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwidHJhY2tsaXN0XCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7bmFtZSA9IFwiXCIsIGFydGlzdCA9IFwiXCIsIGFydHdvcmsgPSBcIlwifSBvZiBjb21wdXRlZC5wbHVnaW5zLm11c2ljLnRyYWNrcykgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cInRyYWNrXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxpbWcgc3JjPVwiZGF0YTppbWFnZS9wbmc7YmFzZTY0LDwlPSBhcnR3b3JrICU+XCIgd2lkdGg9XCIzMlwiIGhlaWdodD1cIjMyXCIgYWx0PVwiXCIvPlxyXG4gICAgICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiaW5mb3NcIj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwibmFtZVwiPjwlPSBuYW1lICU+PC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImFydGlzdFwiPjwlPSBhcnRpc3QgJT48L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNzUgMS41YS4yNS4yNSAwIDAwLS4yNS4yNXY5LjVjMCAuMTM4LjExMi4yNS4yNS4yNWgyYS43NS43NSAwIDAxLjc1Ljc1djIuMTlsMi43Mi0yLjcyYS43NS43NSAwIDAxLjUzLS4yMmg2LjVhLjI1LjI1IDAgMDAuMjUtLjI1di05LjVhLjI1LjI1IDAgMDAtLjI1LS4yNUgxLjc1ek0wIDEuNzVDMCAuNzg0Ljc4NCAwIDEuNzUgMGgxMi41QzE1LjIxNiAwIDE2IC43ODQgMTYgMS43NXY5LjVBMS43NSAxLjc1IDAgMDExNC4yNSAxM0g4LjA2bC0yLjU3MyAyLjU3M0ExLjQ1NyAxLjQ1NyAwIDAxMyAxNC41NDNWMTNIMS43NUExLjc1IDEuNzUgMCAwMTAgMTEuMjV2LTkuNXpNOSA5YTEgMSAwIDExLTIgMCAxIDEgMCAwMTIgMHptLS4yNS01LjI1YS43NS43NSAwIDAwLTEuNSAwdjIuNWEuNzUuNzUgMCAwMDEuNSAwdi0yLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICAgIE5vIG11c2ljIHJlY2VudGx5IGxpc3RlbmVkXHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICA8JSB9ICU+XHJcblxyXG4gICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5wb3N0cykgeyAlPlxyXG4gICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgPGgyIGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTQuNDU2LjczNGExLjc1IDEuNzUgMCAwMTIuODI2LjUwNGwuNjEzIDEuMzI3YTMuMDgxIDMuMDgxIDAgMDAyLjA4NCAxLjcwN2wyLjQ1NC41ODRjMS4zMzIuMzE3IDEuOCAxLjk3Mi44MzIgMi45NEwxMS4wNiAxMGwzLjcyIDMuNzJhLjc1Ljc1IDAgMTEtMS4wNjEgMS4wNkwxMCAxMS4wNmwtMi4yMDQgMi4yMDVjLS45NjguOTY4LTIuNjIzLjUtMi45NC0uODMybC0uNTg0LTIuNDU0YTMuMDgxIDMuMDgxIDAgMDAtMS43MDctMi4wODRsLTEuMzI3LS42MTNhMS43NSAxLjc1IDAgMDEtLjUwNC0yLjgyNkw0LjQ1Ni43MzR6TTUuOTIgMS44NjZhLjI1LjI1IDAgMDAtLjQwNC0uMDcyTDEuNzk0IDUuNTE2YS4yNS4yNSAwIDAwLjA3Mi40MDRsMS4zMjguNjEzQTQuNTgyIDQuNTgyIDAgMDE1LjczIDkuNjNsLjU4NCAyLjQ1NGEuMjUuMjUgMCAwMC40Mi4xMmw1LjQ3LTUuNDdhLjI1LjI1IDAgMDAtLjEyLS40Mkw5LjYzIDUuNzNhNC41ODEgNC41ODEgMCAwMS0zLjA5OC0yLjUzN0w1LjkyIDEuODY2elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgUmVjZW50IGFydGljbGVzXHJcbiAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvdyBmaWxsLXdpZHRoXCI+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBvc3RzLmVycm9yKSB7ICU+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuMzQzIDEzLjY1N0E4IDggMCAxMTEzLjY1NyAyLjM0MyA4IDggMCAwMTIuMzQzIDEzLjY1N3pNNi4wMyA0Ljk3YS43NS43NSAwIDAwLTEuMDYgMS4wNkw2Ljk0IDggNC45NyA5Ljk3YS43NS43NSAwIDEwMS4wNiAxLjA2TDggOS4wNmwxLjk3IDEuOTdhLjc1Ljc1IDAgMTAxLjA2LTEuMDZMOS4wNiA4bDEuOTctMS45N2EuNzUuNzUgMCAxMC0xLjA2LTEuMDZMOCA2Ljk0IDYuMDMgNC45N3pcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLnBvc3RzLmVycm9yLm1lc3NhZ2UgJT5cclxuICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuMDAyIDIuNzI1YS43NS43NSAwIDAxLjc5Ny0uNjk5QzguNzkgMi40MiAxMy41OCA3LjIxIDEzLjk3NCAxMy4yMDFhLjc1Ljc1IDAgMTEtMS40OTcuMDk4IDEwLjUwMiAxMC41MDIgMCAwMC05Ljc3Ni05Ljc3Ni43NS43NSAwIDAxLS43LS43OTh6TTIgMTNhMSAxIDAgMTEyIDAgMSAxIDAgMDEtMiAwem0uODQtNS45NWEuNzUuNzUgMCAwMC0uMTc5IDEuNDg5YzIuNTA5LjMgNC41IDIuMjkxIDQuOCA0LjhhLjc1Ljc1IDAgMTAxLjQ5LS4xNzhBNy4wMDMgNy4wMDMgMCAwMDIuODM4IDcuMDV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICBGcm9tIDwlPSBjb21wdXRlZC5wbHVnaW5zLnBvc3RzLnNvdXJjZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5wb3N0cy5wb3N0cy5sZW5ndGgpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7dGl0bGUsIGRhdGV9IG9mIGNvbXB1dGVkLnBsdWdpbnMucG9zdHMucG9zdHMpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgcG9zdFwiPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTQuNzUgMGEuNzUuNzUgMCAwMS43NS43NVYyaDVWLjc1YS43NS43NSAwIDAxMS41IDBWMmgxLjI1Yy45NjYgMCAxLjc1Ljc4NCAxLjc1IDEuNzV2MTAuNUExLjc1IDEuNzUgMCAwMTEzLjI1IDE2SDIuNzVBMS43NSAxLjc1IDAgMDExIDE0LjI1VjMuNzVDMSAyLjc4NCAxLjc4NCAyIDIuNzUgMkg0Vi43NUEuNzUuNzUgMCAwMTQuNzUgMHptMCAzLjVoOC41YS4yNS4yNSAwIDAxLjI1LjI1VjZoLTExVjMuNzVhLjI1LjI1IDAgMDEuMjUtLjI1aDJ6bS0yLjI1IDR2Ni43NWMwIC4xMzguMTEyLjI1LjI1LjI1aDEwLjVhLjI1LjI1IDAgMDAuMjUtLjI1VjcuNWgtMTF6XCIvPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImluZm9zXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJkYXRlXCI+PCU9IGRhdGUgJT48L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cInRpdGxlXCI+PCU9IHRpdGxlICU+PC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNzUgMS41YS4yNS4yNSAwIDAwLS4yNS4yNXY5LjVjMCAuMTM4LjExMi4yNS4yNS4yNWgyYS43NS43NSAwIDAxLjc1Ljc1djIuMTlsMi43Mi0yLjcyYS43NS43NSAwIDAxLjUzLS4yMmg2LjVhLjI1LjI1IDAgMDAuMjUtLjI1di05LjVhLjI1LjI1IDAgMDAtLjI1LS4yNUgxLjc1ek0wIDEuNzVDMCAuNzg0Ljc4NCAwIDEuNzUgMGgxMi41QzE1LjIxNiAwIDE2IC43ODQgMTYgMS43NXY5LjVBMS43NSAxLjc1IDAgMDExNC4yNSAxM0g4LjA2bC0yLjU3MyAyLjU3M0ExLjQ1NyAxLjQ1NyAwIDAxMyAxNC41NDNWMTNIMS43NUExLjc1IDEuNzUgMCAwMTAgMTEuMjV2LTkuNXpNOSA5YTEgMSAwIDExLTIgMCAxIDEgMCAwMTIgMHptLS4yNS01LjI1YS43NS43NSAwIDAwLTEuNSAwdjIuNWEuNzUuNzUgMCAwMDEuNSAwdi0yLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICAgIE5vIHJlY2VudCBwb3N0c1xyXG4gICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIpIHsgJT5cclxuICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgIDxoMiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk00Ljc1IDBhLjc1Ljc1IDAgMDEuNzUuNzVWMmg1Vi43NWEuNzUuNzUgMCAwMTEuNSAwVjJoMS4yNWMuOTY2IDAgMS43NS43ODQgMS43NSAxLjc1djEwLjVBMS43NSAxLjc1IDAgMDExMy4yNSAxNkgyLjc1QTEuNzUgMS43NSAwIDAxMSAxNC4yNVYzLjc1QzEgMi43ODQgMS43ODQgMiAyLjc1IDJINFYuNzVBLjc1Ljc1IDAgMDE0Ljc1IDB6bTAgMy41aDguNWEuMjUuMjUgMCAwMS4yNS4yNVY2aC0xMVYzLjc1YS4yNS4yNSAwIDAxLjI1LS4yNWgyem0tMi4yNSA0djYuNzVjMCAuMTM4LjExMi4yNS4yNS4yNWgxMC41YS4yNS4yNSAwIDAwLjI1LS4yNVY3LjVoLTExelwiLz48L3N2Zz5cclxuICAgICAgICAgICAgQ29udHJpYnV0aW9ucyBjYWxlbmRhclxyXG4gICAgICAgICAgPC9oMj5cclxuICAgICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMi4zNDMgMTMuNjU3QTggOCAwIDExMTMuNjU3IDIuMzQzIDggOCAwIDAxMi4zNDMgMTMuNjU3ek02LjAzIDQuOTdhLjc1Ljc1IDAgMDAtMS4wNiAxLjA2TDYuOTQgOCA0Ljk3IDkuOTdhLjc1Ljc1IDAgMTAxLjA2IDEuMDZMOCA5LjA2bDEuOTcgMS45N2EuNzUuNzUgMCAxMDEuMDYtMS4wNkw5LjA2IDhsMS45Ny0xLjk3YS43NS43NSAwIDEwLTEuMDYtMS4wNkw4IDYuOTQgNi4wMyA0Ljk3elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIGlmICghY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhci5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk03Ljk5OCAxNC41YzIuODMyIDAgNS0xLjk4IDUtNC41IDAtMS40NjMtLjY4LTIuMTktMS44NzktMy4zODNsLS4wMzYtLjAzN2MtMS4wMTMtMS4wMDgtMi4zLTIuMjktMi44MzQtNC40MzQtLjMyMi4yNTYtLjYzLjU3OS0uODY0Ljk1My0uNDMyLjY5Ni0uNjIxIDEuNTgtLjA0NiAyLjczLjQ3My45NDcuNjcgMi4yODQtLjI3OCAzLjIzMi0uNjEuNjEtMS41NDUuODQtMi40MDMuNjMzYTIuNzg4IDIuNzg4IDAgMDEtMS40MzYtLjg3NEEzLjIxIDMuMjEgMCAwMDMgMTBjMCAyLjUzIDIuMTY0IDQuNSA0Ljk5OCA0LjV6TTkuNTMzLjc1M0M5LjQ5Ni4zNCA5LjE2LjAwOSA4Ljc3LjE0NiA3LjAzNS43NSA0LjM0IDMuMTg3IDUuOTk3IDYuNWMuMzQ0LjY4OS4yODUgMS4yMTguMDAzIDEuNS0uNDE5LjQxOS0xLjU0LjQ4Ny0yLjA0LS44MzItLjE3My0uNDU0LS42NTktLjc2Mi0xLjAzNS0uNDU0QzIuMDM2IDcuNDQgMS41IDguNzAyIDEuNSAxMGMwIDMuNTEyIDIuOTk4IDYgNi40OTggNnM2LjUtMi41IDYuNS02YzAtMi4xMzctMS4xMjgtMy4yNi0yLjMxMi00LjQzOC0xLjE5LTEuMTg0LTIuNDM2LTIuNDI1LTIuNjUzLTQuODF6XCIvPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICBDdXJyZW50IHN0cmVhayA8JT0gY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhci5zdHJlYWsuY3VycmVudCAlPiBkYXk8JT0gcyhjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyLnN0cmVhay5jdXJyZW50KSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNSAxLjc1YS43NS43NSAwIDAwLTEuNSAwdjEyLjVjMCAuNDE0LjMzNi43NS43NS43NWgxNC41YS43NS43NSAwIDAwMC0xLjVIMS41VjEuNzV6bTE0LjI4IDIuNTNhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2TDEwIDcuOTQgNy41MyA1LjQ3YS43NS43NSAwIDAwLTEuMDYgMEwzLjIyIDguNzJhLjc1Ljc1IDAgMDAxLjA2IDEuMDZMNyA3LjA2bDIuNDcgMi40N2EuNzUuNzUgMCAwMDEuMDYgMGw1LjI1LTUuMjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICB+PCU9IGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuYXZlcmFnZSAlPiBjb21taXRzIHBlciBkYXlcclxuICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhci5zdmcpIHsgJT5cclxuICAgICAgICAgICAgPCUtIGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuc3ZnICU+XHJcbiAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICA8JSB9ICU+XHJcblxyXG4gICAgICA8JSBpZiAoYmFzZS5tZXRhZGF0YSkgeyAlPlxyXG4gICAgICAgIDxmb290ZXI+XHJcbiAgICAgICAgICA8c3Bhbj5UaGVzZSBtZXRyaWNzIDwlPSAhY29tcHV0ZWQudG9rZW4uc2NvcGVzLmluY2x1ZGVzKFwicmVwb1wiKSA/IFwiZG9lcyBub3QgaW5jbHVkZVwiIDogXCJpbmNsdWRlc1wiICU+IHByaXZhdGUgY29udHJpYnV0aW9uczwvc3Bhbj5cclxuICAgICAgICAgIDxzcGFuPkxhc3QgdXBkYXRlZCA8JT0gbmV3IERhdGUoKSAlPjwvc3Bhbj5cclxuICAgICAgICA8L2Zvb3Rlcj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgIDwvZGl2PlxyXG4gIDwvZm9yZWlnbk9iamVjdD5cclxuPC9zdmc+Iiwic3R5bGUiOiIvKiBTVkcgZ2xvYmFsIGNvbnRleHQgKi9cclxuICBzdmcge1xyXG4gICAgZm9udC1mYW1pbHk6IC1hcHBsZS1zeXN0ZW0sIEJsaW5rTWFjU3lzdGVtRm9udCwgU2Vnb2UgVUksIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWYsIEFwcGxlIENvbG9yIEVtb2ppLCBTZWdvZSBVSSBFbW9qaTtcclxuICAgIGZvbnQtc2l6ZTogMTRweDtcclxuICAgIGNvbG9yOiAjNzc3Nzc3O1xyXG4gIH1cclxuXHJcbi8qIEhlYWRlcnMgKi9cclxuICBoMSwgaDIsIGgzIHtcclxuICAgIG1hcmdpbjogOHB4IDAgMnB4O1xyXG4gICAgcGFkZGluZzogMDtcclxuICAgIGNvbG9yOiAjMDM2NmQ2O1xyXG4gICAgZm9udC13ZWlnaHQ6IG5vcm1hbDtcclxuICB9XHJcbiAgaDEgc3ZnLCBoMiBzdmcsIGgzIHN2ZyB7XHJcbiAgICBmaWxsOiBjdXJyZW50Q29sb3I7XHJcbiAgfVxyXG4gIGgxIHtcclxuICAgIGZvbnQtc2l6ZTogMjBweDtcclxuICAgIGZvbnQtd2VpZ2h0OiBib2xkO1xyXG4gIH1cclxuICBoMiB7XHJcbiAgICBmb250LXNpemU6IDE2cHg7XHJcbiAgfVxyXG4gIGgzIHtcclxuICAgIGZvbnQtc2l6ZTogMTRweDtcclxuICB9XHJcblxyXG4vKiBGaWVsZHMgKi9cclxuICBzZWN0aW9uID4gLmZpZWxkIHtcclxuICAgIG1hcmdpbi1sZWZ0OiA1cHg7XHJcbiAgICBtYXJnaW4tcmlnaHQ6IDVweDtcclxuICB9XHJcbiAgLmZpZWxkIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBhbGlnbi1pdGVtczogY2VudGVyO1xyXG4gICAgbWFyZ2luLWJvdHRvbTogMnB4O1xyXG4gICAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcclxuICB9XHJcbiAgLmZpZWxkIHN2ZyB7XHJcbiAgICBtYXJnaW46IDAgOHB4O1xyXG4gICAgZmlsbDogIzk1OWRhNTtcclxuICAgIGZsZXgtc2hyaW5rOiAwO1xyXG4gIH1cclxuICAuZmllbGQuZXJyb3Ige1xyXG4gICAgY29sb3I6ICNjYjI0MzE7XHJcbiAgfVxyXG4gIC5maWVsZC5lcnJvciBzdmcge1xyXG4gICAgZmlsbDogI2NiMjQzMTtcclxuICB9XHJcblxyXG4vKiBEaXNwbGF5cyAqL1xyXG4gIC5yb3cge1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICB9XHJcbiAgLnJvdyBzZWN0aW9uIHtcclxuICAgIGZsZXg6IDEgMSAwO1xyXG4gIH1cclxuICAuY29sdW1uIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICB9XHJcbiAgLmNlbnRlciB7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcclxuICB9XHJcbiAgLmhvcml6b250YWwge1xyXG4gICAganVzdGlmeS1jb250ZW50OiBzcGFjZS1hcm91bmQ7XHJcbiAgfVxyXG4gIC5ob3Jpem9udGFsLXdyYXAge1xyXG4gICAgZmxleC13cmFwOiB3cmFwO1xyXG4gIH1cclxuICAuaG9yaXpvbnRhbCAuZmllbGQge1xyXG4gICAgZmxleDogMSAxIDA7XHJcbiAgfVxyXG4gIC5uby13cmFwIHtcclxuICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7XHJcbiAgfVxyXG4gIC5maWxsLXdpZHRoIHtcclxuICAgIHdpZHRoOiAxMDAlO1xyXG4gIH1cclxuXHJcbi8qIFVzZXIgYXZhdGFyICovXHJcbiAgLmF2YXRhciB7XHJcbiAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjMDAwMDAwO1xyXG4gICAgYm9yZGVyLXJhZGl1czogNTAlO1xyXG4gICAgbWFyZ2luOiAwIDZweDtcclxuICB9XHJcblxyXG4vKiBDb21taXQgY2FsZW5kYXIgKi9cclxuICAuY2FsZW5kYXIuZmllbGQge1xyXG4gICAgbWFyZ2luOiA0cHggMDtcclxuICAgIG1hcmdpbi1sZWZ0OiA3cHg7XHJcbiAgfVxyXG4gIC5jYWxlbmRhciAuZGF5IHtcclxuICAgIG91dGxpbmU6IDFweCBzb2xpZCByZ2JhKDI3LDMxLDM1LC4wNCk7XHJcbiAgICBvdXRsaW5lLW9mZnNldDogLTFweDtcclxuICB9XHJcblxyXG4vKiBQcm9ncmVzcyBiYXJzICovXHJcbiAgc3ZnLmJhciB7XHJcbiAgICBtYXJnaW46IDRweCAwO1xyXG4gIH1cclxuXHJcbi8qIExhbmd1YWdlICovXHJcbiAgLmZpZWxkLmxhbmd1YWdlIHtcclxuICAgIG1hcmdpbjogMCA4cHg7XHJcbiAgICBmbGV4LWdyb3c6IDA7XHJcbiAgfVxyXG5cclxuICAuZmllbGQubGFuZ3VhZ2Ugc21hbGwge1xyXG4gICAgbWFyZ2luLWxlZnQ6IDRweDtcclxuICAgIG9wYWNpdHk6IC43O1xyXG4gIH1cclxuXHJcbi8qIEhhYml0cyAqL1xyXG4gIC5oYWJpdHMge1xyXG4gICAgbWFyZ2luOiAwO1xyXG4gICAgbGlzdC1zdHlsZS10eXBlOiBub25lO1xyXG4gICAgcGFkZGluZy1sZWZ0OiAzN3B4O1xyXG4gIH1cclxuXHJcbi8qIEZvb3RlciAqL1xyXG4gIGZvb3RlciB7XHJcbiAgICBtYXJnaW4tdG9wOiA4cHg7XHJcbiAgICBmb250LXNpemU6IDEwcHg7XHJcbiAgICBmb250LXN0eWxlOiBpdGFsaWM7XHJcbiAgICBvcGFjaXR5OiAwLjU7XHJcbiAgICB0ZXh0LWFsaWduOiByaWdodDtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xyXG4gICAganVzdGlmeS1jb250ZW50OiBmbGV4LWVuZDtcclxuICB9XHJcblxyXG4vKiBTcGVlZCB0ZXN0IGNhdGVnb3JpZXMgKi9cclxuICAuY2F0ZWdvcmllcyB7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIGp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kO1xyXG4gICAgbWFyZ2luLXRvcDogNHB4O1xyXG4gIH1cclxuICAuY2F0ZWdvcmllIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIGZsZXg6IDEgMSAwO1xyXG4gIH1cclxuXHJcbi8qIEdhdWdlcyAqL1xyXG4gIC5nYXVnZSB7XHJcbiAgICBzdHJva2UtbGluZWNhcDogcm91bmQ7XHJcbiAgICBmaWxsOiBub25lO1xyXG4gIH1cclxuICAuZ2F1Z2UuaGlnaCB7XHJcbiAgICBjb2xvcjogIzE4YjY2MztcclxuICB9XHJcbiAgLmdhdWdlLmF2ZXJhZ2Uge1xyXG4gICAgY29sb3I6ICNmYjhjMDA7XHJcbiAgfVxyXG4gIC5nYXVnZS5sb3cge1xyXG4gICAgY29sb3I6ICNlNTM5MzU7XHJcbiAgfVxyXG4gIC5nYXVnZS1iYXNlLCAuZ2F1Z2UtYXJjIHtcclxuICAgIHN0cm9rZTogY3VycmVudENvbG9yO1xyXG4gICAgc3Ryb2tlLXdpZHRoOiAxMDtcclxuICB9XHJcbiAgLmdhdWdlLWJhc2Uge1xyXG4gICAgc3Ryb2tlLW9wYWNpdHk6IC4yO1xyXG4gIH1cclxuICAuZ2F1Z2UtYXJjIHtcclxuICAgIGZpbGw6IG5vbmU7XHJcbiAgICBzdHJva2UtZGFzaG9mZnNldDogMDtcclxuICAgIGFuaW1hdGlvbi1kZWxheTogMjUwbXM7XHJcbiAgICBhbmltYXRpb246IGFuaW1hdGlvbi1nYXVnZSAxcyBlYXNlIGZvcndhcmRzXHJcbiAgfVxyXG4gIC5nYXVnZSB0ZXh0IHtcclxuICAgIGZpbGw6IGN1cnJlbnRDb2xvcjtcclxuICAgIGZvbnQtc2l6ZTogNDBweDtcclxuICAgIGZvbnQtZmFtaWx5OiBtb25vc3BhY2U7XHJcbiAgICB0ZXh0LWFuY2hvcjogbWlkZGxlO1xyXG4gICAgZm9udC13ZWlnaHQ6IDYwMDtcclxuICB9XHJcbiAgLmdhdWdlIC50aXRsZSB7XHJcbiAgICBmb250LXNpemU6IDE4cHg7XHJcbiAgICBjb2xvcjogIzc3Nzc3NztcclxuICB9XHJcbiAgQGtleWZyYW1lcyBhbmltYXRpb24tZ2F1Z2Uge1xyXG4gICAgZnJvbSB7XHJcbiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IDAgMzI5O1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbi8qIE11c2ljIHBsdWdpbiAqL1xyXG4gIC50cmFja2xpc3Qge1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICAgIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47XHJcbiAgICBhbGlnbi1pdGVtczogZmxleC1zdGFydDtcclxuICAgIG1hcmdpbi1sZWZ0OiAyOHB4O1xyXG4gICAgbWFyZ2luLXRvcDogNHB4O1xyXG4gICAgd2lkdGg6IDEwMCU7XHJcbiAgfVxyXG4gIC50cmFjayB7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIGp1c3RpZnktY29udGVudDogY2VudGVyO1xyXG4gICAgbWFyZ2luLWJvdHRvbTogNHB4O1xyXG4gIH1cclxuICAudHJhY2sgaW1nIHtcclxuICAgIG1hcmdpbjogMCAxMHB4O1xyXG4gICAgYm9yZGVyLXJhZGl1czogN3B4O1xyXG4gIH1cclxuICAudHJhY2sgLm5hbWUge1xyXG4gICAgZm9udC1zaXplOiAxNHB4O1xyXG4gICAgbGluZS1oZWlnaHQ6IDE0cHg7XHJcbiAgfVxyXG4gIC50cmFjayAuYXJ0aXN0IHtcclxuICAgIGZvbnQtc2l6ZTogMTJweDtcclxuICAgIG9wYWNpdHk6IC43O1xyXG4gIH1cclxuXHJcbi8qIFBvc3RzIHBsdWdpbiAqL1xyXG4gIC5wb3N0IHtcclxuICAgIGFsaWduLWl0ZW1zOiBmbGV4LXN0YXJ0O1xyXG4gIH1cclxuICAucG9zdCAuaW5mb3Mge1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICAgIG1hcmdpbi1ib3R0b206IDRweDtcclxuICB9XHJcbiAgLnBvc3QgLmluZm9zIC50aXRsZSB7XHJcbiAgICBmb250LXNpemU6IDE0cHg7XHJcbiAgICB3aWR0aDogNDAwcHg7XHJcbiAgICB3aGl0ZS1zcGFjZTogbm9ybWFsO1xyXG4gICAgb3ZlcmZsb3c6IGhpZGRlbjtcclxuICAgIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzO1xyXG4gICAgbWF4LWhlaWdodDogNDBweDs7XHJcbiAgfVxyXG4gIC5wb3N0IC5pbmZvcyAuZGF0ZSB7XHJcbiAgICBmbGV4LXNocmluazogMDtcclxuICAgIGZvbnQtc2l6ZTogMTJweDtcclxuICAgIG9wYWNpdHk6IC43O1xyXG4gICAgd2lkdGg6IDQwcHg7XHJcbiAgICBwYWRkaW5nLXRvcDogMXB4O1xyXG4gIH1cclxuXHJcbi8qIEZhZGUgYW5pbWF0aW9uICovXHJcbiAgLmFmIHtcclxuICAgIG9wYWNpdHk6IDA7XHJcbiAgICBhbmltYXRpb246IGFuaW1hdGlvbi1mYWRlIDFzIGVhc2UgZm9yd2FyZHM7XHJcbiAgfVxyXG4gIEBrZXlmcmFtZXMgYW5pbWF0aW9uLWZhZGUge1xyXG4gICAgZnJvbSB7XHJcbiAgICAgIG9wYWNpdHk6IDA7XHJcbiAgICB9XHJcbiAgICB0byB7XHJcbiAgICAgIG9wYWNpdHk6IDE7XHJcbiAgICB9XHJcbiAgfVxyXG5cclxuLyogQ2FsZW5kYXIgKi9cclxuICA6cm9vdCB7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1iZzogI2ViZWRmMDtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwxLWJnOiAjOWJlOWE4O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYmc6ICM0MGM0NjM7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1MMy1iZzogIzMwYTE0ZTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUw0LWJnOiAjMjE2ZTM5O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwxLWJnOiAjZmZlZTRhO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwyLWJnOiAjZmZjNTAxO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwzLWJnOiAjZmU5NjAwO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUw0LWJnOiAjMDMwMDFjO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDQtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDMtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDEtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gIH0iLCJmb250cyI6IiJ9LCJ0ZXJtaW5hbCI6eyJxdWVyeSI6InF1ZXJ5IE1ldHJpY3Mge1xyXG4gIHVzZXIobG9naW46ICRsb2dpbikge1xyXG4gICAgZGF0YWJhc2VJZFxyXG4gICAgbmFtZVxyXG4gICAgbG9naW5cclxuICAgIGNyZWF0ZWRBdFxyXG4gICAgYXZhdGFyVXJsXHJcbiAgICB3ZWJzaXRlVXJsXHJcbiAgICBnaXN0cyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHJlcG9zaXRvcmllcyhsYXN0OiAkcmVwb3NpdG9yaWVzLCBpc0Zvcms6IGZhbHNlLCBvd25lckFmZmlsaWF0aW9uczogT1dORVIpIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgICB0b3RhbERpc2tVc2FnZVxyXG4gICAgICBub2RlcyB7XHJcbiAgICAgICAgbmFtZVxyXG4gICAgICAgIHdhdGNoZXJzIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgc3RhcmdhemVycyB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIGxhbmd1YWdlcyhmaXJzdDogNCkge1xyXG4gICAgICAgICAgZWRnZXMge1xyXG4gICAgICAgICAgICBzaXplXHJcbiAgICAgICAgICAgIG5vZGUge1xyXG4gICAgICAgICAgICAgIGNvbG9yXHJcbiAgICAgICAgICAgICAgbmFtZVxyXG4gICAgICAgICAgICB9XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfVxyXG4gICAgICAgIGlzc3Vlc19vcGVuOiBpc3N1ZXMoc3RhdGVzOiBPUEVOKSB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIGlzc3Vlc19jbG9zZWQ6IGlzc3VlcyhzdGF0ZXM6IENMT1NFRCkge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBwcl9vcGVuOiBwdWxsUmVxdWVzdHMoc3RhdGVzOiBPUEVOKSB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHByX21lcmdlZDogcHVsbFJlcXVlc3RzKHN0YXRlczogTUVSR0VEKSB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHJlbGVhc2VzIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgZm9ya0NvdW50XHJcbiAgICAgICAgbGljZW5zZUluZm8ge1xyXG4gICAgICAgICAgc3BkeElkXHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICBwYWNrYWdlcyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHN0YXJyZWRSZXBvc2l0b3JpZXMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICB3YXRjaGluZyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHNwb25zb3JzaGlwc0FzU3BvbnNvciB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHNwb25zb3JzaGlwc0FzTWFpbnRhaW5lciB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIGNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uIHtcclxuICAgICAgdG90YWxSZXBvc2l0b3JpZXNXaXRoQ29udHJpYnV0ZWRDb21taXRzXHJcbiAgICAgIHRvdGFsQ29tbWl0Q29udHJpYnV0aW9uc1xyXG4gICAgICByZXN0cmljdGVkQ29udHJpYnV0aW9uc0NvdW50XHJcbiAgICAgIHRvdGFsSXNzdWVDb250cmlidXRpb25zXHJcbiAgICAgIHRvdGFsUHVsbFJlcXVlc3RDb250cmlidXRpb25zXHJcbiAgICAgIHRvdGFsUHVsbFJlcXVlc3RSZXZpZXdDb250cmlidXRpb25zXHJcbiAgICB9XHJcbiAgICBjYWxlbmRhcjpjb250cmlidXRpb25zQ29sbGVjdGlvbihmcm9tOiAkY2FsZW5kYXIuZnJvbSwgdG86ICRjYWxlbmRhci50bykge1xyXG4gICAgICBjb250cmlidXRpb25DYWxlbmRhciB7XHJcbiAgICAgICAgd2Vla3Mge1xyXG4gICAgICAgICAgY29udHJpYnV0aW9uRGF5cyB7XHJcbiAgICAgICAgICAgIGNvbG9yXHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICByZXBvc2l0b3JpZXNDb250cmlidXRlZFRvIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgZm9sbG93ZXJzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgZm9sbG93aW5nIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgaXNzdWVDb21tZW50cyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIG9yZ2FuaXphdGlvbnMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgfVxyXG59XHJcbiIsImltYWdlIjoiPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgd2lkdGg9XCI0ODBcIiBoZWlnaHQ9XCI8JT0gNDhcclxuICArICghIWJhc2UuaGVhZGVyKSo2MlxyXG4gICsgKCEhYmFzZS5tZXRhZGF0YSkqMTA4XHJcbiAgKyAoISFiYXNlLmFjdGl2aXR5KSoxMDhcclxuICArICghIWJhc2UuY29tbXVuaXR5KSo5NFxyXG4gICsgKCEhYmFzZS5yZXBvc2l0b3JpZXMpKjE0MlxyXG4gICsgKCghIWJhc2UucmVwb3NpdG9yaWVzKSooISFjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMpKSoxOFxyXG4gICsgKCghIWJhc2UucmVwb3NpdG9yaWVzKSooISFjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwKSkqMTAyXHJcbiAgKyAoKCEhYmFzZS5yZXBvc2l0b3JpZXMpKighIWNvbXB1dGVkLnBsdWdpbnMubGluZXMpKSozNFxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5wYWdlc3BlZWQpKjExMFxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMpKjEyNFxyXG4gICsgTWF0aC5tYXgoMCwgKCgoISFiYXNlLm1ldGFkYXRhKSsoISFiYXNlLmhlYWRlcikrKCghIWJhc2UuYWN0aXZpdHkpfHwoISFiYXNlLmNvbW11bml0eSkpKyghIWJhc2UucmVwb3NpdG9yaWVzKSsoISFjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkrKCEhY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMpKS0xKSkqMjBcclxuJT5cIj5cclxuICA8JVxyXG4gICAgbWV0YS4kID0gYDxzcGFuIGNsYXNzPVwicHMxLXBhdGhcIj4ke2Ake3VzZXIubG9naW59YC50b0xvY2FsZUxvd2VyQ2FzZSgpfUBtZXRyaWNzPC9zcGFuPjo8c3BhbiBjbGFzcz1cInBzMS1sb2NhdGlvblwiPn48L3NwYW4+JHtjb21wdXRlZC50b2tlbi5zY29wZXMuaW5jbHVkZXMoXCJyZXBvXCIpID8gXCIjXCIgOiBcIiRcIn1gXHJcbiAgICBtZXRhLmFuaW1hdGlvbnMgPSAhbWV0YS5wbGFjZWhvbGRlciA/IHtzdGRpbjouMTYsIHN0ZG91dDouMjgsIGxlbmd0aDooMitPYmplY3Qua2V5cyhiYXNlKS5sZW5ndGgrT2JqZWN0LmtleXMoY29tcHV0ZWQucGx1Z2lucykubGVuZ3RoKX0gOiB7c3RkaW46MCwgc3Rkb3V0OjAsIGxlbmd0aDowfVxyXG4gICU+XHJcblxyXG4gIDxkZWZzPjxzdHlsZT48JT0gZm9udHMgJT48L3N0eWxlPjwvZGVmcz5cclxuXHJcbiAgPHN0eWxlPlxyXG4gICAgPCU9IHN0eWxlICU+XHJcbiAgICAgIC5zdGRpbiwgLnN0ZG91dCB7XHJcbiAgICAgICAgYW5pbWF0aW9uLWR1cmF0aW9uOiA8JT0gbWV0YS5hbmltYXRpb25zLnN0ZGluICU+cztcclxuICAgICAgfVxyXG4gICAgICAuc3Rkb3V0IHtcclxuICAgICAgICBhbmltYXRpb24tZHVyYXRpb246IDwlPSBtZXRhLmFuaW1hdGlvbnMuc3Rkb3V0ICU+cztcclxuICAgICAgfVxyXG4gICAgICA8JSBmb3IgKGxldCBpID0gMCwgZCA9IDA7IGkgPCBtZXRhLmFuaW1hdGlvbnMubGVuZ3RoOyBpKyssIGQrPW1ldGEuYW5pbWF0aW9ucy5zdGRpbittZXRhLmFuaW1hdGlvbnMuc3Rkb3V0KSB7ICU+XHJcbiAgICAgICAgLnN0ZGluOm50aC1vZi10eXBlKDwlPSBpKzEgJT4pIHtcclxuICAgICAgICAgIGFuaW1hdGlvbi1kZWxheTogPCU9IGQgJT5zO1xyXG4gICAgICAgIH1cclxuICAgICAgICAuc3Rkb3V0Om50aC1vZi10eXBlKDwlPSBpKzIgJT4pIHtcclxuICAgICAgICAgIGFuaW1hdGlvbi1kZWxheTogPCU9IGQrbWV0YS5hbmltYXRpb25zLnN0ZGluICU+cztcclxuICAgICAgICB9XHJcbiAgICAgICAgPCUgaWYgKGkgPT09IG1ldGEuYW5pbWF0aW9ucy5sZW5ndGgtMSkgeyAlPlxyXG4gICAgICAgICAgZm9vdGVyIHtcclxuICAgICAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiA8JT0gZCAlPnM7XHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgPCUgfSAlPlxyXG4gICAgICA8JSB9ICU+XHJcbiAgPC9zdHlsZT5cclxuXHJcbiAgPGZvcmVpZ25PYmplY3QgeD1cIjBcIiB5PVwiMFwiIHdpZHRoPVwiMTAwJVwiIGhlaWdodD1cIjEwMCVcIj5cclxuICAgIDxkaXYgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hodG1sXCIgeG1sbnM6eGxpbms9XCJodHRwOi8vd3d3LnczLm9yZy8xOTk5L3hsaW5rXCI+XHJcblxyXG4gICAgICA8ZGl2IGNsYXNzPVwiaGVhZGVyXCI+XHJcbiAgICAgICAgPHNwYW4gY2xhc3M9XCJ0aXRsZVwiPjwvc3Bhbj5cclxuICAgICAgICA8ZGl2IGNsYXNzPVwiYnV0dG9uc1wiPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cImJ1dHRvblwiPuKUgDwvZGl2PlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cImJ1dHRvblwiPuKWoTwvZGl2PlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cImJ1dHRvbiBleGl0XCI+4pyVPC9kaXY+XHJcbiAgICAgICAgPC9kaXY+XHJcbiAgICAgIDwvZGl2PlxyXG5cclxuPHByZT48JSMgLSU+XHJcbjwlIGlmIChiYXNlLm1ldGFkYXRhKSB7ICU+XHJcbjxkaXYgY2xhc3M9XCJiYW5uZXJcIj48JSMgLSU+XHJcbkdpdEh1YiBtZXRyaWNzIGdlbmVyYXRvciA8JT0gbWV0YS52ZXJzaW9uICU+XHJcblRoZXNlIGdlbmVyYXRlZCBtZXRyaWNzIGNvbWVzIHdpdGggQUJTT0xVVEVMWSBOT1xyXG5XQVJSQU5UWSwgdG8gdGhlIGV4dGVudCBwZXJtaXR0ZWQgYnkgYXBwbGljYWJsZSBsYXcuXHJcblxyXG5MYXN0IGdlbmVyYXRlZDogPCU9IG5ldyBEYXRlKCkudG9HTVRTdHJpbmcoKSAlPlxyXG48L2Rpdj48JSB9IC0lPlxyXG48JSMgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSAtJT5cclxuPCUgaWYgKGJhc2UuaGVhZGVyKSB7ICU+XHJcbjxkaXYgY2xhc3M9XCJzdGRpblwiPjwlLSBtZXRhLiQgJT4gd2hvYW1pPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG48Yj48JT0gdXNlci5uYW1lIHx8IHVzZXIubG9naW4gJT48L2I+IHJlZ2lzdGVyZWQ9PCU9IGNvbXB1dGVkLnJlZ2lzdHJhdGlvbi5tYXRjaCgvXi4rPyBbeW1dLylbMF0ucmVwbGFjZSgvIC9nLCBcIlwiKSAlPiwgdWlkPTwlPSBgJHt1c2VyLmRhdGFiYXNlSWR9YC5zdWJzdHIoLTQpICU+LCBnaWQ9PCU9IHVzZXIub3JnYW5pemF0aW9ucy50b3RhbENvdW50ICU+XHJcbiAgY29udHJpYnV0ZWQgdG8gPCU9IHVzZXIucmVwb3NpdG9yaWVzQ29udHJpYnV0ZWRUby50b3RhbENvdW50ICU+IHJlcG9zaXRvcjwlPSBzKHVzZXIucmVwb3NpdG9yaWVzQ29udHJpYnV0ZWRUby50b3RhbENvdW50LCBcInlcIikgJT4gPGI+PCUgZm9yIChjb25zdCBbeCwge2NvbG9yfV0gb2YgT2JqZWN0LmVudHJpZXMoY29tcHV0ZWQuY2FsZW5kYXIpKSB7IC0lPjxzcGFuIHN0eWxlPVwiY29sb3I6PCU9IGNvbG9yICU+XCI+Izwvc3Bhbj48JSB9ICU+PC9iPlxyXG4gIGZvbGxvd2VkIGJ5IDxiPjwlPSB1c2VyLmZvbGxvd2Vycy50b3RhbENvdW50ICU+PC9iPiB1c2VyPCU9IHModXNlci5mb2xsb3dlcnMudG90YWxDb3VudCkgJT5cclxuPC9kaXY+PCUgfSAtJT5cclxuPCUjID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0gLSU+XHJcbjwlIGlmICgoYmFzZS5hY3Rpdml0eSl8fChiYXNlLmNvbW11bml0eSkpIHsgJT5cclxuPGRpdiBjbGFzcz1cInN0ZGluXCI+PCUtIG1ldGEuJCAlPiBnaXQgc3RhdHVzPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG48JSBpZiAoYmFzZS5hY3Rpdml0eSkgeyAtJT5cclxuPGI+UmVjZW50IGFjdGl2aXR5PC9iPlxyXG4gIDxiPjwlPSBgJHtjb21wdXRlZC5jb21taXRzfWAucGFkU3RhcnQoNSkgJT48L2I+IGNvbW1pdDwlPSBzKGNvbXB1dGVkLmNvbW1pdHMpICU+XHJcbiAgPGI+PCU9IGAke3VzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxQdWxsUmVxdWVzdFJldmlld0NvbnRyaWJ1dGlvbnN9YC5wYWRTdGFydCg1KSAlPjwvYj4gcHVsbCByZXF1ZXN0PCU9IHModXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0UmV2aWV3Q29udHJpYnV0aW9ucykgJT4gcmV2aWV3ZWRcclxuICA8Yj48JT0gYCR7dXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0Q29udHJpYnV0aW9uc31gLnBhZFN0YXJ0KDUpICU+PC9iPiBwdWxsIHJlcXVlc3Q8JT0gcyh1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsUHVsbFJlcXVlc3RDb250cmlidXRpb25zKSAlPiBvcGVuZWRcclxuICA8Yj48JT0gYCR7dXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbElzc3VlQ29udHJpYnV0aW9uc31gLnBhZFN0YXJ0KDUpICU+PC9iPiBpc3N1ZTwlPSBzKHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxJc3N1ZUNvbnRyaWJ1dGlvbnMpICU+IG9wZW5lZFxyXG4gIDxiPjwlPSBgJHt1c2VyLmlzc3VlQ29tbWVudHMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiBpc3N1ZSBjb21tZW50PCU9IHModXNlci5pc3N1ZUNvbW1lbnRzLnRvdGFsQ291bnQpICU+XHJcbjwlIH0gLSU+XHJcbjwlIGlmICgoYmFzZS5hY3Rpdml0eSkmJihiYXNlLmNvbW11bml0eSkpIHsgLSU+XHJcblxyXG48JSB9IC0lPlxyXG48JSBpZiAoYmFzZS5jb21tdW5pdHkpIHsgLSU+XHJcbjxiPlRyYWNrZWQgYWN0aXZpdHk8L2I+XHJcbiAgPGI+PCU9IGAke3VzZXIuZm9sbG93aW5nLnRvdGFsQ291bnR9YC5wYWRTdGFydCg1KSAlPjwvYj4gdXNlcjwlPSBzKHVzZXIuZm9sbG93ZXJzLnRvdGFsQ291bnQpICU+IGZvbGxvd2VkXHJcbiAgPGI+PCU9IGAke3VzZXIuc3BvbnNvcnNoaXBzQXNTcG9uc29yLnRvdGFsQ291bnR9YC5wYWRTdGFydCg1KSAlPjwvYj4gcmVwb3NpdG9yPCU9IHModXNlci5zcG9uc29yc2hpcHNBc1Nwb25zb3IudG90YWxDb3VudCwgXCJ5XCIpICU+IHNwb25zb3JlZFxyXG4gIDxiPjwlPSBgJHt1c2VyLnN0YXJyZWRSZXBvc2l0b3JpZXMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiByZXBvc2l0b3I8JT0gcyh1c2VyLnN0YXJyZWRSZXBvc2l0b3JpZXMudG90YWxDb3VudCwgXCJ5XCIpICU+IHN0YXJyZWRcclxuICA8Yj48JT0gYCR7dXNlci53YXRjaGluZy50b3RhbENvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+IHJlcG9zaXRvcjwlPSBzKHVzZXIud2F0Y2hpbmcudG90YWxDb3VudCwgXCJ5XCIpICU+IHdhdGNoZWRcclxuPCUgfSAtJT5cclxuPC9kaXY+PCUgfSAtJT5cclxuPCUjID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0gLSU+XHJcbjwlIGlmIChiYXNlLnJlcG9zaXRvcmllcykgeyAlPlxyXG48ZGl2IGNsYXNzPVwic3RkaW5cIj48JS0gbWV0YS4kICU+IGxzIC1saCBnaXRodWIvcmVwb3NpdG9yaWVzPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG5Ub3RhbCA8JT0gdXNlci5yZXBvc2l0b3JpZXMudG90YWxDb3VudCAlPiByZXBvc2l0b3I8JT0gcyh1c2VyLnJlcG9zaXRvcmllcy50b3RhbENvdW50LCBcInlcIikgJT4gLSA8JT0gY29tcHV0ZWQuZGlza1VzYWdlICU+XHJcbjwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMpIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy5lcnJvcikgeyAtJT5cclxuLS0tLSAgPGI+ICAgICA8L2I+ICB2aWV3cyA8c3BhbiBjbGFzcz1cImVycm9yXCI+KDwlPSBjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMuZXJyb3IubWVzc2FnZSAlPik8L3NwYW4+XHJcbjwlIH0gZWxzZSB7IC0lPlxyXG4tci0tICA8Yj48JT0gYCR7Y29tcHV0ZWQucGx1Z2lucy50cmFmZmljLnZpZXdzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICB2aWV3c1xyXG48JSB9fSAtJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy5zdGFyZ2F6ZXJzfWAucGFkU3RhcnQoNSkgJT48L2I+ICBzdGFyZ2F6ZXI8JT0gcyhjb21wdXRlZC5yZXBvc2l0b3JpZXMuc3RhcmdhemVycykgJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy5mb3Jrc31gLnBhZFN0YXJ0KDUpICU+PC9iPiAgZm9yazwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy5mb3JrcykgJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy53YXRjaGVyc31gLnBhZFN0YXJ0KDUpICU+PC9iPiAgd2F0Y2hlcjwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy53YXRjaGVycykgJT5cclxuZHIteCAgPGI+PCU9IGAke3VzZXIucGFja2FnZXMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAgcGFja2FnZTwlPSBzKHVzZXIucGFja2FnZXMudG90YWxDb3VudCkgJT5cclxuZHIteCAgPGI+PCU9IGAke3VzZXIuZ2lzdHMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAgZ2lzdDwlPSBzKHVzZXIuZ2lzdHMudG90YWxDb3VudCkgJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXApIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IpIHsgLSU+XHJcbmQtLS0gIDxiPiAgICAgPC9iPiAgSVNTVUVTIDxzcGFuIGNsYXNzPVwiZXJyb3JcIj4oPCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IubWVzc2FnZSAlPik8L3NwYW4+XHJcbmQtLS0gIDxiPiAgICAgPC9iPiAgUFVMTF9SRVFVRVNUUyA8c3BhbiBjbGFzcz1cImVycm9yXCI+KDwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmVycm9yLm1lc3NhZ2UgJT4pPC9zcGFuPlxyXG48JSB9IGVsc2UgeyAtJT5cclxuZHIteCAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICBJU1NVRVNcclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLm9wZW59YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUnOKUgOKUgCBvcGVuXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jbG9zZWR9YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUlOKUgOKUgCBjbG9zZWRcclxuZHIteCAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICBQVUxMX1JFUVVFU1RTXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm9wZW59YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUnOKUgOKUgCBvcGVuXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm1lcmdlZH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAg4pSU4pSA4pSAIG1lcmdlZFxyXG48JSB9fSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLmxpY2Vuc2VzLmZhdm9yaXRlLmxlbmd0aCkgeyAtJT5cclxuZHIteCAgICAgICAgIExJQ0VOU0VcclxuLXItLSAgICAgICAgIOKUlOKUgOKUgCA8JT0gY29tcHV0ZWQubGljZW5zZXMuZmF2b3JpdGUgJT5cclxuPCUgfSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMpIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IpIHsgJT5cclxuPHNwYW4gY2xhc3M9XCJkaWZmIGVycm9yXCI+QEAgPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IubWVzc2FnZSAlPiBAQDwvc3Bhbj48JSB9IGVsc2UgeyAlPlxyXG48c3BhbiBjbGFzcz1cImRpZmZcIj5AQCAtPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZGVsZXRlZCAlPiArPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuYWRkZWQgJT4gQEA8L3NwYW4+XHJcbjwlIH19IC0lPlxyXG48L2Rpdj48JSB9IC0lPlxyXG48JSMgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGFuZ3VhZ2VzKSB7ICU+XHJcbjxkaXYgY2xhc3M9XCJzdGRpblwiPjwlLSBtZXRhLiQgJT4gbG9jYWxlPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG48JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IpIHsgLSU+XHJcbjxzcGFuIGNsYXNzPVwiZXJyb3JcIj48JT0gY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IubWVzc2FnZSAlPjwvc3Bhbj48JSMgLSU+XHJcbjwlIH0gZWxzZSB7IGZvciAoY29uc3Qge25hbWUsIHZhbHVlfSBvZiBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5mYXZvcml0ZXMpIHsgLSU+XHJcbjxiPjwlPSBuYW1lLnRvTG9jYWxlVXBwZXJDYXNlKCkucGFkRW5kKDEyKSAlPjwvYj4gWzwlPSBcIiNcIi5yZXBlYXQoTWF0aC5jZWlsKDEwMCp2YWx1ZS81KSkucGFkRW5kKDIwKSAlPl0gPCU9ICgxMDAqdmFsdWUpLnRvRml4ZWQoMikucGFkRW5kKDUpICU+JVxyXG48JSB9fSAtJT5cclxuPC9kaXY+PCUgfSAtJT5cclxuPCUjID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0gLSU+XHJcbjwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkgeyAlPlxyXG48ZGl2IGNsYXNzPVwic3RkaW5cIj48JS0gbWV0YS4kICU+IGN1cmwgLUkgPCU9IHVzZXIud2Vic2l0ZVVybCAlPjwvZGl2PjwlIyAtJT5cclxuPGRpdiBjbGFzcz1cInN0ZG91dFwiPjwlIyAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkLmVycm9yKSB7IC0lPlxyXG48c3BhbiBjbGFzcz1cImVycm9yXCI+PCU9IGNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkLmVycm9yLm1lc3NhZ2UgJT48L3NwYW4+PCUgfSBlbHNlIHsgLSU+XHJcbjxiPlVzZXItQWdlbnQ8L2I+OiBHb29nbGUgUGFnZVNwZWVkIEFQSVxyXG48Yj5Mb2NhdGlvbjwvYj46IDwlPSB1c2VyLndlYnNpdGVVcmwgJT5cclxuPCUgZm9yIChjb25zdCB7c2NvcmUsIHRpdGxlfSBvZiBjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZC5zY29yZXMpIHsgLSU+XHJcbjxiPjwlPSBgWC0ke3RpdGxlLnJlcGxhY2UoLyAvZywgXCItXCIpfWAgJT48L2I+OiA8JT0gIU51bWJlci5pc05hTihzY29yZSkgPyBNYXRoLnJvdW5kKHNjb3JlKjEwMCkgOiBcIi1cIiAlPiVcclxuPCUgfX0gLSU+XHJcbjwvZGl2PjwlIH0gLSU+XHJcbjwlIyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09IC0lPlxyXG48JSBpZiAoYmFzZS5tZXRhZGF0YSkgeyAtJT5cclxuXHJcbjxmb290ZXI+Q29ubmVjdGlvbiByZXNldCBieSA8JT0gTWF0aC5mbG9vcigyNTYqTWF0aC5yYW5kb20oKSkgJT4uPCU9IE1hdGguZmxvb3IoMjU2Kk1hdGgucmFuZG9tKCkpICU+LjwlPSBNYXRoLmZsb29yKDI1NipNYXRoLnJhbmRvbSgpKSAlPi48JT0gTWF0aC5mbG9vcigyNTYqTWF0aC5yYW5kb20oKSkgJT48L2Zvb3Rlcj48JSMgLSU+XHJcbjwlIH0gLSU+PC9wcmU+XHJcblxyXG4gICAgPC9kaXY+XHJcbiAgPC9mb3JlaWduT2JqZWN0PlxyXG48L3N2Zz5cclxuXHJcbiIsInN0eWxlIjoiLyogU1ZHIGdsb2JhbCBjb250ZXh0ICovXHJcbiAgc3ZnIHtcclxuICAgIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgICBmb250LXNpemU6IDE0cHg7XHJcbiAgICBjb2xvcjogIzc3Nzc3NztcclxuICB9XHJcblxyXG4vKiBUaXRsZSBiYXIgKi9cclxuICAuaGVhZGVyIHtcclxuICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgIHRvcDogMDtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47XHJcbiAgICB3aWR0aDogMTAwJTtcclxuICAgIGhlaWdodDogMjBweDtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICBwYWRkaW5nOiAwIDhweDtcclxuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICBib3JkZXItdG9wLWxlZnQtcmFkaXVzOiA1cHg7XHJcbiAgICBib3JkZXItdG9wLXJpZ2h0LXJhZGl1czogNXB4O1xyXG4gICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KCM1MDRiNDUgMCUsIzNjM2IzNyAxMDAlKTtcclxuICB9XHJcblxyXG4gIC50aXRsZSB7XHJcbiAgICBjb2xvcjogI2Q1ZDBjZTtcclxuICAgIGZvbnQtc2l6ZTogMTZweDtcclxuICB9XHJcblxyXG4gIC5idXR0b25zIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBhbGlnbi1pdGVtczogY2VudGVyO1xyXG4gIH1cclxuXHJcbiAgLmJ1dHRvbiB7XHJcbiAgICBjb2xvcjogYmxhY2s7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgICBtYXJnaW4tcmlnaHQ6IDVweDtcclxuICAgIGZvbnQtc2l6ZTogOHB4O1xyXG4gICAgaGVpZ2h0OiAxMnB4O1xyXG4gICAgd2lkdGg6IDEycHg7XHJcbiAgICBib3JkZXItcmFkaXVzOiAxMDAlO1xyXG4gICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KCM3ZDc4NzEgMCUsICM1OTU5NTMgMTAwJSk7XHJcbiAgICB0ZXh0LXNoYWRvdzogMHB4IDFweCAwcHggcmdiYSgyNTUsMjU1LDI1NSwwLjIpO1xyXG4gIH1cclxuXHJcbiAgLmJ1dHRvbi5leGl0IHtcclxuICAgIGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCgjZjM3NDU4IDAlLCAjZGU0YzEyIDEwMCUpO1xyXG4gIH1cclxuXHJcbi8qIFRlcm1pbmFsICovXHJcbiAgcHJlLCAuYmFubmVyLCBmb290ZXIge1xyXG4gICAgbWFyZ2luOiAwO1xyXG4gICAgZm9udC1mYW1pbHk6ICdDb3VyaWVyIFByaW1lJztcclxuICAgIGNvbG9yOiAjREREREREO1xyXG4gIH1cclxuICBwcmUge1xyXG4gICAgYmFja2dyb3VuZDogIzQyMDkyQjtcclxuICAgIHBhZGRpbmc6IDEycHg7XHJcbiAgICBib3JkZXItcmFkaXVzOiA1cHg7XHJcbiAgfVxyXG4gIC5iYW5uZXIsIGZvb3RlciB7XHJcbiAgICBjb2xvcjogI0FFOURBNztcclxuICB9XHJcblxyXG4vKiBQcm9tcHQgKi9cclxuICAucHMxLXBhdGgge1xyXG4gICAgY29sb3I6ICM3RURBMjk7XHJcbiAgfVxyXG5cclxuICAucHMxLWxvY2F0aW9uIHtcclxuICAgIGNvbG9yOiAjNDg3OGMwO1xyXG4gIH1cclxuXHJcbi8qIERpZmYgKi9cclxuICAuZGlmZiB7XHJcbiAgICBjb2xvcjogIzNBOTZERDtcclxuICB9XHJcblxyXG4vKiBFcnJvciAqL1xyXG4gIC5lcnJvciB7XHJcbiAgICBjb2xvcjogI2NiMjQzMTtcclxuICB9XHJcblxyXG4vKiBBbmltYXRpb25zICovXHJcbiAgLnN0ZGluLCBmb290ZXIge1xyXG4gICAgd2lkdGg6IDAlO1xyXG4gICAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcclxuICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICBhbmltYXRpb24tbmFtZTogc3RkaW4tYW5pbWF0aW9uO1xyXG4gICAgYW5pbWF0aW9uLWZpbGwtbW9kZTogYm90aDtcclxuICB9XHJcblxyXG4gIC5zdGRvdXQge1xyXG4gICAgbWF4LWhlaWdodDogMCU7XHJcbiAgICBvdmVyZmxvdzogaGlkZGVuO1xyXG4gICAgYW5pbWF0aW9uLW5hbWU6IHN0ZG91dC1hbmltYXRpb247XHJcbiAgICBhbmltYXRpb24tZmlsbC1tb2RlOiBib3RoO1xyXG4gIH1cclxuXHJcbiAgQGtleWZyYW1lcyBzdGRpbi1hbmltYXRpb24ge1xyXG4gICAgMCUgeyB3aWR0aDogMCU7IH1cclxuICAgIDEwMCUgeyB3aWR0aDogMTAwJTsgfVxyXG4gIH1cclxuXHJcbiAgQGtleWZyYW1lcyBzdGRvdXQtYW5pbWF0aW9uIHtcclxuICAgIDAlIHsgbWF4LWhlaWdodDogMDsgfVxyXG4gICAgMTAwJSB7IG1heC1oZWlnaHQ6IDM2MHB4OyB9XHJcbiAgfVxyXG5cclxuLyogQ2FsZW5kYXIgKi9cclxuICA6cm9vdCB7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1iZzogI2ViZWRmMDtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwxLWJnOiAjOWJlOWE4O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYmc6ICM0MGM0NjM7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1MMy1iZzogIzMwYTE0ZTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUw0LWJnOiAjMjE2ZTM5O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwxLWJnOiAjZmZlZTRhO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwyLWJnOiAjZmZjNTAxO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwzLWJnOiAjZmU5NjAwO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUw0LWJnOiAjMDMwMDFjO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDQtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDMtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDEtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gIH0iLCJmb250cyI6IkBmb250LWZhY2Uge1xyXG4gIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgc3JjOiB1cmwoJ2RhdGE6YXBwbGljYXRpb24vZm9udC13b2ZmO2NoYXJzZXQ9dXRmLTg7YmFzZTY0LGQwOUdSZ0FCQUFBQUFEK2tBQklBQUFBQWNiQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFCR1JsUk5BQUEvaUFBQUFCd0FBQUFjaVR2ME1VZEVSVVlBQUQ2MEFBQUFLQUFBQUNvQS93RTFSMUJQVXdBQVAxUUFBQUF5QUFBQVFCYWJLSmhIVTFWQ0FBQSszQUFBQUhnQUFBQ2laNGR5eFU5VEx6SUFBQUlNQUFBQVR3QUFBR0J3MW8vV1kyMWhjQUFBQXlBQUFBQ3VBQUFCVXNSdFd5SmpkblFnQUFBTGFBQUFBRU1BQUFCc0p1RVFoV1p3WjIwQUFBUFFBQUFHOGdBQURoV2VOaFBPWjJGemNBQUFQcXdBQUFBSUFBQUFDQUFBQUJCbmJIbG1BQUFNZ0FBQUwzd0FBRmRRZytIRXJtaGxZV1FBQUFHVUFBQUFOZ0FBQURZWG1ScXNhR2hsWVFBQUFjd0FBQUFnQUFBQUpBc1BBZmxvYlhSNEFBQUNYQUFBQU1FQUFBRFlMM1FkdzJ4dlkyRUFBQXVzQUFBQTBnQUFBTkl2QkJsK2JXRjRjQUFBQWV3QUFBQWdBQUFBSUFIUkFnWnVZVzFsQUFBNy9BQUFBY1FBQUFPVEFWeXVwbkJ2YzNRQUFEM0FBQUFBN0FBQUFVbGtYOFR5Y0hKbGNBQUFDc1FBQUFDaUFBQUF2VnF4M3pzQUFRQUFBQU1FbTFPdXd6UmZEenoxQUI4SUFBQUFBQURabklQaEFBQUFBTm43U1VmLzVQNWxCT2dGaHdBQUFBZ0FBZ0FBQUFBQUFIamFZMkJrWUdCeitPdkN3TUJ5NXYrVC8wOVlYakFBUlZBQUN3Q3BGQWNRQUFFQUFBQm9BSEFBQlFBdkFBSUFBZ0FzQUZvQWpRQUFBS1lCQ2dBQ0FBRjQybU5nWVRuRE9JR0JsWUdCMVpqbERBTUR3MHdJelhTR29ZbEpDOGhuWU9Wa2dBRm1CaVFRR0Jyb3lIQ0FRWUZoQTV2RFh4Y0dCdlljWmdVRkJvYkpZSVZ6V0JZREtRVUdaZ0JuL1F5aUFIamFZem5ETUpVQkNGak9RRERqUzRiL0REWU1teG1NR0NZelBtWFVaTXhtMk0rd2lyRUVpTzh6SEdQWXczQ0hZVGRRWkRLUWRaTGhLY001aGdPTTl4azdHR29aVmpHc1ovZ0gxTVhGRU1CUUJzUWdtQVRFSnhpS3dXdzVCamVHQ0NBTnd2TVlxb0E4cnYvZmdPcHRHSll6ZWpHbU1iejQvNFRSa3FHZFFaV2hIZ2duQVcycFovQUZrdnNZbkJrMi92OERaTGVBNVNZRDNWYks0TUZnQk5UdEJ0Uy9pV0Vqa3pURE80WnBETi8rLy83L20wR0VZUjhUTzhOdUFCRlVQa2tBQUFCNDJtTmdZR0JtZ0dBWkJrWUdFUEFCOGhqQmZCWUdBeUROQVlSTVFEcWFvWTVody8vL1FKWUNReXlJOWYveC8wZi9OMEoxZ1FFakd3T2N5d2pTdzhTQUNvQ1N6Q3lzYk93Y25GemNQTHg4L0FLQ1FzSWlvbUxpRXBKUzBqS3ljdklLaWtyS0txcHE2aHFhV3RvNnVucjZCb1pHeGlhbVp1WVdsbGJXTnJaMkRQWU9qazdPTHE1dTdoNmVYdDQrdm43K0FZRkJ3U0doWWVFUmtWSFJNYkZ4OFFrTUJFRWlBMDBCQUJWTkg1Z0FBSGphclZkcld4dkhGWjdWRFl3QkE1S3dtM1hkVWNhaUxqdVNTZXM0eEZZY3NzdWlPRXBTZ1hHNzZ6VHRMaEx1L1pMMFJxL3AvYUw4bWJPaWZlcDh5MC9MZTJaV0NqamdQbjJlOGtIbm5abDM1bHpuekVKQ1N4SVBvekNXc3ZkRUxPNzJxUExnVVVTM1hMb1JKNC9sNkdGRWhXYjYwYXlZRllPQk9uQWJEUkl4aVVCdGo0VWpnc1J2a2FOSkpvOWJWTkNxb1JvdEttbzVQQzdXNnNJUHFCcklKUEd6UWkzd3MyWXhvRUt3ZnlScFhnRUU2WkJLL2FOeG9WREFNZFE0dk5yZzJmRmkzZkd2U2tEbGo2dE9GV3VLUkQ4NmpNZXJUc0VvTEdrcWVsUVBJdFpIcTBHUUUxdzVsUFJ4bjBwcmo4WTNuSVVnSElSVUNhTUdGWnZ4M2pzUnlPNG9rdFR2WTJvTGJOcGt0Qm5ITXJOc1dIUURVL2xJMGdhdmJ6RHo0MzRrRVkxUkttbXVIeVdZa2J3MngrZzJvOXVKbThSeDdDSmFOQjhNU094RkpIcE1ibURzOXVnYW8ydTk5TW1TR0REalNWa2N4UEV3amNueDRqajNJSlpEK0tQOHVFVmxMV0ZCcVpuQ3A1bWdIOUdNOG1sVytjZ0F0aVF0cXBod0l4SnltTTBjK0pJWDJWM1htcysvVkV6Q0FaWFhHMWdNNUVpT29DdmJLRGNSb2QwbzZidnBYaHlwdUJGTDJub1FZYzNsdU9TbXRHaEcwNFhBRzR1Q1RmTXNoc3BYS0JmbHAxUTRlRXpPQUliUXpIcUxMbWpKMWk3Q3JaSTRrSHdDYlNVeFU1SnRZKzJjSGw5WUZFSG9yemVtaFhOUm55NmtlWHVLNDhHRUFLNG5NaHlwbEpOcWdpMWNUZ2hKRjBaT3JFUnFWYnB0VlN5Y3M1MnVZNWR3UDNYdDVLWkZiUnc2WHBnWHhSQmFYTldJMTFIRWwzUldLSVEwVExkYnRLUkJsWkl1Qlcvd0FRRElFQzN4YUErakpaT3ZaUnkwWklJaUVZTUJOTk55a01oUklta1pZV3ZSaXU3dFIxbHB1QjFmcDRWRGRkU2lxdTd0UnIwSGR0SnRZTDVxNW1zNkV5dkJ3eWhiV1FuSVNYMWE5dmpLb2JUODdCTC9MT0dIbkZYa290anNSeG1IRC83NkkyUVlhcGZXR3dyYkp0aTE2N3dGTjVsbllualNoZjFkeko1TzFqa3B6SVNvS3NRcklIRnY3RGlPeVZaZGkwd1V3djJJVnBRdlExcEUrUzBvbEJ4S3NZYVpCRGI4NThvVlJ5eUxxdkI5bnlOUmd5Rll5MnF6SG4zb3VjOGpicXR3dHU2MTZMTE9ISlpYRUhpV245TlprZVZ6T2l1eGRIVldabmxWWnhXV245ZlpETXRyT3B0bCtRV2RYV0RwYVRWSkJGVVNoRnpKTmpudjhyVnBrVDZ4dURwZGZNOHV0azRzcmswWDM3ZUxVZ3U2NUozbk1QdjZiK3NyTzNyU3Z3YjhrN0RyZWZqSFVzRS9sdGZoSDhzbS9HTzVCdjlZZmhIK3Nid0IvMWgrQ2Y2eFhJZC9MTnRhZGt6bDN0UlFleVdSNkg1T0VwamM0amEydVhnM05OMzA2Q1l1NWd1NEUxMTVUbHBWdXFtNHd6K1Q0YkwzWDU3a09sdXNoRng2OU1KNlZuYnFZWVR1eUY1KzVVUjR6dVBjMHZKRlkvbUxPTTF5d3MvcXhQMDkweGFlRjZ2L0V2eTNmVTl0WnJlY092dDZHL0dBQTJmYmoxdVRicmJvSmQyKzNHblI1bitqb3NJSG9MK01GSW5WcG16TEx2Y0doUGIrYU5SVlhUU1RDQzhnMmkrZXBrM0hxZGNRNFR0b1lxdDBHYlFTK21yVDBMSjU0ZFBGd0RzY3RaV1VuUkhPdkh1YUp0djJQS3JnTnVSc1NRazNsNjNkNkxna3k5STlMcTJWbjR0OWJybHo2TjdLN0ZBN0NWV0NwKzl0d20zUFBrK2xJQmtxS3VOMXhYSXBTRjNnaEZ2ZTAzdFNtSWFIUU8wZ3h3b2FkdmpwbWd1TUZweDNoaEpsbTJzRmx4akpLS1BneXA4NUZTZXlFVTAyb29qZnZLVitxZ3VGMEpuRVFtSzJ2SmJIUW5VUXBsZW1TelJuMW5kVWw1VnlGdTlOUThqTzJFaVQySS9hc29PWG5hM1BKeVhibGFlQ0trMk03cC84aUxGSlBLdmE4MndwTHZsWFQxZ1NUTktWOEpmTzB5NVBVcnlGL3RIbUtPN1E1U0RxdTNoY1pTZHVaeHRPRGZmMnRWT3JlMjcvMUtwLzV0NW43UWcwM2ZHZXBYQmIwMTF2Qk51NHh1RFV1VlFrdEUwYjJCRWFsN2srMTJ6a1UzeXArZFoxTGxDRjY5UEd6YlBuNytoc0RvL09aTXYvV05MZC8xY1ZzMC9jeHpvS3JlcEV2VFRpM000dUd2QWRieEtWMXpHNjZ6VlVIcGZjbTJrSTdpTUVkWHZ0OFZtQ0cxNXQwMjNjOGpmT21lL2hPS2RXcFplQTM5VDBNc1JiSE1VUTRaWTdlSUVuMFhwYmMwSFRXNEJmMVdNaGRnRDZBQTZEWFQxMnpNd2VnSmw1d0p3dXdENXpHRHhrRG9Pdk1ZZkIxL1V4ZW1FQUZBRTVCc1g2MkxGemo0RHMzRHZNY3hoOWcza0d2Y3M4Zzc3SlBJTyt4VHBEZ0lSMU1raFpKNE1EMXNsZ3dKelhBWWJNWVhESUhBYVBtY1BnMjhhdWJhRHZHTHNZZmRmWXhlaDd4aTVHM3pkMk1mcUJzWXZSRDQxZGpINWs3R0wwWThTNE0wM2dUOHlJdGdEZnMvQTF3UGM1Nkdia1kvUlR2TFU1NTJjV011Zm5odVBrbkY5Zzh5dlRVMzlwUm1iSGtZVzg0MWNXTXYzWE9DY24vTVpDSnZ6V1FpYjhEdHg3MC9OK2IwYUcvb0dGVFArRGhVei9JM2JtaEQ5WnlJUS9XOGlFdjRENzZ2Uzh2NXFSb2YvTlFxYi8zVUttL3dNN2M4SS9MV1RDeUVJbWZLakhGODBuTGxYY2NhbFFEUEhmRTlwZzdIczBlMGpGNi8yanlXUGQrZ1Qxb0FQNkFBQjQybVB3M3NGd0lpaGlJeU5qWCtRR3hwMGNEQndNeVFVYkdkaWR0akJvU3pNemFJR1kydzFZRkRpRTJKbTVJRHdUSmcwMlNWWXdqOHRwRDQ4RGh3UExBUVptQm00Z245ZHBENE1ER0lMNE80RWtnOHRHRmNhT3dJZ05EaDBSSUg2S3kwWU5FSDhIQndORWdNRWxVbnFqT2tob0YwY0RBeU9MUTBkeUNFd0NCTFliTVNteGliQXk4Mm50WVB6ZnVvR2xkeU1UZzh0bTFoUTJCaGNYQUgyVkxnY0FBSGphWTJBZ0FJd2drR1VuQXdQem5QL2YvaFVoV0F6emdIQUt3eFNXeFF3TXJBck1jeGdZL3RXdzdQei9paldZZWRQL1YvL1NZSHBaelJnZkEvRkZBTW1FR1lnQUFBQUFpQUNJQUlnQWlBRGlBUEFCa0FKaUF3d0Q2Z1FnQkdRRXFnVW9CWEFGbmdYSUJlNEdMQVoyQnNBSFBBZTRDQklJaEFqcUNVQUp1Z29lQ21BS3BncmtDeW9MYUF2eURKNE5CZzFzRGRnT0pnN0FEMHdQeGhCQ0VJZ1EzQkYyRWNZU1JCTEFFd29UWWhRcUZLd1ZRQldZRmU0V1FoYkNGMFFYcWhnQUdEd1llQmpBR09vWkdCbmVHcHdiQmh2RUhDSWNwaDJFSGd3ZUdCNGtIcmdmQ0IvT0lISWd1aUZtSWhJaWtpTW1JNFFrRWlSbUpOWWxWaVc0SmpvbXdpYjBKM29uMmlnb0tOWXAyQ3J3S3p3cmFDdW9BQUI0MnJWOEIzd2MxYlgzdlZPM2FGZmExUlpKMjdSZHZhNTZXM2ZaNnU2eWJFdHlsOEZOMklCd0V6YkdnS20yQVp0Z0lOUWtOR09EUVhUNENDV1VKQThlNUZGQ1BnSUV5RXZndmNTRUlvMitjKy9NN0s2S2JYN3YvVDcvck5uWm1UdXo5L1QvdWVmTUlCYmRLSDNHTmZFNUtCbWxvaXEwS0RxL1BOK2Z6Z2tjYnVZeHh3Z01Kd3pxUkVaZzRmOHVEY2FJNFRDelZvdFpoTmhGOE1HaWJ0aERiUlpMU2dwQ2xpcExaYVFrSytSeHA2U21wSnBOY0ZkRG1WNnc1eUtibGJVSWZxOHZWSllhS1MvMXNxbGV0anhVRnFsSVpXRmJYbHBpc3p0d1BZWlBxMFZrVTJFcitIMWhQUmI4WElHTGRmbUdYL2VSRDdZc254bkpaQTRGMkhmZlpYeFdjenAvNTUxOHV0bnFZOTU5bHcxWVE5bzc3OVNHK0J4UDhJZHBRWThueUQ4VDlQemc1UWQrMlArdHljQUorQlo4aEJXTlpyMU9Pb2xiZEhxelVXU2xkZElhZ1RPWVVuR0xkRElWTWZqTDBXK1pQM09ua1JFNTBZTEhkU3pESW95Ym00N2IyeGRIN1FnaDNNdGhqQU10UE5ETzlDS0c4VE90anFnVkRnSWZNT3BMUE40Wk5TY25JNVRzVEhiWUxIREhwS0NnSWJ3UVdTUDIrMEpoTmxSZWc4MDJGeWJVaHVvd01JSjUxc0lVTTY2TURBOHVZaXoyUGJpbVp1cFUrT05PcDJXTTFOblQwKzNNLzhsSUcwNTMrVzd4dWVobWRCU05NcSt6YjNLblUveElONXFCVUFxTGRPaHpSUDR4cUhiMEsrNTZiZ2cxb1RhME9McGdWaTJqMVhsdERNc3d6U2tHUGFzMWFoaUV0V2lkS1Zsa3NjQXhEQXZ5VGNJNlhSWWxNWnR0Ylc1R3FMbXR1YTIxQlc0eVo4YTBhRU4xWlZtcE54RDBXLzBCYjhDczhSRHhXb1JjTEZMNXdZNU1IeEd2Tjc1TFA0RGdDblVuTlNad2IzeTNGRmQ0UmU0Q29PM0Y2Tk9FeEUvbWNaNVVaeDdUSlAyZzd0MUJqdjg2K2h6NStMUkRQdGlJZVhYdm1EUVFsWDZNc3IzZWNOaDdtbXlrNTFKTTdqUldoejN4dmRoSlhDRWZrdjRhMzVPMm56NU4rTWVpazZON3VRdytFODFDN2FnVDNSTjE4Q3lqUVJhTU5ZdmJxcTBjajZ1d2xzOEtNWXlXQnkzSkJDM0owMk1OUnBwT0FUUUM4d2ozSVY3TDhKMUpXQXVtdzJxWlBzU3lZcThPaTJLQUJkVXBnVDNFaXAzbnVvcGN3UGJDU0xhak0rcnM2R2hzUktpanM2T3pzYjJ4SFdZMzB4M004anVEV1FhTkM4VGh3amE3YkZleWNvVkRZYXZON3NaV2l4R0xWa1hkNEZoYzhVcklhYnNwRkM3QVpSR1FCcm1hRWF3V214M3VaQzR2aTRUZ0hpWm1uN2U3dzVlZDdmTmwrNHkxMSsxdWJ1OWNkTitGM21EUXUyT0JmTmlhcG5WdTZkd3pjM1pIMTgvWGVJTjNyYzNPOHJmL2MyTmVkdDRDUHRQamV5aHRkcjdmN2ZZLzYzZG5iSFg4eStoMGJWeXllRjh6YzhMbjhmaWVTVjlRU1U1KzQzZW4ycG9XSm1ON2lzdTFkdDZpbmRHZit6elNnUm0xbVZtR0pQM1hJOTN6cHZyeWpNazY2YitJakhoVUFqcCtDK2g0TXZLaVlqUUZkYUFWMFc2d1pSNHovQ0JpTllLR0ZRWVJoNURJb2I0a0xCcXdWaU5xKy9TWTV6RUlBdU9zRnFUUkNMMUlFTEtGMXFsVFMwcDhQb1NtZGt4dG45TllNcVVrV2wzcEsvWVY1V1E1MHMwcDhDUEdrSkdZc2N4TnYwOWhHRmRhWWljYWpDbTdRZUZ4d0FnajNLRFk5VENpQVB2SFgyRmt4cHpHMSs2YU0wZjl6enhqejBoTFR4dSt5VVkvMmZVakpWUERZZlUva3pnMG5IQ0NHNXFUY0diUTRiRFo3Y012MnVBenpjYldXeEtIanJ5WE9IUlA0aW5pTnc0QlR6Y0FUK3RSSS9wNzAvRmlVT3cwUFVhNEVqT29FYlBNTEwrVjVkaEN6SE44czJQeVV4bzQxU2w3eml4UWFnYUN4eURjbWVVWXRnK2NxdGlyQlpYT2F0RmdqdU43QlJDR24yOTF5RDlWY3M3eENJYlRYVlZzam1qUldTNUNzV3NTSk4wSkRocWhtZE9CeURwL3hCK29Eb1IweEh6c2NaY2M4dnVJRkcxMlhGNEJMa3Z4YjRKb1YxMmRyNUFJbkVpMHZDSkV4VXFzaG9pMUFqT2YzbXdsVnRHOG9hSWpKenNIQjdNeWs3S09FYSsxTEZDeVlUN1o2Uzl5TDlyN1VOL1JqalhMVnM0N3N1cWR1b0s1WlJkMlNUOXlRK3VTdzd1Sk1Td3BMR2d0akhRV1NxY1diNERJRnZSYzBuMEorZkQySGxseWM5ZnEyNlpzdmJyejRQeVIzUE9tUmVZWGJjWWhJUG96NW5YbUx4RERrbEM1elA0a0VyaTZHUks0RURES3pKQm9oUmVSQTZnWDlzQ1JSSFV3SmducEFpelI3WGlFcXNITVg0UUsxdTkyQmRnS29mQnU3blNKVkovaGRHYmdGNG1RY0xiMFM3YVhYNDA4eUhNUzdqYUgvdUJqY0s4dy9OSkorTHl3ODFHYkJXdHN1WWo0R0dJaEF1aTltZTZSSHdHSHc1UkZ6T1VWckZHWDR0S2JEQTkrOWVWREJwUGVsYUxUWC9MZWxWZitZWUJmYlRPNzBpM2FmdW5xMFZIcCtuNnRKZDFsdGdtei80SG52dm9xbm45Nk5wbkhlVENQdTVSNWFER2FUWDB4bVVkT2ZCNXVKNTJIeld5MU1JSklCRXdOdGR4c1NtSG9Ib2xDZG1icUg2Njg4cjFMOVBKc0h2cnlxd2VWMmZDMjA5SURyNzRxUGZTUDJZSXlJN3daUWZqRlc5VTVFWCtFMFhQNEtzNEF0bE9HNWtlVGl6RGlDc1ArOUdRV1hEc0RNU0lIQkpKS0pJQXZCNGpGWmJVQWJFQzVSQzVXMk9Nd2gvQWdrY3hsOUN3SEtNSUFkeTFERVhlZ0FBQkVCZ1VRd1hLRm00TEl5MHoxZ3lhS2l1OXB3RUdpa1RJOXZBeXhtTVA1ZkFBanV5a3RxQk44bWRKWEw2WG51RE55MHZmdlQ4L0pjT2VrdnlqOVo2WlAwQVhUVEhhTUFqZy9oeHNxeXBHK0dOQjVQYWxtWjBnbysxMjZLK2kyRnB3K1hXQjFCMTNwdnlzVFFrNXpxc2VyRzhCcHZNNmZKZFArSzNRVjUrTVlrRU4rTkFlTUdrRVE0ekJBSTNBT2VDMnhjb0tPZUtZRFJudVFPK0QzQi95aXhrRWdoTWxMYmNydk5WSGpLek41S1ZBbzlackk5QTk0Y0JXeEdPa1ZvdjNTSzJRZlYzbUNIRFB4V0pDT0pmUEJXNlgzbWIrQlZhUWdkOVFCaWdGZ0RsSGxSekhkRDRVWVRSckZNQ0lMUDB5d1NqMEd2Zi9BTEw1am50N0lMT2NjMWhkeEtEWFptQ3c1czB1NEpQeEpxcFhTeWpDY2o3a0tHWkFuNmt5MHFXNXl0ZzErMzREMEVXcFFNbUVLUFJ3UDh4d1J5R3laSDVpcnlIekpINTN2eDRBLy80Yno0TXIwcUUwMVVPUkhyZlJ1U1VINWJtTWc0ME1ORFkyTjhJZnpYTDRueUUyZmtHbEhMMHZIT0lIdlJ5WlVma3JQTURLUUpSQWxpZHc0cDBXeDBxaU9hdU0rYWlUVUQ1aFFTbGlkdG9oVkJFY0FPdnR2RVhha1IvVGJzeUlzY3dkODh2MXV1MGI3L1kwcEZ2SXBuSmRpa1hIbjB4QS9VbWhNOXFDOGFEYkJrakowQmw4TVV5RkVaYU5Xa2pTa2VGTGNhVFlhVjJWNFRNMFRmcEs2aGZGUmt2bjhoYjYrNXkrOTlQbSt2aGNHMndhbVR4OW9rN2ZjMEZIcHl5ZWVrTDQ2ZWhUYm5uZ0MyNDhlM3ZUMndZTnZiOXhJdHBzSVB6NUVDT3p5YVpoUlVUVGZDTEFLZEFFMkxJTUJKYkFBZURuQ2lKNFl2MEUvdy81QWhOaGNZSXdBVGFxaFZWQTdCTTFsdnlFaVhVNFYwUEM5eVpocE4zcndnTVZpYzZIUksxUUJzMHQrcHN0T3Mvbk1YeVM1TW9aWktxT25BR1IrRFh3cVJPYy81c01jUzBSa0JCRUZFT3l6SE15TXFOVm1tSjhjSTdPSTFKZ2VOZkVJSmd3RDc3RnI4bkdkVVNOOEswUUZnWnd5djUyYUc4RWlnb2k5Q1NqUnEwb1p3SjdmRjRPSjFJMHdUenpjcy9vODZUZytRUUlha0RySDUwckdUeXh0dW1qRHhsNXl5RDc3VjB1NG9YbTNiVmh6L3dicC9sMGtjcjFJcUE2bDRHZVg3MnhjdHFGeUl6bDJLSnhTVmtOOTVPaFg3SDlUZk5FVWJTekdBaThBR1V3ekVnQlFDQnlRdzVKTWhLQTJGcmdDYUpnWGV6VnlLSStyRDJ3aGRBY0NrVWpBbnFjbG9Wc21Td1ZhaW44SEowZzBpSUJZQ05oeThrRy9KVklKOGIyVWVlR0I1ZTJ6dTFiM1BubnBpbGZiM0thTXpCVHoxRnRhZCt6WmUrRnNJdHFLL2dzdlBIOHJCY0FHNDNYSHVhR09HMWN0M0JrTUhWeXo0ZDZsMDZ0dFRvc3J4MUJjdFczTjJ2T0l2SHVXTHVnTlR5TmtiN0JsYUJkVHV6Z0VPZ2d3RFFWUkZpcVBsbVpoSk9CbUVTTmVkcEFhTEFoWkxRRDVHYllIWk9sbmdjWndDRVpEcGhYeEJueGFqVE1YV1UwcStyQ1dsaVFvWmcwdWk4bXdGSHRUMlpsM2tsbmZlUm4xbTNQSjlyRGs4N2wwK0ZOYlNVZzZEeS9VY0VPdEkvdklYUCtrS2luc2VJM016ejN1a1FyOGplelRuNmF5dWd0RjBNem9OQkZnTlNaeVlubUJCYnZoZUpiYkJZTkFnSHdmREJlN2laaDhCSEhSUERpYklXS0tvQkovS0dBUCtRSlVUUEtrV1pETTVLSlNqTjBuUjJuaWowdTk3TTJFaWdMRHFnc3VQcjVzM2ZPN2VsNXM4NlFRQ1UwNTB0UnhjVVBOcGpuVHp5OU44ZVg0R1F1VG1jM1l1THRvVUhpdWNzMWoyN1lOclk5V1dOMjJqRnhEUWZtVWJhMXorcVArZ003dHgvLzB1MlYvOVJyNHF5VHVTY2o2ODFCdHRFb2pVNG1CV2s2bWl3V3pJazRpZ1M0WHVGbFhuaXMzNklmTEhLRkFRS05KbDJrVEljc2d3WGNNZGVaQUJScVhFckRISWJoSzMwcWZPQ05IRm01OFpQV2Fwd1kyUEY3WmNnaFArVTQ2dkhWS3d3WE56ZjMxZFZ0YXVTZERwUjRITnY3cm5lbHpsait3K2Z6N2UxWjFYL2JiQjNIa1RmM0l0Ulc5RFRNMzFsZXVuVDVqWFJXVjEyZEFDdy95Y3FDNWp3RXdaNGhQU1NJQUhuWUJJdmRESUdDN09hREcxeUxia1NPYUxwOUNneFBPZFZMMDZFRHBmbXVZVitoTGlBbmVoQnpTeTM3aEVxU0YyckFqa00vam02V1E3Q3VZTzRrbzBsSisvTDkydXl2TnFHZi9mSkRZeExzUThWajBGdWlXQlBiZ0FBaFVnNlpIcDFnRVFBZkVNWU1JT0lidkUybmtFT1RJd1hHcTZlZmxPWjBJNWRYa1ZVZEtuTG5PbklBUGJwRUJUc0ErM2duSTJIenluSXNaSncvbXJWLzJMSjJ6YlBQNko3ZHVmWEw5NXFWenVucCt1YTYrdDdKeVpXM3R5c3JLM3ZyWm14c2FOcytXdDl6UW9pTmRIWU5aT1RldFdIdlA4dVgzckYxeFUwN1dZRWZYa1VXSDgrZFhsczR2S3BwZldqay9YK0xMZSt2clYxUlVyS2l2N3kwbnV2Yjg2SmNjQ3pRcnVtYkNEQWNFY3lBQ2pnRjZlVDZtYTByNEIzckg2bG9nRUpaMWpXQS9oaE1GWXY0VmViaml6T2tsOHdwUkxPbTU3eHlnY2xpSDNYR1ZrM1ZzTnRVM2JvaHFsdlRHbTNvOFh1Y095em9tNnh2TWxtSVY5bDdBSlE0UzR6a1ZyUVNKajRhc0FGTUhab1RZWTNRWU02eXBGTURRR0srdU9kQzR3NHo5NWxiZ2pQckhiSTdEbXBITHgwQWNtTU1WMHZzUUFNa2MzQ2duR3JiTFVaMkZ1TTZzams4SWd3OXlPMjBXT2dOK3dnek1FN0NmT29rckV6Rmc0a3lrVXhQeDRFNjBuWE54cVNpZDRFRzlobGhVTThGMHFKTXVITUlJM09ITXBHQlRXU3pRWWdXN2g3R3NwcGg5emVTMUpXV1A5REIzWkNmWkFBb1AveXZkWmt0bnRWeHFicHJaYTVHZWxaNjFlTTFwdVRxOE15a3pQVDB6Q2U4a092VXJYTTM1MkxsVUZvQnUxUFhJdFNBRWtNVWl1aXpaVGJqU3BzZ2ozV3FtOEZTWUFFL05ad2Fydm9SOWRxNGFNcVROQ1JBV3FId1krTkNtOHNHY3pNUkFkMmNjZER2REt1Z1c0a3NtV3F3R0FjeFZBZFhELzdKUWJqQjNqUFRJM0dDMXpDQ2xXdHFyby96QVUvRlVtUi9TWHNJSGFmUmI5bVhJZmNPUU1WMGMxV1ZnQmh2QUJUTEtFbTRvNXVjZzRpSitGM0YzMU5nQ0xjVHd1RjV3TVg0T0hHSmczRUFZZzRodTlTVU82NHhhc2lEdnlTckxpaFRtdzArR0FubloxQzVsMzVPTWFWWVdLbS9BOWN3a2NHUGMwdSs3eCtiTjJML0J3TmMxc0FZbTJUU2pmVm4rNnFXN0Z4TW5tbVM0K1dsVGVYbGRIZnh4cDl1dVdiWndlMWYrOVVWRkwxdlNSS2UzdXJHNGFVbXdrempWM1ZhSHB1dkgvM0w1K3VucUFyRVNCcFdNcnVVT2N1Vm9EbHFNdXFLTE0reU1qdEZoVmtmZ0Z1SWhsQS9xc1FaeGpJYnJRMHdTMXJHTXJrK0xJV1ZEQW9zQWVva2kzMGtCR0JKNXNhT3BDYUdteFUyTDVyYkREV2VIUzBMQmdsQWdaTkM0NDB0aW9YQ0NIeXF4SzJFZExNeHFzVkVjUm1PNzRwL0s2V2wxT1lCY1pBNlVVc2RzazUxWHlNL20vMlhYek1GNVU1YlpJOHNiaWpzS0ZoNWNzRERISTZRbXAxcnNYSXVZNVc5YTJQUEl3QlVmN1Z6eTBQWVorOG8wck5QQXA1WGYzSEg3NTl0dng3WUhheGRVQmR6Rml5SlpBYTc4d0hkM2JEMjVjbXJEdEdubHEyZDIvV2IvcWdhOUtLWWJwWDl6cE9jVUhoclk4OXphR3lYcDlzRm4xbGhNVEw1WjU5Q2xPZmYrODc0WGNjMmowdExPQTdNS0M3cXVtbHBRS21NR1NKVzRGeUhPNXFOaVZCa3RRMXJ3TzFwMkxSSkZUYmNPYXpTK0ZvRmpXTEwwQW1BQys0a1RLaXFFMGJrRXk1a0NFYitlTU0xbXgrTlFYTmdyampzaVIxdXdScEgxc3N3dmlwTndieDBGZGJlUjdmNjVrbVBlQVAxK2dtd3JjZE5UTkJQWkZId0tYL0VrUkYvZmNFZzEwYi8vUFphT0hDTGJLMGIrekxqa3RlNTJvR2NtME9NR1ZTNUVkZEZxQVl0eVpCSXhKNElyQVU4QzZJNWdBMEZKYytWTXFUQS9KeXNjOUVLK2hKemVRSzFXTllGWUVGYnBNS2wwc0NvY2g2UWZkdnhlNXZ1NzU4MklydCt5NUlGTFJsNGprNy9rRWtyQzZjOStlOEdGVzdmOUZtdTM3L3RSQWhUYWZrTnY4N2FnNytaTmZVZm14cW1RaEo3RlM1Y1BiMWpmKzVic2d5NEVERFFEWW13Sm1oYU5GbUNBY3pRcUlKWWhFSWZ2RlFGbXlFbFNmQi9TZVdMWTJSeEJyQ1dvT0JUMmg0SkJEWUhja09QSml4SlVkVlhVTUZaMWxZUzFSRjU2NTFKOHhITHJkaTA3Lzc1bGkrODhmK1dqalNiSWtjMmVaUjlzdmZYTDNYditldlB5Z3lXK2JHN0k3WmRPRWRPZHZubGEvenZYWHZ0MmYzV0ZNZXkydTIxVHBwSk05bkZzdnlWYVU2M2lWQ0tqclNDak5PQjhialJMbG9sQVpjS05rWW5mNjBpSFVUWnZvRnlrVUVGT3F5ZVRoSXdRY3VFbWY5Kzc5Ky9IcEd6QytjMmJLZi9mKy8yVEZ4M3Y2VGwrRWFqUmRkSS9UcDJTL25sZG5PMC9mdGIzNXFGRGI2NlhlVTdtMWd4enEwRUhtNDdyd051V0k0QW1ETmVmaFBWYURkYjNnN3ZSNmdVdFdBaUNKRUhUSjg4ZWtjbVRaWGcxOVhaRUs4bUZJaWNNMGl1MWVzM2dUN3kwTTJxRG5ScFVYUUZhRmZTYlVvT1FOWlVaNUJxVnlUSUovU1Z4Sit3MUtlbXdJdXpZRVM0SFlPendIc0tRTld2SWxsMFBCMEM2STE5aXhwT1Y1U0Yva3NUaytyTHhReURQOXhJTnpCT1VpSGlmbEs3cElwL1NpMlRiSmEzN0RFUXE4MndoOEt3Y1hTcnpyQkFzRVVKUFA4aWE0Tisxb0xXY3dITGdrREhXZGV1eFR1ZHJJVm1pMkExK3hpL0s2OTZrVEVuWHZYL1NKUkMyZ0VubEtGSlVBSTRvbGJJcEtjNGltZkRTY2F6d204YjVwQmdIdVNxRkYxS01GVjlRb0NDUjdXVTArMlN2SURtQTlCMmgvU1ZwWUF3bmRveDFTTEl1clZEcWxyVm9UblJXSmNZaVFYWVFzRGdDYURoMWJWL0QwQlVCeURwait3eWpMdS9ENFZwVUV3b0dJajR3WXgzMXRaT2FjVVZaWEJsb1dtMmExS0E1YXRCVGRpM2FkSDlQMTMwYkg5N3hMMm9oRDVKdFptRHV1OXR1L1hydi9xK1BMTCtoV0RIclB4TDZhcGVYeVdaZDllY1lYanBkYkNrc1BvcnRqNS9DYWJmVVZCUlQ0NVoxWVFmb3dqVGlzNUFlY1ZqUHJVM1NhU0NFYUx1TkJrYXI5YldJUEV2V1VzSGs2Y29PWERjTlRhbXJxYTZxTEM4cFZPS0tONUFjTDhwT0VKdjNqSUpVcWZmR1Jkc050RFUyMHREeU10a3VsWXhMNDkva003aWFuc0gvdlZUK0ppZmV3eHRVY3ZFUmFkMVlFVk1tWElNdm9PTEc2RldnbXdPNlBTZzdHdUlBS1BMZFpBbkwxd0tVWW9KYUZVbzl5RVZYUVpUMVlycFU3QzBadXpLbjdyQnZ3MXhHRWJaUVRaeEtaMllaUlJTNjNqUitoakhGdytnQzBMdkxZUzVCc2pwakoydUR6U1JxQUhJZVRKd1pJa2twS1grUW9BNkQvZjVBMkIrZkdGRWhwYjVnVXN5SUFwL1k5TGcrbU1ocmI3elVQeFJOSVZvMS8rRGVDNlg3NmV3ZWxXYzNVdkx3b3gwelV6T3hpOXJLZDAxYkI1ampjZnNndW5JM3pITWVzWTg1bUlPWk1HVDlEQU9PdzF5Zlh0RWFRNUtpTlF6SnlBU3NMQ25CWlIwdFRiTm5UWXNDUXdOWmtjcmlnREd1TWxqR2ErUy9MVmJ6SWpYa0FoeW15QzBabjFPSFlvaUZVbG9uTGRPazdHMzFGRG81YjBxNDFFa0luYnQ2VnJyUEhyS256UzdJYVhXNzZWS1Z0RGdoOUt5UTFlcVVyR1RUbGZXYzgvQ3FyRlZOdWdXdVJ2TDFRTW1pdXZsZVg4RHRja252VEtKazgvQ0RZM2xHNGxNQWxZQ2JoYlFFTVA0Z29Ic2tkRU1PSXNnUk5MN3VCdU44RUR6OHBvQUNBUlRqaVB2RkNkUXpIOEJVL3h0L0xTOTh5QkhqVGtvWms2TXFIWjVOQlhyQlJKOEhYb0I3Q09ZWEpmWmY2N0d6SEtMb2kxU0ZCaldZeUZPdk80TVhpS0w2cW5JaXpBQ3hrS1M0TUZQSFNVb3ZyOTJFOWVOUlo2eEJnemJqd0NmdHdpakpLSS9iK3liYkc0YmNRQ0RYOEtaMVUveG9lWG94K1hnN3pTbjg4U045MGRzVHJLdDA1R1ZDTWxNOS9PWllFYVdZUm01bmVyMkU5cG1LM1pXaDNsTzVCbEtzVURJMkIrZ3VrUkQ0ZDFsRURJTjdpV01BMDNORVBSUFBVbFRnYjVHTnN6TnFvc1d6VW9JRElnRi9RQWtETVJNTm56R3dVVWJnVXRNWVJhNEtoc284STk5ejE4VFI5N1FXc3YyVHphSEI3M01EaWJvNnJITmtWckMzRDc4NmxtcWpjZmc0OHlrVk80TVdBOTFiL3ovVVNWam02NzE3djc3MVZycmRlRjhYQkN4NXl3M2RJbjM1K09QU2wwZEpBQ0xvOHJBY24vcmZ2dmJhZC9wVmpMa1laT0ZGT2Fnc1dnTFFDMkVCclJWSjRSM3cvMFRQbkpNVjhNRm9EL0hPSWExYVhqRGkzRFA3aVZnQ3dGWTh1M0xscy92KytnMTExSDlJc0JqL1g5ODljUERRVmU5eWR5MS9ZTXVXWHk2VDNodkx4NUdiZG0yNWdJQ2V4ZEkzbElkVmFEWWFpcWFXWUNUYUFCSVdZc2krbW5XWXdVMU54d09nU21GaVNTd21XUzVCRWV4cWtxUUp2VnE2NWc3UVNDMjFPWnFPaDJCNEVMQW13aUprd0dlK1RBTTZtSU40bHI5ODRtREU4Z3piTjJad1oyZlVYbDJOVVBYczZzYXBVWmh3WlhFdzMrOFA2YW1EVVFRYUZ1WGlycEpmMkJKeVkrcCs0MVhlczRyZW1YWnBSMXRtVmU2TWNGWkxybGFYN0VreTJhclhsbWJVQkRXUkdWbm5ieE0xWG4rRzl0RmJIb2F4bSs3dDZycDNrN3psaG02US9ubmloSFQ2Qm1aL3BrYWJuT0VSMGl3dVcwWktia0FqTW5wZE1WdmdTemZxMzZqRy90K2V3RWszSEY3LzZwVlh2dHJYUjdicll6a0tpVTIxYURwcWlOYUNrOUtBSDlQQUdRM1RwNlZBVkVkckJEekxxQjExTkR1ZVByV2hEcTZxSm5xVUhhblh4eXM2dER2SmxoaU9RbW84T3F1U1pjbzZKcHhjZHZqU3lxQW56K0ZNVnNKUFkrMjhzQzNUSGN4d3o2KzVnanBxYVdOQzN2bkRWNjlqNHhVNy9wMjdhLzZSMWYyM3VXekYyUjAxZFU0YWRCcWE4eHFuemc3azVFcjd4bW5rRjYvMDlNbSsvRGF3NjJ6YWQ5Y1JiWjJGc2VERkRFL2lNeFo2Z1kxVTQ4Qnh4ZlpKVllFRjc1WGRna2lKbk81U3gwNTc3a3FLOG5OREFZL0xIOVRTVlRPbHE0c0dZOUtkSWdmcitQS0xWYW1nUnhKclh6SzcxQVl2QmRXeWZ3QlVHeklXUGJScDQwQk8yTCs4YmVIcTRsVmJWangzK2FyN0crU09ydHprN0pON0I2OXNxQTB0YVoyN3FiQzljK1VqV3hiZlhTMWozTS85N295dTdqVUxzeXN0Wm51eXlXN0pQclJ6M2JIRnMyZTJFbytQOC96dW5LMDdOblkxdEdXWXJDa3BUbXRnKzZxMVJ6cW1WOWZKK1N4R2w0Q3V6QVZkeVVhUmFMR0FsUTRlc2w2aUZwTGlQcDBHNVd3VTlwdG8ycUpVa21MZEFwTWczVGdidkZ3WnpWS2swLzlKSGMxQnN2MVA2YlFjcWRrbE5EM1pUeWRkbGdnTXBkZnBzUUUxUnF0eEtwLzJOOURsSGJZYmhFZ0xKcVNmTEFZSzgxRXVvTUlJL01WS1hpb3NMSnNBbCtSMXNiR3hwdjZEVjEvOW9GNE9LQlFXN1Rsd1lNL214QUF6c3ZIM2I3MzFlK2FnT3QyUlBVY3Z2L3dvczB2QjFUcVlLMW1mQ3BPNXVrbU52NWxYWmd4cE9aMnhPdGt3Q3Zyb1hCT2dqZ0lVOExpNWF1UFE3aDZZUzR0MDFGQ2FsMXVhSk4zYVRPZDJJZGxlZzB0dzJTcjZ2VlVKaGlsK3Q4ZkhmcVBPZGZocWRxczh6OUZ2WVo3djB2cGk3K081QVFPTEJSTDgwK1hnejhKOE9STGZJZjlxZ2NRdTJNS293ZDhOa1luVVR3ZkhqVklHeUxFL2drb0NSQXhqWXovdGI2SU54cVRMYVJ5RkRxeDBKTWNJSFNJdzV5bytPMnV1WmVncDY3eHdOcmVQWWg1TThlckJWVThicXpQOXdsUHJkb3dKL3lrQjF4Um14c2hUVTl6K0JMby9acG9MTFphUkIxbXZqUHd3S29HNTMwTHp2bWkwcmpvN1RlU0lxSFJhRVlqU2RDZnBHWGtwVVlaOC9OakVyNm9pQW9Lai93MXgwS2NkRCs3WThRZTBlQUxSWTVLK0tkTHJlRWwxSE9Wc0dKVituRWUvMHE3Y2VyeE1lblZHbkFXZEgvMnhsbjRyVW1CNnErU0o1WDhicEJnZ3gzL0d4MlBnL0NWY0c4dTdhb0VIMXdNUFNsQkZOQUlzWUFrTFJDQ2E1RndnMTBuU3dSSlVwSktlSU5tSjBlQXNsQktFTzEyNit4UHFFdTZsN2NiU3ZUTmx0YVY5ZWo4TVQwa2thK1QzMHEweFVsWXhoVEZTMXVLamNSeC9IOURpVjNQSVNSbzAxQnd5M3FDaDVKRFdNcjlWelNGRlBDSFRpRlZiWlkvR2pyaDBJMzJNUmVuSVlId3VJM05JMGlsRjF6K1JHYWNiaDl1eGdlWWJENU9aMnF6c0E5OVRoMWFuOUJ2TmtVNnlhL2lseUU1eWI1SVJrZjV2VHU3djUrTDkvVERXam15QnNnZ3BBWE14L3BwaWJDV3BPRHViNkFkTjJ6QlZHbWtJejNxRzlGaDdnb0kzU0Z1dWY3aUk4Z2l2Z2QvZFEzODNLeG9rdjhjQXRGb2JiODJLdFZEWmtSV1NNS1h5YkpvMDFWOGQvOWxaMHBEODgveFNUL0Q3aitYZjVLOGtXMWsyWCtCdjJVOGhMcnRRMWlQQ3F1bFJseEVTQ0VqeWdXekU3Q05Wc3d0aG5BczV3K2tjaE5wSEJNQXdrQWJRT3BVZzUwMUsxNkxTWjhIc2NldHdSSERhelBaVWwvQzN2d211Vkx2WjVoUndST2QyY2tQbTFKRkhkSHFUUXhRTlNmaFBVbWFTUVJRZEpramoybExOTUovUlQ2VWQzQmVqSERLZ1REb2Y2M2dXQkFPTU1nOXViRjN1STcwKzZjZWNKTmh5N3c1bjVPUmtrRC9LMnlyT3lPYnkrNUVKcGRON0dwSGEzcFZtVVcrR2xMcGpNRlp4WTNQVGJHbEdzM1NWemUzMXBacnhVbTVqYXJvalhmZUJJY01WemphTXl1dlArMG44WTArZ0FsU05QbTA2N2dJbm5lekVHcmFpSE5CZENzeWFiWGFNT1NMQ0VhVUxPQnZ4SE9rWEdVUXNvR0xFYXZvUTZkOGxpREMzUlNSMDl6SXlGSFRJZHk0OTl3VkFycC91cWswWmptangyYTVDc1lzQThLdlhFRmhlV0loUVlYVmhWVmtwMEpidkR3UURrWWhlWGZwUGhKMnhuZ0pnR2kzcUNiRnVNS1g3MTBhV0ZBa1FEejA5MVUvVU1UcGxtWEh1YytldC90bmlUMDdlZnNPR2dhWTdaNXVNWHBzK09QK0YzdWYzcmU1NjVZN3B0N2F4SjM1eGo5VGZSdHpJbEliRzFobVhkZDEyYyttQzNxNmNvTFlvTGNXZm1sY29jVzBMWjNmY3M4Rm1sMlVSQkZtMDhKbmdPc3JRSjZkU0lEVVIxYXpaajlSY0xkQkNPcUJwYXBQYkl0RDBVZzJnY2pOZy9wbUh5czVXdVFxcEY1RUc3VndZanpoZ2ROOVB1Q1NhUGRsb0ZCc01VVjBkMndtaXNJVkNDSVhLUXBHQ1BPSVZ3ZnBENE9EbEZ0RXhIVU9LUk1ZbTdlTmJiUEEwMTZWUDczaHA4K2FYZHF5NHQ4SGx1NTJ1UGRGVi9HZHcrb0cydGdPZG5ZUFRwZzEyOHBtQUFJdnYyZmJCNGNNZmJGczh0MTMyN0Z3SzlmdFMrNUYxNjQ2MEx6aXljdVdSQmNRdWR3UHZYV0FIWjYwdjVTYlVsM0wvMS9XbGNjRDlYM1E1T3JxN3MrZkl3bzVEUFVzZm5HVTF1OUtUTTl2Zjc3L3VnNHN2K2VDYXpoc2p2bXoyaExvUVhiYzhzdkNXbnQ2akM2dktVN0xUN1g1NzdmUmRIMTUxMVllN3B0VFdFalRPVUpvT3hmVEptY3lnTStvVGVSS0ZKUklmYTdTVDZWUGkwRzVxZVVLaXVTYnFFOHR6YTMvQ0pZbytqUnVOWW9OQm4rS1dQVUdmZktGZ3hLL3FVNnlOUDFTSHg5U3N6NmhQN0djdTJra0hldFJ3N3dwWnNaNitsSzVZZkMrNXFDWjFVcTBpK3ZUakF6SkNhSis3V05hcmUvQUJXWjlrVFpLMWl2RCtJUEIrR3VoVEprQnh5Sm5WMVVuRXcwa2UwYjVBcnBlc3dPUzIwSjRGUkovTjhrSlU4NGE5b1lBZkx2U0UvVDVJaWpKSXptd25rZUtNS21URW9wZVFndDdjcUFIa2tDZmVkZVBTUjZlYmpINmJOcS9sMzliZi9PN21TLzV3WVB2UDA1bVYxcHYzc0NlMi9YYS96M25qMGNLd3RzeHF5cktGaTdhK2Y5TjFIdzdjc0hQVEJRTktEeXUzaEEraVVuVFJZNERSdEdxYmNiYjZRSVlHTXlKcDcyUWh3R050cnc1cnRRRVFLZEVUSkQvMkVRMnJZK0VrM0ZLTCsrSVhKWTZrajJ6QUw1VW9EWkYrbTU3QVhyVUhQZ3orMklYamtPUU1LM3ZVZ082OXJJZzFCdlNHM1J0L2c1ZFF1SEt2L0VtYVcxMitsK25pNXN0RDkvSEJVbk9SUHJtS0wvNlBqVlI0TDZtd2o2SDRkZnM5UTdJLzNpMnQ0UTZCREF0UkE5WkY5VUVHQ0VpankvS3lFZVVpVUZtZTVRWjFHdEpvM0tzVkdOb3NKWXJxc3lsS2IyRSt0WXNBcmFBbVhxSUdNZm42Ym5TMnE0bFZSZFNya1loNFZ1VDd6bnlYaEdzaGdJNi9MTGFHUmJWdjRqWEV6T3hGUlFnVk5SVFZWNWJUVnVPQVBSQW9reU9vWFZsT1ZYTGRTVnB6NjlTbmFDWnBYTHNoN3JaWFA3Ky81NlVGWVkwNXJOZTNQdEIyMWRVN1hwQXRzQzNCOE5nVE1lODkvTlpGOXkveGVvemhsTFFLenBtNXQvKzFXemY5N3VxcmY3ZnBjTnMxWFYzWHRNMjVwcWZubWpsRWg4RjljUHZCOTlXZ0RVU0hPVldIQTBpajBYYkxHcXUySCthT1gzOTNSSDFFYlRWSVM3SEc1SU5remExQlZmSkNkQ1FRMUNzMVY2VlRkRUxpRXBHZlBqcmoralR1ZFUyNWYyWFg1WTF6NDRuWjBybnRDdzR0WGhvL01KZnVuNlRSemRpN3R1M3dTc2taUzJIK3ZYUGRpZ2ZXUzUrb0IrUm9oMFpIcVUzUDV1ZWwrTkJhaEZJWXRJYUR5Y1B4WjZVMTdINTZmRFY5MG5RTmVwSGk2bWtLL3hyUXRxaTJMaS9aeUdGUjVXRVExRlBvQnE4c0J3Uk5OL0EwMktMWGNReHBVK3NtejcvUXFyK2Z0Q05wQkw3dkxLUGsyblVEcXErdGpoQUhBSWw5aEZRN0FtUFRYZEY2NWtWOXEybmlra1lwdHo3R3NjWWZUODJPTjlOczJrdTI3NE5YMlRrcm5oaldTTy9qOXVwWVp6L091ZU9xc1R6MEJJZS93TzJ4L0hCRWt2TWU5QWp3cVFINDVFQ3paT2JZd1pOejNlUlpuMEFMRXd0NEJEVlo0U0FwNWJOckU0L0xqd001VURxaFhYNGN5SHJHS2loenB3dlRCSGI0Ry9uWkdPbHIrcmt1TVRqRnhFN3lrV0dZMytmZ3c5clJLZXBEVGpWT1pjQk5ORHZvamdhcldONmpJUTlMYUh0cFFTcllZa2dTZVk1aFVMZEFsblRsTlhUaWdYTG9NRjB2YVVMSWJaR3Y2VWFUWHhFTms0VmdkU3kxdThsSGdyTkpnOG0ybzdhbTJUT25OOVFTZ3dxUy8wWlZFU2dzSEdjL2t4MmJURDFjOG9QbzluTEZLTG5YZ0dNMytsejVKWVh0aGZRUnBPdVZMeEdxSlo5U0s2TW1DS055TDU0NWZZMjU4NXFhWlJYMWlub3c3VE5tTFByWlN1bTVTYjlDRkxsYTNsdTV2SHRwNTJNMUE0dEhQcEYxaGZpa0cwQVdOZWh1eXMzSEtza2FRck9EZklveFNUaEpoN1NtVjZkbGlMMk02emhUeEJBaVkrVEFTeEluR0M5YjEvalI0TzdpNDFETUNNY042MVJkV1hWRTlXWFVsZjFQZkpqQ2I3YmtIRjZNQXZhVFB0ZlVSOWF3Sjg3dXhGUitYcnptZkRrdVh3YllxaEg0T0tIR2xudXVHdHZabjlobHZ2NXc1ODRQcjd5U2Juc1B0YmNmNnBXMzdJa2RIeDA0OE5FT2VYdDR3ZEVWSzQ0dWtMYzBiNE9jdndYbWs0MnEwR09uUWxwRzVGU2NEWWtPUXg1VjFaS1VJUmdyU21YSDE3N0NzZWhlU01jbVJITUZKWjN4c21qZW1FQitqdUVrcE9ma0lKUlRsVk5aVWdTVHpTTFM5c20xS3BVeDRYTUpkbnh0S2wwQnpBL0V5LzFyRXZEMHlvU0VESUNuakptbGJlTjlLK0RwdzJNek1obC83ZUR1aS9IVlErQlhJbDhuZ1Z6WjhlcENtRTNrNjlteDFyakx4dkgxSE1Nbjh0VkhBdG1rVUdrOGMzOFNTRm9UWiswRGF1cDdCbnowWTJ4WkdoOVFNdC9EWXpNVDRvZklNMHR6Z2E5RjZNS29EbFJFeUNPTFpRcG52U2loWnFQVXM0SmppallPQUw2SmRSMzZIRmR1Q3gzZmpjYVA3b3lDSGNKUEZjcSt4YWFWbjhpT3czc2pqZ1A4U1pXT0tXVS9uNTZsdFFhVERjV1ZTMDV0d3gwVTFOTzErV083eWZZTm42dm9pbHVhMkJOWmFTRnpXcFhHc2ZOMzIxNGM3ejUrcy9peVJwbitrK0EvTW9EK1psTExhNXlrbHBlYlVNdkxQVXN0cnhrMXpaeGVXdncvcWVYRlg5Snd0bUxlYitpTEdYTHYzdFc3SVR2THUyaEc3MFZsN1oxZEQxOXkvdDExc2RjekJINXg5ZFlkZWRuK3JwbkxkNVhSMXpUMC9yeGFYaWdnYjJXWU8yMUdmV2FXUVo4azZsTlRYUnVYTE5rL3A3WXUvbHFHbnNYelovcnlqUHBrVVdlenlpOW5xSTdray9VRGpMWVJQOHNOb1h5NjdnMWtZNVlaRk9pemJTeDl0azFwMEV0WUJjbEhlUUYvbUR3RXJGYno0ZzhCMnlZMDJKYkZCRTBXbnZFL2ZQaG5WTmRYdDYyWWRuaUcwZVJMTTNoYm41LzNxMk92azhPdksyMTR0QzlJT3R5L3ZqeGZWNUNSbW1rcGJuamtPQjZnV3ArbjFpRWJZZTRYczdkQ1pubnRZOGswek1ycW5VRldzamhTNGVPNFlBcy9icjJEdUl2QXhCSHlNZ1EvWnMzQ04yWll3bUtGL0VTMHNneVpRcFBiWWhuT3hIZ3l5U3JGR0R5cmRNckhqckcvaWExUlFMeFVFNFJmK2x3MHJGNUx2bnpHM3VvSmpoUVJKcmlEQTJ2T2g1Q0tQNVVWZitRdk5LQmlkNncrUmQ2dkFidzVVeDB4K0wrdEkrNkVDVFZJenhncmlvdktrcVhuNitQdFg0UFloQzJMNUw1Q2xwWmVSdXprVlNITWw3R2E1MWJaWU5VNklzeXpIRlZISy9KRFJscEluTFJHR0NzaXluMncvZ0RNT1RTeFFLaXU5azlXSXFTclJPTktoR20vMW9WRHVjVkpSMytXVkpvYkNtbGZNTk9aaDhoMisvWDNpU0ZQZy9IZXc2dnBRYk5LVHNEbDhlRVRVcXZQNHdva2tQVWsvcDAxSTB2S1ptYkdhbVF6WWY2WEEzMW5xUk1HLzVkMVF2MDU2NFQyaW5GMXd2ZndsRkpxaGI4ZzI1NXZ2bTZMdDRhVjRCblMrN1BpWmNMbWQvNjlRcTZueWRSTHIwZ1B4aUlRSTBteC9RVzRRdDMvL1BPWUhrcXJxUjRXa0Y2Qm9JVTJpUW1LV0ZXN0l0MWhvSTM1VkxRRktNOUhBV3BpQ1I0YkdmcThYRVU5VTNFT25heVgxazdaOGJOTi9sQlp6NWJ1R2RMQmhrVEZ6TUNHemtURkhINXkzNUZaSEE0V1RtSDU4cjBIbUxkaW9ueUxLWW5KOEFSTU5nTm9DS0liNUg1dnYxd2c3STgvNTAzTGc4RXh6M25MejI4RzRrUEhsQktENTM0bWZPSzRUdm1oOEVuS2poTWZDUi83a09jL1hNa2p0K0hQbExLampaUWRWMHBWU3RueERjSU1sMmxrK1FNMFpCQU91Sk9adTI0azMvNUQ0Y0VqMGtuMmoveFNTQ0RXUlhYbGtPUWE2TFBmY2o3c2lEM3lUUlpBbWRWMEJaM01ucnpJSStvbHI1UkFISS82NHNOQTVPVEJNdUpGTWRNUnkwMktDM096TTkwWmFRRXg5b1FiWUFjUHRnbWlsVVRYWkN5WGFteEtUVFhTZ09Wbnd1VTNrc0YrSWFhNzdBc2c1ZlVEeFJ6TGI5cTlhd3ZXNEwzVWhiNzJNYU5uTHIrZTdCNjREUFBNUjYvelMwbWhzWHI3cXNhTGowVjB3ZXMyMnZRRGh2VGRXOG5SUngvMW03YzdrN1pzSVY5MmJiWG81cmdOUTJUaEVETU82Ump6Q04rUERLamdwNzJmSWY0aUNHdENpd3R6blU4TzhueS8yLy85ZzRUandqdzF2djFkT3NrNUtNOVhSM1Y1Y0Q4cmhnQWQ0emtNWWNsTHArUUhKNUg2UnA0Y1R1VTVyZDdFaHdGZTYwVHltODVZd3ZOa21lZmxrVUIySUZ1VVZ5WEdjUmoyUFRqRzdFUU9rMklaTUw5QU5UNzgzVWNNank4N1FIUHR5NEhKSDlNbmdxN2RDNnpmc212M0pwN2xpZ2ZXazBQODBxRWhnM3VPenJKMUYySHJsaTFKenUxbS82T1BraTliZDZjYkJ2UzJqZGNGZFpGakZ6ZXUybDR0VjRFeHVnay95SlV6SDRQdU45UDY2QlFEc0RjVGxJbGdPcDQ4N3pjSUpzU0FUZzZTUnl0UUoyRUFxU2dTQmhDU0VYMTlTUkFGZklHd2ozWjlLM1ZpK2pUQkdNZ3lwbU9QRkFqeGg2dWoxWTNoQlROVGJEWnJwbGg0Uld2MXFxbVZjMElKQjVpUGM3SjhtZk5UVFdsT283NjVLeWZMNjQxOUlYbk90OHlWYkVqcEdhMmdGT1J4cEFMRkF1QWlmWWVJNlZUeVdnWjFUSkxXMHNtZUk3VmRjbWxUMDZYTnpYUWJuaGFPL2VlR1lvZGh1ei94RkxDRUcvMXgxTWY5SG5UWmhRcFJLK3BBbStqOFZubUF3KzJZMDA3RmdvNXR0bW9aWmc1NUM4dytZRGEvRDNGYW5aYlREWkluRHBFV283Vkl5NG5hVHNDZ3JFNkRCVkVuOUNHdFZseUJSSzA0dDYydHFLaXRvNjJqcUxXb1pVNmozeDlLUzgveis0ckowZytsaXppdHNnZ2d4SGlicE54RlFUYUJNUy9vSW9JeUt5OVNVSjk3b1JwWW9ieUwwRlRxVDJVWms4VXFUY3ZKK2RVMXhpUjdzc0grbzlhUWJMblRhbUdhamNQclJhM2RhalN5TjVIUGpSYUxwU3ZEN1haSUwxdlNCUTJ1Uy9aWVhmbGRiL0FmTVMrbGwwWHdHM05FcHpYWm90L05tMDBqdjA1MzFGdFNOU08vNVp3V3MxbkxGSFBPRVdlYTA1bCtGTzVpT2VyTlRFN1Y0NEZVczhNaVhZMTEwcmVnaU1EYkxPNTFoYmZMMENqbGJMSUhKRDhkY3lJamMxVkdyVFZ4NW1yZ25GN2s5T1JSS3AxT3Z6bUJ5VWprdEdJZjBnbUNiaEhTNllRZUpPaUVkZ1hXMXA3aEZxSmV0K3ZjOTRoT1RSU3ZxQkU1elNEUzZFV05mdGRQdmdrcDNSVVZGUzByV3RwSkV0YnNjbG5TaHYreHBDR2swVXNxZ3NvN1RvU3hMem1oamlwWkRvQS9XZW9yTXJJbGYxWUd0aFhsVHEwUHpIU0JBbVNZaW5mWGJkbzlkZVlyMkpEaG5sejRtOGNKZi9nV3EzVm5mbTJtL2N1czZkbkZWYWJraFRhcjFYWkptdDRiMkxvaXVyN3FuaWxXSzlnWHNsRDd1Z0NjYlFzNkgyMUMzMUV0eUNqQUFnOE9nSnNDU1ZjS0JNNU5XR3RjRFl3V3dNT25nalJiMVJlcmFMRDZaaFd0VVdmVTZnWkpod1l2aUh3OG9JSURNVEtvejRTTjJpUmpaekxXR2JBK1NhY25CNHhKSzFDU01XbXVJem8vOXFZV0RZQU5EUUViNUxhN0pyMnQ1aWZldGpNYWFBWGN0bkZENi9tdDU2M3NYYjYwYzlHOGpsa3o2K3RJYkFrRVNpTUJlNDRaa0Z6TWdkSG5TNFV6dk9obDh2ZThFRUdqQ2UvcU15ZGtXWlA0QXJZMEZTL2RWTHU4b3U2S3krcDJGS2VLUm9lb3plbkpiNXJiTmljdllEWjdaemJPbVRLdGtzcSs2T0lhVmtjVkpLNG94dnd1eXlUZVlmUVBQSDlCU1ZmMXF0TFVlZlVydHpnZE9wc2hOY3phMGl0S0t2SWphYTZpc3VLU3RESXIvRnVhb1hXNVJ2N3NOSTlSRytrWWNRK1RlQTFwR2RiSmNaL1dhd0J2WmhMTXJNY01mUlJmMFFDMThCQ01MWVBtMDNmcVpDSzNQMkFQcXNXRnlSZ2NiNzVhN3pyMnEzblB0M29OYVQ2VGNjYmhhU3ZhSkJrV1N3UUpEbTg2L2toRHNTVXpOYU5BbDErK3ZwK055cmthSTNKdHpLLzVlUUJsd2xTRGxmZG5kU2E4a3k0QjZNamhkY3pUOHNleXNpb3E0SStmNXdyc0Niam9ScWxGendaNkhTaE1GN05WQ2hOTEtPZXVuOFNlNTNsZ1hQMWtoSDdNanlmUDhSVWp1T3YvQTJBK2hmeDQybzJTVVd2Yk1CU0ZqOXkwWXc4TmcyMHZmWmtlMDBHdHBGMmhOS3dRQW4xWm9jMW9DM3RNTTJHN0pKRWp5UStGL3FuMVI0eXh0LzJnd1k1VXJVdkRPbVpqNjd2WDl4eGRTd0x3QWw4aGNIOTl4dmZFQXB2aVErSU16MFNWZUExdnhKZkVMYndXUHhPdll6TlRpVGZ3S2lzU3Q3R1YzVkVsV3M4WmZZc09nUVcyaEVxY29TMCtKVjdEa1Zna2J1R3QrSkY0blQ0dkUyK2drNzFQM01hNzdCWkRHTlM0Z1VXRkFpVThKSGJSUlEvN3BITm1OTWRRMWNRYXpiZkVXZVJaL0JiWTRKbzhpZW9CS3oxMWhubkh1Qk5kUFdkeE9JVGlYVkFiS2hwY0lhZkswRWxod2Rnd3J6bk9sNkl4bFVHclZycjQwOE0yWFRBMDlZMnRpdExMM1c1dlg1NlhXZzVOWXl0dDVabXRacHB2YzYwblhnNGFYeHJyWktmMHZuYUhTaFdWTDV1cmZHSm1hdEVZcjV0NUhNWjE3VlN5aUE3YllaWW5Gd0tQWmdNK01sZXdkc29mc0F4MTBVekhoRDAyRzViM0FIMk1jTUZuUUhycTEzWldmZmJ5YnUrZ1A3b1lEZnJMdmUwOCtQOXJxMWE4SHEvUGc4TmxWRHFxRERkQ0xuV01TMjFkWmVZeWRvSC83L3J2cmY0K0YvZW53dkVrQklPYU9jY3BRd05UanVFY0ZmeCtpbU9jVU1SZDQ2YTVpYTFxNzNKWFRYTmpDM1Y2ZklKZjMyS3pLSGphWllyWFRzSmdBRWJQWDBZUm5BekZMVzVSc2NWWlYxd291QVVucUtVeFlDOElOUVZqdk5Wbjg3V01wb2t4MFhOenZweDhTRGg4ZnZEMkxjRmZUS2RLdUhEandZdU1qd2I4Qkdpa2lXWmFhS1dOSUNIQ1JHaW5neWlkZE5GTkQ3MzAwYzhBTVFZWllwZ1JSaGxqbkFuaVRETEZOQWxtVUZCSk1zc2M4eXl3eUJJYXk2eXd5aHJyYkxESkZ0dnNrR0tYUGRKazJPZUFRNDQ0NW9SVHpzaVM0NXdMTHJuaW1odnlGTGpsam50MGloaThDMG00aEZ0NGhGZklJYXRhMG1zVm8yYnFaZXZaVHBSdDR5SDQyK292bHBNaWRkTXUvVHZLajVYWEoxUFRmSTVWUmZrWjZoY05SelZRQUFFQUFmLy9BQTk0Mm1OZ1pHQmc0QUZpSlNCbVltQUd3a1FHUm9Za2hoUWdMNVVoSGNobUFjc3dBQUFuMUFJMWVOcGpZR1JnWU9CaUNHRklZbUIyY2ZNSllSQkpMMHJOWmxESVNTekpZOUJoWUFIS012ei96d0JTaGN3V1kyQjJkZ3hSWUJEejlmY0Jra0grdmtBU0xzdVlWcFNZek1BQllvRXhDMWd2STFDRUVXZ21FOUErQlNESnhzREhrTXpBekNERUlBcXlIVWlMZzlXbXdObE1EQ0lNWWdDMXRoTVplTnBqWUdSZ1lPQmlzR0d3WTJCMmNmTUpZUkJKTDByTlpwRExTU3pKWTlCZ1lBSEtNdnovRHlTd3NZQUFBRnNhQzJzQUFBQUFBQUVBQUFBQTFhUW5DQUFBQUFEWm5JUGhBQUFBQU5uN1NVYz0nKSBmb3JtYXQoJ3dvZmYnKTtcclxuICBmb250LXdlaWdodDogbm9ybWFsO1xyXG4gIGZvbnQtc3R5bGU6IG5vcm1hbDtcclxuICBmb250LWRpc3BsYXk6IHN3YXA7XHJcbn1cclxuXHJcbkBmb250LWZhY2Uge1xyXG4gIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgc3JjOiB1cmwoJ2RhdGE6YXBwbGljYXRpb24vZm9udC13b2ZmO2NoYXJzZXQ9dXRmLTg7YmFzZTY0LGQwOUdSZ0FCQUFBQUFFQ29BQklBQUFBQWRQUUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFCR1JsUk5BQUJBakFBQUFCd0FBQUFjaVR2MEhrZEVSVVlBQUQrNEFBQUFLQUFBQUNvQS93RTFSMUJQVXdBQVFGZ0FBQUF5QUFBQVFCYWJLSmhIVTFWQ0FBQS80QUFBQUhnQUFBQ2laNGR5eFU5VEx6SUFBQUlNQUFBQVR3QUFBR0J5QXBLMlkyMWhjQUFBQXhnQUFBQ3VBQUFCVXNSdFd5SmpkblFnQUFBTFlBQUFBRDRBQUFCc0o3RVJWbVp3WjIwQUFBUElBQUFHOGdBQURoV2VOaFBPWjJGemNBQUFQN0FBQUFBSUFBQUFDQUFBQUJCbmJIbG1BQUFNZEFBQU1Ja0FBRnE0aUs1eE9HaGxZV1FBQUFHVUFBQUFOZ0FBQURZWG1ocFFhR2hsWVFBQUFjd0FBQUFnQUFBQUpBc1BBZTlvYlhSNEFBQUNYQUFBQUxvQUFBRFlLdWNaUG14dlkyRUFBQXVnQUFBQTBnQUFBTkpZZWtKT2JXRjRjQUFBQWV3QUFBQWdBQUFBSUFISEFoRnVZVzFsQUFBOUFBQUFBY0lBQUFOdit4OXFnbkJ2YzNRQUFEN0VBQUFBN0FBQUFVbGtmY1R5Y0hKbGNBQUFDcndBQUFDaUFBQUF2VnF4M3pzQUFRQUFBQU1FbXdpYmlRaGZEenoxQUI4SUFBQUFBQURabklQaEFBQUFBTm43U1RULzJ2My9CUElGcEFBQkFBZ0FBZ0FBQUFBQUFIamFZMkJrWUdCeitPdkN3TUJ5NXYrdC83ZFlQakVBUlZBQUN3Q29HZ2NHQUFFQUFBQm9BRzRBQlFBeEFBSUFBZ0FzQUZvQWpRQUFBSndCRlFBQ0FBRjQybU5nWVRuRHRJZUJsWUdCMVpqbERBTUR3MHdJelhTR29ZbEpDOGhuNE9Ca2dBRm1CaVFRR0Jyb3lMQ0FRWUZoQTV2RFh4Y0dCdlljWmdVRkJvYkpZSVZ6V0JZREtRVUdaZ0IwbHd5eUFIamFKWTZoaXdKeEVJVy9BWlBaSmdnS2drVUZteUJjRS93elZvTkJPSk5nRXhHTDhXQnQ1eG9VWVMyYUJGRmsyd1dEV2N3SEJ5YkQxcDlQYng3dkc5N0FESk00NDZOS25QOXRQMnlwc0pBN2RqS3pJa2RDOCtTSWdERjdadXpvczJIT2dUVlRpNnluSFBMRmhheUxxZE9tOWxaRFYwSmFZbzJrK0tIK3NrK1Rpb3ZkblF3RkpwYXpFcEc3V29wUDBnendHTEVTeTJKQWxXLzNFTHZrTlJ2b04wKzNDdHF1djdaWjJoKy9ETG01dXhRVEtLK2VOOGs5TVFBQWVOcGpZR0JnWm9CZ0dRWkdCaER3QWZJWXdYd1dCZ01nelFHRVRFQTZtcUdPWWNQLy8wQ1dBa01zaVBYLzhmOUgvemRDZFlFQkl4c0RuTXNJMHNQRWdBcUFrc3dzckd6c0hKeGMzRHk4ZlB3Q2drTENJcUppNGhLU1V0SXlzbkx5Q29wS3lpcXFhdW9hbWxyYU9ycDYrZ2FHUnNZbXBtYm1GcFpXMWphMmRnejJEbzVPemk2dWJ1NGVubDdlUHI1Ky9nR0JRY0Vob1dIaEVaRlIwVEd4Y2ZFSkRBUkJJZ05OQVFBVlRSK1lBQUI0MnExWGExc2J4eFdlMVEyTUFRT1NzSnQxM1ZIR29pNDdra25yT01SV0hMTExvamhLVW9GeHUrczA3UzRTN3YyUzlFYXY2ZjJpL0ptem9uM3FmTXRQeTN0bVZnbzQ0RDU5bnZKQjU1MlpkK1pjNTh4Q1Frc1NENk13bHJMM1JDenU5cWp5NEZGRXQxeTZFU2VQNWVoaFJJVm0rdEdzbUJXRGdUcHdHdzBTTVlsQWJZK0ZJNExFYjVHalNTYVBXMVRRcXFFYUxTcHFPVHd1MXVyQ0Q2Z2F5Q1R4czBJdDhMTm1NYUJDc0g4a2FWNEJCT21RU3YyamNhRlF3REhVT0x6YTRObnhZdDN4cjBwQTVZK3JUaFZyaWtRL09vekhxMDdCS0N4cEtucFVEeUxXUjZ0QmtCTmNPWlQwY1o5S2E0L0dONXlGSUJ5RVZBbWpCaFdiOGQ0N0VjanVLSkxVNzJOcUMyemFaTFFaeHpLemJGaDBBMVA1U05JR3IyOHc4K04rSkJHTlVTcHByaDhsbUpHOE5zZm9OcVBiaVp2RWNld2lXalFmREVqc1JTUjZURzVnN1Bib0dxTnJ2ZlRKa2hndzQwbFpITVR4TUkzSjhlSTQ5eUNXUS9pai9MaEZaUzFoUWFtWndxZVpvQi9SalBKcFZ2bklBTFlrTGFxWWNDTVNjcGpOSFBpU0Y5bGQxNXJQdjFSTXdnR1YxeHRZRE9SSWpxQXIyeWczRWFIZEtPbTc2VjRjcWJnUlM5cDZFR0hONWJqa3ByUm9SdE9Gd0J1TGdrM3pMSWJLVnlnWDVhZFVPSGhNemdDRzBNeDZpeTVveWRZdXdxMlNPSkI4QW0wbE1WT1NiV1B0bkI1ZldCUkI2SzgzcG9WelVaOHVwSGw3aXVQQmhBQ3VKekljcVpTVGFvSXRYRTRJU1JkR1RxeEVhbFc2YlZVc25MT2RybU9YY0Q5MTdlU21SVzBjT2w2WUY4VVFXbHpWaU5kUnhKZDBWaWlFTkV5M1c3U2tRWldTTGdWdjhBRUF5QkF0OFdnUG95V1RyMlVjdEdTQ0loR0RBVFRUY3BESVVTSnBHV0ZyMFlydTdVZFphYmdkWDZlRlEzWFVvcXJ1N1VhOUIzYlNiV0MrYXVack9oTXJ3Y01vVzFrSnlFbDlXdmI0eXFHMC9Pd1MveXpoaDV4VjVLTFk3RWNaaHcvKytpTmtHR3FYMWhzSzJ5Yll0ZXU4QlRlWloySjQwb1g5WGN5ZVR0WTVLY3lFcUNyRUt5QnhiK3c0anNsV1hZdE1GTUw5aUZhVUwwTmFSUGt0S0pRY1NyR0dtUVEyL09mS0ZVY3NpNnJ3Zlo4alVZTWhXTXRxc3g1OTZMblBJMjZyY0xidXRlaXl6aHlXVnhCNGxwL1RXWkhsY3pvcnNYUjFWbVo1VldjVmxwL1gyUXpMYXpxYlpma0ZuVjFnNldrMVNRUlZFb1JjeVRZNTcvSzFhWkUrc2JnNlhYelBMclpPTEs1TkY5KzNpMUlMdXVTZDV6RDcrbS9yS3p0NjByOEcvSk93NjNuNHgxTEJQNWJYNFIvTEp2eGp1UWIvV0g0Ui9yRzhBZjlZZmduK3NWeUhmeXpiV25aTTVkN1VVSHNsa2VoK1RoS1kzT0kydHJsNE56VGQ5T2dtTHVZTHVCTmRlVTVhVmJxcHVNTS9rK0d5OTErZTVEcGJySVJjZXZUQ2VsWjI2bUdFN3NoZWZ1VkVlTTdqM05MeVJXUDVpempOY3NMUDZzVDlQZE1Xbmhlci94TDh0MzFQYldhM25EcjdlaHZ4Z0FObjI0OWJrMjYyNkNYZHZ0eHAwZVovbzZMQ0I2Qy9qQlNKMWFac3l5NzNCb1QyL21qVVZWMDBrd2d2SU5vdm5xWk54Nm5YRU9FN2FHS3JkQm0wRXZwcTA5Q3llZUhUeGNBN0hMV1ZsSjBSenJ4N21pYmI5anlxNERia2JFa0pONWV0M2VpNEpNdlNQUzZ0bForTGZXNjVjK2pleXV4UU93bFZncWZ2YmNKdHp6NVBwU0FaS2lyamRjVnlLVWhkNElSYjN0TjdVcGlHaDBEdElNY0tHbmI0NlpvTGpCYWNkNFlTWlp0ckJaY1l5U2lqNE1xZk9SVW5zaEZOTnFLSTM3eWxmcW9MaGRDWnhFSml0cnlXeDBKMUVLWlhwa3MwWjlaM1ZKZVZjaGJ2VFVQSXp0aElrOWlQMnJLRGw1MnR6eWNsMjVXbmdpcE5qTzZmL0lpeFNUeXIydk5zS1M3NVYwOVlFa3pTbGZDWHp0TXVUMUs4aGY3UjVpanUwT1VnNnJ0NFhHVW5ibWNiVGczMzlyVlRxM3R1LzlTcWYrYmVaKzBJTk4zeG5xVndXOU5kYndUYnVNYmcxTGxVSkxSTkc5Z1JHcGU1UHRkczVGTjhxZm5XZFM1UWhldlR4czJ6NSsvb2JBNlB6bVRMLzFqUzNmOVhGYk5QM01jNkNxM3FSTDAwNHR6T0xocndIVzhTbGRjeHV1czFWQjZYM0p0cENPNGpCSFY3N2ZGWmdodGViZE50M1BJM3pwbnY0VGluVnFXWGdOL1U5RExFV3h6RkVPR1dPM2lCSjlGNlczTkIwMXVBWDlWaklYWUErZ0FPZzEwOWRzek1Ib0NaZWNDY0xzQStjeGc4WkE2RHJ6R0h3ZGYxTVhwaEFCUUJPUWJGK3RpeGM0K0E3Tnc3ekhNWWZZTjVCcjNMUElPK3lUeUR2c1U2UTRDRWRUSklXU2VEQTliSllNQ2Mxd0dHekdGd3lCd0dqNW5ENE52R3JtMmc3eGk3R0gzWDJNWG9lOFl1UnQ4M2RqSDZnYkdMMFErTlhZeCtaT3hpOUdQRXVETk40RS9NaUxZQTM3UHdOY0QzT2VobTVHUDBVN3kxT2VkbkZqTG41NGJqNUp4ZllQTXIwMU4vYVVabXg1R0Z2T05YRmpMOTF6Z25KL3pHUWliODFrSW0vQTdjZTlQemZtOUdodjZCaFV6L2c0Vk0veU4yNW9RL1djaUVQMXZJaEwrQSsrcjB2TCtha2FIL3pVS20vOTFDcHY4RE8zUENQeTFrd3NoQ0pueW94eGZOSnk1VjNIR3BVQXp4M3hQYVlPeDdOSHRJeGV2OW84bGozZm9FOWFBRCtnQUFlTnBqOE43QmNDSW9ZaU1qWTEva0JzYWRIQXdjRE1rRkd4blluYll3YUVzek0yaUJtTnNOV0JRNGhOaVp1U0E4RXlZTk5rbFdNSS9MYVErUEE0Y0R5d0VHWmdadUlKL1hhUStEQXhpQytEdUJKSVBMUmhYR2pzQ0lEUTRkRVNCK2lzdEdEUkIvQndjRFJJREJKVko2b3pwSWFCZEhBd01qaTBOSGNnaE1BZ1MyR3pFcHNZbXdNdk5wN1dEODM3cUJwWGNqRTRQTFp0WVVOZ1lYRndCOWxTNEhBQUI0Mm1OZ0lBQ01JSkJsSndNRDh4d0dobjgxQ0JZakR5TVB3Mk9HeHl5TEdSaFlGV0N5LzEreEJqTnYrdi9xWHhwTUw2c1o0Mk1ndmdnQTFsRVZMZ0FBQUFBQWlBQ0lBSWdBaUFEY0FPb0JrQUpFQXVvRG5nUGFCREFFaGdVSUJWd0ZqQVc4QmVJR0pnWnFCcndIUEFleUNCWUlnQWpvQ1VRSnNnb1lDbG9Lb2dyaUN6QUxjQXY0REp3TkVnMlVEZm9PWWc4c0Q4Z1FSQkRZRVNnUmdoSXlFcVFUTmhQQ0ZBWVVmQlZFRmVvV2VoYldGendYbkJnY0dMUVpLaG1hR2RZYUVocGFHb29hdUJ1RUhEd2NwaDFXSGJRZVBCN2VIM1FmZ0IrTUlDQWdlQ0VjSWE0aDlpS1VJeklqM0NSaUpNQWxRQ1dnSmg0bXNpY2dKNVFvSmloY0tPNHBaQ21zS29JcmtpeWNMT2d0RkMxY0FBQjQycTE4Q1h3YjFiWDN2Yk5vdDJ4dGxoZkpzbVpHa21WWjhpN0Z1eEpudFMxbnQrUEVpZVBzRGxrZ0lhd2htSWFrSlFtVVFLRXBCR2hKZ0s5QUE0U0drQkFlYTF2YVF2ZW1mWlFDNzlIU1g3cTk5eWp3Q3NTVDc5dzdNMXBzaC9DKzcwR3NHYzNjR2QyejNIUCtaNWxCTExwTC9pUFh6VmVpZk9SQVRhZy91U2dlRllzNUhZZDdlTXd4T29iVGpacjBqSTZGZjdzTUdDT0d3OHg2STJZUll2dGh3NkloMkVOem5jNkNBb1NjVGM0cERYVVZRVjlaZ2FQQVliZkJYZk1helRwM0JCVzZXS2RPOUF2QlJrZER2TjdQT3Z4c1BOallrSEN3OEJtdnJ5dDBsK0oyREZ1WFU4ODY0Rk1uQ2lFejFvbGN6TXQ2aGZNL0ZzaUdiWXd5WStYTW5SSjc5aXdqdU96Ri9JTVA4c1YybDhDY1BjdEtycUR4d1FlTlFiN1NGL2kwTStEekJmam5BNzVQL2Z5MW4zNzVZMXNlcDhQMzRFT3MzbW8zbStTbmNjcGt0bHYxckx4QlhxZmo4bXdPbkpLZmRpQUd2M2JoWTVialBrSVdWSUo2dXA5MHoxdVNkQ09FOEJDSE1aWlNQSkRNRENPR0VabmUwcVFMRGdMNUdJMWtIeDlJMnZQeUVNb3J5U3QyMnVGR0prbG5JQ3pRczRRb05oaHZ3VXloRnhNU2cyMFlxR2YrMDhrMDhTdFc4RTJNMC8yK2Y4NmNCUXZnai91b3FHUnNhM016YzdDazZQeGlyM0JXOE5JUG1NMkZDK2dwNWdIT3ozMVVJQ0tUL0FGQ0JTd3lZU3NpL3pHbzdzS2Z1WHU0VTJnaDZrZExrLzF6cHpOR1U2Q0VZUm1teDVhdlo3R09ZeGdXeEdqQkpsTkZ5bXBnRURJT0ZlU1pXYU14UUNrTXM3MkxGaUcwcUg5UmY5OWl1TTJDVlBmc1dkT1NiUzMrWUVCMGlVRi8wRzd3UlZBWmRqbXRPSUwxOVhYcFhTc0dxaG9iT3JDWXRTdkVjR05ETzI3QmlheGRWZHo1dUQ1ckYwYm91ZTBsZVhrbFJZZmJiaXlpTzZlU1hLUXNPZ2NuZnEvdHJGRk9QTkI2azdKenBrMDUwZmkydHJOS1h0NzYremIyY1h0TmRYV043Wnl5K2JqQVZsNmlZMytsYlcza3FQMmNzdm1yY3ZCSDJsYU9uenNIbW4zMHdtNHV4cGVqR1NpRkZxRnJrKzZVazJjNWpCYjJUSEZ4UEY2VXFBaHlETStDcXBTRHFwVHBRQjh3ai9BSTRtR2hzRHd6Z2xoV1AyekFlcjNFZ3NaSXNJZFkvY0RFY1dRSU93em4yUGtEU1ZoTDhJdlRQWUVLRWY2TUJpK29qeGNYdXBXMW91aE9LQmh5RmJvVnh1dGRxamJCc1l4ZTFibmhpaGdPQlFuSEUrUmFSdWR5a29Pb3NZRmN6bnc5V0Z0VjI1R01SMm9ibmNrVjE2WG1MZTE3ZUVjd2tRZzIxRFluay9IcTJyYkNsdlZUUnlMN2xqMndOcGk0cFZaeVNUaGM2UW56NVI3eEJYdXBpYWprTHdXdmE3cjNEbXU1LzZyaFpWL3A1YjRyZWp6aTY3WXlBem41anIvTTArMzlscW1zcU9kbzMraE01b2pva1hzcnZPVU9NMy9iMkc5bitGMFczVGVBVmo2dHMvbElSTldvQTNXalRjbVJRc3p4NWRoZ1pIcGdaZktZNFVjUmE5QVpXTjBvNGhEU2MyakVndlY1MkdqUUcwZk1tT2Z4c0FsV2FVVUtHUXk2WWFUVGhYVzl5V1JOalNRaGxPeE9kczJjWHROUjB6NGxMbFZMc2NvS1Q0bTlBSDdPR3JTUzFhbndVVlBQZW82WUpHS01NT0VtNFdBQ2M4Qzh3dnE2ZUdORFVCdy8zb296NS9CdHU3cTZ0SC9NdHgxV3NiaXE4UHlkYnB0VkxJcTYyYzFqcytyckpRbittT3lCa25xUU85V1ZkWFNqdXlUcWNSU2UveGVYdTZTbTFPWm1wN1VwdzZSNnVTQjc0SFBhWVZqL2x3RXZyd2RlZHFJZWRERHBzbUNFZTlwY1lLQzZnd3pITm1DZTQxVFRWZ0ZheUlCUkg0V3JXSTVoUnhERyttRWpxR0pGeW9BNWpoL1dBVnRGSGpTMzdsSkRoeENNcExzYTc4RVFJdFExRytZeFRZeUx3V1lwWkNLYUREcWJ0bjVCVVNCYzllRjRnaGlGdEIzUjZkMFpveUpVRXlrUVRzY1RWSmVwSGdPN0V5SG0zNDhWdXBxVDdiSFpzNmJNbk5Kd290U3BMM0s5cFZpRlphVmx5MUxLN21NVjVWTnZlbUhrL3I2bFN4Y1BQcjdqRmYrMFJHL0hLOXlwbFJhdjYzdUMxeU91azJhMzFDeVBQeisxelZsWVVGVlpXV1ZMSlZmWXlFNkJ2L082L252WEROM1plczNPMVllWG5CL3JERGROYi9zeGNBTy93RHpBT3NCWFdGSGJDU013R2F0Y3RWQ0h3UkNIZ1lCemRvWjRDZHhQRHFCaDJFT3d3azB3eG9vc0VrdVVUODlTV3hraXpyQUZzdzc5SEw0eUZxdms1K0RLVDdtUDZ1Unl2eWo2OGJ1Y0lVanVqTEg4Q1BzQXZ4NzUwRFRsQjgxd3VESUZaMEs0dDFTeFJHYWsvQmlxaEVQRW5zRFhBWEwxTVB3K25qOHdjTUxsTEdmSWoydWFybU5jVGp2ZEk1TUp4VERUMkdDUEoxaWIxVjNybE95dnZmNzZhM2JKV2V1Mld2Zi82ZmJiLzdTZlh4L3d4Y09sbGh2azU4K2VsWisvd1ZJYWp2c0NocmwveDcxdnZJRjcvejZYempVS2MvMXg3bHd4aHJraUZFS1p1U3J6d3BXSXpwVndhd0JsbURWd3d1dXBvSE10dEx1Y2pFNmZYcE54ZTJNRFEvZUlDM0V6aStqTXJCTm16QmY4WFQ3K3hodnk4Yi9QTmFpenhwMW56K0pPYmRaa0J1aDV2SnZMaDNYVGdoWWw4NmN3RE9JYXcxNGJtQlhFZ0dSZE1GTUhFU1hlQzlDSXEwaUIzMGNSTW1NWDdIR1lRM2lVaVBobWVwWUQ3UWNRQVBkcXJnNVdoM1NHRWdLQ3dNVWw0aXJEZGZtWVdtOUtUYlhpT1FrcDhRNGNJcnBPU2ZKUjZ3MkcrNEVPcnZycGNrRklXQTNOMVQrNzMrVk9CRVBsamRhRkM2Mk41YUZnd3UyNi8yZlZ6UVpyUWhES242N21PcHE0VTIzVnR2elhOem1ySXFYTzZCVGVjWXNqNm82SFBTSGhwWmVFa0NjY2QwZmhFRDhsNml5TlZEazN2WjV2cTI0alBIZ1U3ZU1FamdIcFJKT1ZzUGdSd3crQXUyTXhaaEJlVDZ3QmdUazhNNTlLTUJpVXBLQ2tONVJTQTJyenEwdFc5TnMwNDJqemF5YlNiNk1yOTY0YUc4NVRWcVg4RDhYMXloOHEzN0VGL0RUSGtETWZLaDViL29kNkprOFppUzN3bmVyVnNQd21XNEJYSVJzcVM1YWE2T0tqZXRPZjBadFFrREVVVWE1VDVFWGhKakV5akd6WC84M1pGNHpnTlZ5cDZ4OTRsVDAvUDMvc1R6V2VZaVBIbERsY1ZCY2V4V2M1Z1RrSjkvY2xQZGtMZUlpY0pib042RGJPWnJtT0RLSHNaM1RTWXpwbDhzeW56RW1GSElVSU92K1hBR2VhOFRhVWg0cVRoWnBsQU4vWEM1OTV5QktnZDg1RmljLzM5dmIzd3gvZTVoVms0bHhsQ2dZeGVrQSt4RVg1cThHWmRUOWpBcldsaHFpVUdDSnk0NnpGSnFuSEVONmpIa3VhMGwrdkdsQ3NFbkdKeXE5cjdvODR2M2c5KzR0bDNOZzZlN0p6R2NmY1kwL3lWMWNKWnVNbnh5SmtvMXNRQWJld0Ivek9MT3JEUzFGVk1reVFKQjdtRkk4TTB5SUVobEV2Q1JRS1NndEtDcDMwcDNTWmRRMC9SVzFPampkbFBubnp5aXZmdlBOTytybGg4K1lONUk4N2RaOTg3cnZmbGM4ZFBvemQzLzB1ZHQvMzN2ZGVmUEhWVjE5ODhYdkFqOU1JY1ZYY0dSUkFOY21vSGVBVjZBWjhzQXdHL01CV3BIaU9FTDB5emU4QWtzSmlNRTdXcURST21DM1lsclkyOFVTQXJGMlhyWjdqRlFGTGlvQS8vcm5kNmhEdFRvY1RQK3p4ZXFXL3ZxRjREc1dSTUE5ZWJaSkNWVjZYeC96M2d2THk4L09wek82SE9ZS3ZSN1ZvMHdrSmN5d1JXUUdJUjBLd0R3QnpsR3J6NVRCZnhRZFhFQ2t5SzdYSUk1QTFES3pQcnNuSERTUkpTRkNMYXFTcVJ0R3RMVk9uVG8vOVdValNyN3BXQ01BSXc0VTBtS1FtaVBuZHFhRmxxK1gvd0NXeDltUnptWGorVXlEYVpNWGZXZGd4cjZlL2p4eU1ERHpieDUxYWRuVEwya2VINUU4R1JZOVgrRUR3QVE4cUt2THdmZk5XTmN4WVZIbUFIUDFiMkYxYml5ajlKMEZYQ29IK1p0U2RuQjNGT29EQmdDcDZFT3p3T2c3SVlrbUlRbkFlQzl3Qm1Nd3JLRHBIbGVDekdUVkpVa09EVkJoV1VETG9MQ1ZSc2FYRTJJS1JWVlFKZ0FTUklxQ00rQ1Iwc2tXL3UzWGhjdmtQM3o4WXRBbVZCc3ZVZlZNM2J1cGJ0SjZnMlo2Qi9rVUx1bnNKcmJWekgxdkluWHJpb2NlNmdsOGVldTZGbENOYUdsM0UrNFM1WGJQblJOdmJZOU5tVHAvcG5rdUlmUzdxS0pkb1BIWU55TG9MYUkyaUdoUlAxdGRncE1NOWVveDR4YWdhc0U1WGtZSXdnR0ZYZ2h4RkZ1aXFqc0hvS244dzdnK0tSb09IRUdiTEFDSlhmZDBFUFcxVWRva1U2M0c5ZzYycGZselJ6c2R2VTdaalAxRzJqOG9MWU1lQno1Yk9xcGZ2KzEwQmR5cFdOZmF1b3JFUFpTdnVRN0NaV3NSMEN1TFlYa0F5R0QxSlpYWUU4UG5NWktjZUFEa204bUo1SFF2cmlvT3dhQmNNNGtFTFI0QnMvUkFSbDVCQ0hFY0Q0ekJEeEZXTm9vSWt1Z09DcElrTDlFOGZWK2pKdUhVU3V0UnJZaUtIaWVVR3czb0doQ0hQdEs1Y3VmT0pwWi85ZnVpNVhrVlc5K3dldkh6WndoV3JLaXVTall5ZjhRck1TdTVJckwwOStrNWc3WW1yZnZqVDZrcFhoSWdwdFhMeC9FR3BvRXhrZ21LWkVpdC9FMmlLYzZjQm4wUlJNdGtHQ0pjMWtWQUR2QWxReUNtMHNMQzBpT0hJb3FXOEhLSHlhSGxWUlJBdUxRc0dDZzJHWXFCSHdVK01udmh1TFVRSVVuZHVsd0tJMkRWTkcwWDJMMTZlQ1QvN1gzdWM4YjM5VzQrdDJ2NzY2SzZYcDRhanorRXQyQ0J2WDFvWDdXL3UyekM4bUR2ZE1NWG02V2VOUGJkdmEyMGFlblRMNVUrdFhyZXk3ZGphWCtMYXgweGpTeXBteDJLOXNZSHVWRDlaVjJlQW5pa2dvekswNElRVmdBdXhLeWF3SzBXd0N3QitHemdIZGdqV0dpdWtsRFZVbWl4V1RxSFJDZWNHS0pRdFF4N1JYY0VUK2loZXdTbytKTXJtVjZUV2FDTlpIYzVXa21lVWgweTFnS2lqVFRwOGpYd0hXVEkrZ1RuUEhRSE5xbldmbDl4dXZTbGFac2xuTDN1UkxCTGNSd1hCb3NkZzNuNVlJNlhnbHVyUjlPUlVwdzVRQmpIY0JoQUR3NC9vcVRmUktkNkU0elFUVUZIaDhTQlVVVjlSRjZ2eWhEeEJvUnh1VVZKbDFCeXpUcDhkcWNVVGs4UnJURlpjeDd6NzdLcSsxTkJsVzErNytlYlh0bTVjbWVwYjlleDFzeGFSZk15aVdYMkRnMzNranp1MTlON2xnemVJNG0yWGJmbFdYOSszdG15NlZSUjJEUzYvZCttYnFZNk9ucDZPanBRY1d0TFYxZGZYMWJVRWRPenVDK2ZBSDUwQ1JsWVJIWE5naGpNVGp2ZUFkV013eHdCdFBKL1dNUlVLQUcwK0gwSytLbDhrQU9FbThnWUtRNnFPQVVVRnNNNlV0ZExPSkNiR29jU1N4N0RJL0pJb2xIeFF2cTZFNk5venY5bVluOWExeGFCYXpWVEp1Rk5VbmVUVDh1RjhyT3BhOTIwN05GMTdoNmlXb21Rd1c0cGIySWNCbzFBZnoybklKVURzTWp0TWZENFlNQ3Y0SFd1cHRjVGxvR0NHK25nMUo2SDRIQ2IzVzc0S2JiUS9aa0VtM3pWMk5DZjNCWFBZQWRoUG9uUHdvY3BrcUVqeDhDejRlR1p0WmtJWTdJM1BDeWlEeklDZk1BT3F5cm00VUp2RjR6bjRNSHN1L3prUktzS2F1d2FsdUdadUtuQUVzS2lSNEttZThmRldXVG5Gb2xxc1pjVHBPQXVyenBmOWZwNVRjcFZJWXllWk9WS0pTM0xtT2M5L1dPeHlGYk1XYnFwVTJlQVRIUEpiOGxzT3dkZFFLWm53SFhrVjRUQzQxenRBdng1Ri84VUo3R0ZBcENJS0o0TWdBOEtLMWVtMFpRRDEyZ0YxMmtXN3Y3U0k0bGJkcExqVmZta2tXelR1TzNzNEc5bks4ZkU0RjkwQnZGbWs4YVlnZzlPejRydXlrSWJUZFZucEZpTk9oM1dZNndBK25QL1FxWENJbVROMlV1VVFhMkVPVVQ3SVcwd0tqN0NFSlpWSDhoYmd6YzlBWDkrSEdGMUNkZWk2cEFWMEJWdkFaNEd5cXNGNk1HMzl3QjhqZmhjeGduUXBTaW15TExsaE1EWWlSMUozNHdiQ0dFUTBieVI3MkVEU0dRaUE4dFVGYXFzcTRVZEZLVktockZvYThGRjNVSTJESFpOZ3JYaTlQUWZ2czhWdmZQMndqcWxLSktvWUMrTmZQM3ZtM0pTQ1FjS25IMnFiUGoyVmdqL3Vvek9QN0g4ZzBsZnNkaGYvdkVydnRNNXFuejZ6akVLd2Z3azdsNXlQZW9WalJIZVBxV3NIK1MrczU0NXdjZFNGK3RHQzVOd2lGMk5rSUh4aW1SNFQxaU9PMFhNamlERmpJOHNZUnd3WXdqNEV6QUw0cGRQeEF3RENTR3FIMTgzdjdrYW91Nys3YjhFOHVOR2NhREFZQzRoQkMvSG9HYWVuTEMwcVFCV0d3WExMdGs2QzVnNHpJYkZlTTJWMnFaN0pzbVVpVy9zZnUrZnVYekpqbVMxMXphSjFTKzVZdUN6ZzU0c2NycEl5YnJhaHZEallLaTU5ZFB1ZW4rOVlmSFQ3VjY0ejZLeE9vOTVpYWZ6V2dpUC9jZU1SN0h1cWVtYTFWQ2JNaUU3ajRnYyt1Zi9HVThNOUhiZnYycmIrcDN1Mnp6RHE5SzQ4K2JWeWx4Um8zOTV6MWZGVlgvMzR6aXVmSEs1Z1MvMmxOcHVkZDN2M2ZQalFpN2psR1RrMTkvcjI2dnFCRzJMckVIUGhZOEIwWjhIUEppRENuNUpzUkVhd1AwWjJQZExyRFVNbWJEQUlLUjNIc0dRRkFrekNJakZHelUwd3VwRmdPbHN3THBvTlpjU1c0MG1nWE1pdm4rU29JMjNrL1hxMm5tWCtyYzZNaFg0MWtsNmliUHVpOHRlaVhlcXhUY3AyMGRnamFoRDk1cExyUDdtR08rSVR6bCttSUR3RjdSMDhtUDJOTlNyYk4rVEYrREZFZmZOTW9IVTcwT3BERllCZ2Q1emdzWjRqdUtJV2xrODUrREE5NXZUcmVZSmZBZk1SOUtCVEEyVVNYNVVtcThBYThUeUJIam9BdnR2SUJUcTRBTFNKWGFtTVJ6cWROaHdXRUVJMXNVaTRncmh5SC9MNmcwMUdiUUhwRmJ5WWljMHlMR0UxakE4d21XN1pvUi9Pbi9QSHQzODY5b0pDL1dXWHFUYkxlUFMycFVzV0w3L3R4WmVIVnIvSUhYbnMwSUlkWXZ1NzMzNUNZUUpyVkxaeUtEbXRzMjNNdkw5ckZyVmo2d0dmckFjZkhrT2R5V1FsQm9oSVBRNHNIQUtiK0dFOXdCVWwrTXJzTXd3MUMyR09JRjhBOU1HZ0tBVUNCaFhPTzlXY3Bwb0NoZmtydUZmTkNDbVJjQjFOK1hOVnNiWloxZlhPeld2MzMvNk5BLzNmWEZGZ3JmWlpZMmQvZmZUVFcvYis3ZTRuRmpjbnVWT0FqRWNGTDFDNDVwclh6cHorY1hXTllXR3dyTDV3NDkzWS9keHA3TDU3VjRkbUExcEJucnRCbmg2SWZKY3FZaXhTeEtlajR1Qnl4Q2VseGNjaERzUkh4S2FNSXpBc0xUYUk2Z09pendzM0xRRVYxMU9SS1ZIOTU4dUx4ZWYzN2ozL2hCeFd4RE04ckNycmIzWnV1UGYrKysvZHdCM1pKMzkwNW96ODBmNWNBWjF2ZU9uMDZSZXBiQWc5QVBoUkhIMm1nTjJZa3F1R3ViSWN4MjhqWXVJWkZnSXRqSTJ3T28xR0FXdzd4K2xXZ3VLSk9wSVpzY0JWMVZsWHNUdzMrZ1V1STZ5clNTZkd2K2gxeVZaa0FKaGcyRGJoU2owSEt5TTlYMUFzNDBybGVwUzVmR0NBNXRXQjJnWi9zRkcwU1g1SHdFektjYXBPZ2Zmd3UyZzlUUWVyUVEzMDZhbEpCY0hGeWtqK1hMNzhReExwZm9qdmFlbWNWZ05oL21DdVBOamJ1U05sb3Z3TGtpdy9ORVppSy9tZEg1RXY4amNGWDY1a2NtUlNqeDVTdUJ2U3VLdVVEOWJyZ1R1R0lhTmlLdFAxQTE3ajZ2akt4TVhIZzdUMXdHcjl0dkZYQVBzTUt5ZGVBT3dqVTZ4SHRjUVVFKzZacUNuT2NNL21yMU1NeldSeGRqYnJwaW1zdXc3WEVON0pQL3RYRlI0ZFU3WTNxZ1ZNOW1nVzcrU2ZFdWI5ZDNhZ25XRWNSblBBemh3Rk85T091cEt6bW9Fc0YyQU1FaWtBcW1NNHJlcGlZR2dtQktMczlEN0RhR1VYT055TzJvTEJZRndBYzVOTlhJNjVTVFJtS0VsbkZteXFEODQxUDFiRi9HellTTXpQMXRVdmFmNUUyZm9jdHVWdlg2MllvaWNYcWFiby8xQlQxTGVDbUtLeVI3SWRqRHhXSkJscmFqU3pkRlVDekJJR2RJYTRlMEJmRmhMN2lzeGdhY3pjZW92SndKTGF0RFdQb1l1SVowa2VHcXdVelc0Qm5RdlIvTzQ1czJmTm5ON2VvdnBWZnpBL3V6UnRtMHlDZnR2bnl6WEREWCsydEpXeWRGT1Q2bDczS2R0T2VXZG43aEZ0Qkw1S0hZRnY3dFNPMERnWW1IQStSd0Z3UlA3MVpBcWhNdXdUckZjVmhPVG5FU2NBbjBJRTZYT0FwUGtoa3ZZVFVzQVpZQTNTT0JOQ0FabzlTaWY5RkhycUprRDhiSnY4SnpyTHYyS1VDL014K3F2cU8zOHgrZnpUQ296UmFsckhQUUxoYXp4WlgweHlyajFrUFlJUEdjMmVMUUpKcmdKZERoTmdCSU5EWWlBb2pwdXNtc1FqcVFVeWJSdU4wYlBxQ2FwQVR2LzI1MysrdDRBcTZJemhCUXRrTmMzRnZLL05kZXl1RjErNnMwREEwNmxLeXVlRi9tVk1mOXBVcWJyM09zeDVKWnFmN0YwTXZxOEtJblNTQVFLb2dzRXFjd3o4MjJWV2xUSFBvaW9qUXdKZUhWWXpkbkQxaWlWOWl4YjB6QUcraStGNGt5MW96ZFpFWEViS1BXNFN2V2ZWT1Vtd0U0cVJnbzhvNUdQWEY5VkxuS1dXWDZMa1J1UUhwd3dLN21DUlpDMnM4WmtVSHV4dld5eTVpKzNCZ3BLa1VDWFdiMWYxdENJWEVlR3ZLZHRxUEwxUlBiSkg0NTM4R0p1bzhjK3E3eW9LVkNoSHVqc2pUY0dlNGxCVXFIdnljM1QyUlp4TTY0VG1DeUpvdFFZYUdVUnlVNk1RU0NIZEVFUjlPZ1YxYUFuUVVoS1dLVVBBRXJDWTI1WTlFbVVHRGlUekVhbkNoUW5UYlVHS3JiSldyNlk2RjNOK3pDZVUzamZ4RU5XZmpOdTc0dzVWaTlhbHRRampLWW9DMVUxMGVCaVpnTWFYZ2NZVXNWK3pBMTZXSTFrQWp1Z1FIalZnb2pobTAwV3NXQXAxejVnR0JFZ1NXYkdXYksxeFRLSVJaaVdNREpueDUwY0pXbE9Wbi9zeXBTVnViYzAxVklPNnIrZkZLaU14NnlIZDh0d3pMZmx4VlJNOHJsTGR5V2QwcFM3c25YenRNL1BrRGFMWEsrSzd4cDZlVEIrc050bUYvMkt6a25VR3R1RVk4S2dERFQ5VFgwQUtWV29NWGdxTGlZZ1hmSm1pQ1F5RGg0bEJDNVBpdFcvaVdYYUlpRCtsR0JERm4zZWdOZ200RjRkQWxMcThIRE1TREdIeFVrWWZRckZzYTYvd3JLbXVOUmExeWUzYzF0eWdxbE96NklhS0F2d0FwMm9OdmpyTm96Ni92OWpEbkJ2NzNtUThLUjJiajhjMDNXRlFCL0RsMXYvdHVobHIrdlNXV3o0OWVwUis3ci85OXYza2p6dDFsM3p1dWVma2MzY1Q5L3NjZHQvMTNtdG56dnp3aDJmT3ZLYkdCVmVBZkFJUXJLelRWcW9Pa2JodHZaNGlLTU1FVjBOV0tzZnI5ZHcyYlNTRXdQektpUU1wYUkyUmZIa0FpUlI1R1ltMVYyRHFKUXhmSmxpNCtXOS9lLzl1RFdiZG8yenZ2Rk5kcStMZFYxOTk3YlZYZ3hCKytzb3JQM3RxTXM2UEhSOWN1WElaNGJuOGI1VG5UV2dHZXFYN1NRZlFhcXJEU0s4ay8wdVRadklGOTVnQVVuWVBLT2NscEFjSzlZajJiUEVETENncEtmdXZKZUcrYnRoSXFqZ0dBbCs5TURhZ2phVVpGRnBHSUU1ay9HQ0lqVmxhd1JzbDQxbHk3ODhaRHNqVjNkeU1VUE9NNXVuSmRwajZGS25DSVlsQk00MG9WVlVJNldrMkpTZXZvdGZLRUdvMUpVVGI4aTZ1Tk1YT2piMjl2aGsrVDB0SmI3Y2xyekNTN3hDYk5qZEozZlZURjhhdTJxb3pPQ3J6QzIxbnZuRU14dTQ3ZUhBZitlTk8zU2FmLzg1MzVNOXVZelo2alRyZVdLR1RmRUZmWlVtbGFEWlp6TldzNUFtSlpiYlgybkRSSzkvQjNHM3ZQZlB3d3lkUFB2endNNW1ZOUZuUVBkS3p0UDBFckhHRGxtRVFrQUhPRzVnUndnVTl4Rk9rcXNTekRNbXRja3B1cFJUQ0JaM2VhTlJ0MDhZaW8xRy9jcktoTkwvUTB6VnpPdnpTVktLRzRYaWJXYXNjRm42dWg3NEltcHhNVFpmLyt6L2o1UzdSWFpUbnJDaDJxSkhVM0ZWaHA4Y3BGZnA2R3BOcVZDVTNqMHRPNUQ5NjE3cFZxOWJkeFIwNS9kU2ZXbDNoMHBab2pjdnZWMVE1MlMyMnhUckxJOEVMYURMZGx2R2M3dTQ1b0VCM2dUM3BBTjN1UXFsazEweU1kVDdNOEFUUFlOMndRYytRYWlQd1BMTlBxbG9zV05Wd0NwSDJEcnBMSFZNWG1qTjltaFNRcXFXQU1TdHJvV2dTaVNMY0NzZVVsRjhvcXhha2FpQmhoOEs4a01xa09xV0prZjFWUEFMeGw3bjZhOE56RmtwQzFXVWJibTcrNXZMVFgzbmtTcVVkVVF5YjQzZXZXVElZRHBXbnV2c3VyKzNwVy9YVXRubGZxYXNGdXJ5Qy9IZkJXMURRTmIrcnhSdXcydXhPVVJyKzdaYWpnMnVESk5XSmV3V3Z2WEQ5aHRuSmlvU2p3RmxnTHl1cDJMTng0ME9ERFRVQmtnSEJhQlhvMmtiUXRTaHFTTmJxc0JvMmtqeWRWclRNK0JnSzdhSW9JcExZd2hGUXE1WTJsZEtMT0JWYmRsR3NweXpSbElpYytLMXF0UHFVN1c5UGtLTStnZDFMWThPbC9qS1lPWUNNSE5kNlFmNVBldnhoVWlURGFvOGt5VG1TM2h5YVhtU0hRSWcwRjBPNkg5T0FPb0VhUlpFQ0NtTW1LVXQ4b2RhVk0ybm9wd0RzQ1JGUDlaYlhEeHg0ZlV0MWJsU1QyckppeFpiVStMaG03QWY3WGwyNzl0VjlURk0yR2h6NzNmWXJydGpPQkRMNWdRc2ZBeTFuYVMwWmFKRm96WVJYS2RMckZJbzBZa2pOR05DZG1JdnVWQkNFSjZHa05Cc2VQMEZuT0YyK3k5cmMxdGFVSnorb3pmbTRzaDM0elI5bmFUZzQ3YjBYUzk0eWtYMHNoNFo3bWJWWjgvOHJ6UDlkbVA5VTFKeE14R00yRnV0SU5SeVIydjRvZ1hpZ1l3U3hjSnlRWXJCR3lsVFVRVUNlRkpSeVFRcHJaUlJFcDhnbnhFNUtsYko4Y3FnN1JXYytaUzFiV0JlYjFtTDU1b09XMXM1WXJZc2RybE5wVWdIZGpzWTc5QlhWZFZXNk8rUHJKOFNpaTRzOWxqSVIvMFlPaTJVV1QvRTR1cC9Gajd1TEhDNDV4Y3pPeXUrQVFsSXN0NUJVTkdmWGx4azVJa0tUVVErRUc0WXNaa1pKZ1N0UWw4OE4yR2ZOaUlOQTZiKzhiTEJybkRRWlBsa3UzRGlaMk4ySkxNYU1LSXlSUDhaaVd5NTBhL2pPWTBIMXlLaXliY2VpL0VsckxzTWlkeHdzVW85c1NnZERlK1Vyc3Rmbmh4L21CUEgzNEszWmpQdjV6N05qekFyZzExSGdWenRLSkJ1QVhTeGhseDRZUkdKaTBKTkpRdmgyMUtxeEtVZFpKa2RMbDF3SU4xQnFxdVJIWDFVdDBTNWwrNnI4ZUN5WDlzN1RaeG9uTE95UDVHeGkwUVhHbEJQdnZZV2xkTHkzRDJpZFFuTVVhNVI4cktoMEsyM0w5RFJwYVlCTDlUUk5IS2YwTklWUVFDeHNGQXZUR1lOMFMxTldzRGRKZTRKNzdHVzhsU1R0SU5UN0JkRG9aTnJsNCtRN1dPSUNTbXViNy94L3YwMFRtd2RvbkRldGxEWFNSQ2RlcWZTTVlDeklUN1AzODRQSVRYSXdKRW9sRDFOd3lqTXhYT2FaR0JqclJvVlNZd05wbmVEVTBvVTZGelhCYVBPelh5S1pRNFk2THBsbUVaL0huWnVxcDAyTGVRVmRSUENTdmMrS2xkK053ZTgrU24rM0loa2d2OGRnbGxtZmFYdE10eWE2a2Nzdk5mSksyY1NtL2k3NVdadTJ3OTVLK2djWjhvTzRVMzZlYm1WKzBDdDg4bXZCRzVzMnJacjdFL2xVZFBjbC9Ddk9ESGpDaThKUDZkWk1UNWE1cmFTQ2ludUFic1RzSWMyUlY4RkFML0lFdzV5aEtQS1VEazBucFMxYXN0RmxERnNvM2FERTNGNXR4TzE4UEN4NHZHSDljOC9wdzE2UEVJN3p1TjBZaTNDbjdJNngrMDBHdDJneTVGdnhYdms2YTc3QkpMb05KbWFWd3c2Mjk4MnhDOXdIOHJ2SWhzcnBmRnpqV2FCMGZ0SnBUTWgzY1c5YmRUcHIzbWVWZVhUTG5aWGZ0ZFhVMUZUYmJOV3dJYkU4ZHJKamJBTi9GTzVmVE85UFlsZWxSYkxJbWI2eFVxWUpCYlIrSlo1dEtDeVhMR1o1cEtpaUtXWXJ3TXU0L2NEVmV0MGJsdkpRdk50OFFjRzVXOEJ2M01zZVIzV3d2UCtndEQvbis3Q0JiVzBCM09vQUNsZ0lQbktPNk5tZUFTVk1Ea05vUVBxc1JrbVBrZ0d4aGhGU0ZxRFJRU1NsSnp3WVpsUkFyTnk1L3RJWEFMa2kzZFVhbTBxVHRaOTNGVXBmQkhHZWRnMEpUT3JyRWFwdnIyOXJTZ0J0dFNLZ3huaWpXUU9OaGJtQU90Mk9ReFBNSkNPZGFlbk9kUGZIRTQwUWtTUmVGY3A5aWpXNnZIMm9lTzZUeTY4NDJ2Lzk0M3Z1WHJTeDVlQXNtNlU0VkpBZkczaHR5WU56Wm5YTytITEx6YnZZNC8veWxQeE9SVlF4VFBXSnRzN1VWNGNQM0ZQbTdVeDZpL2hBVlpXbjNsWmVQdlpHWFUxMWJhSW1XYXJJcFJUa2NobGZqaXBSTS9xQndtNFRDd0djRGNNYUE1R29YMGd1WHBVR0dEVTFJcFpTNURFSUdxZEhVam9hdmFzdVg1VkQ5T0pERlh1dlhvWFVqRWNFaGlJT3hEQnk2ZEhBKzhKSUJBWTBSNXJxYTJIK0ZmNWdZekJnVW9KclcyNGpHZzIySnd0ZDdGb3RYcTNONDBQZStyMjl1MS9kc09IVjNVT0hHN3pDdXlycTA4cHpucmMzdExkdlNMWVAxdFlPdHZQbFlFeVdOYldOdnZXVnI3dzFPakJ2a2VCVmk4bDcxYkQ3aWRZZDgrYnRhTzI0c3JmM3lnNnlSbThrZlhkMEhYUW1rN0dMMUZNaldmWFV5TGg2S2loWk1DUUdneFBxcWRtZEJabVNhbGFQbEZMVVlEOVJpaHJoK1Uyek43VzBiSnFkK2xhUFBUOHEyQ1BMMzFoLzZQMGJkdjNyM2djN201UHNjVERKTDlERVgrWHNTTWVPVkdwSFIxMlZhVzZrTEZyVTBMenpyUU1IZm4vOWpqaUpLeGcwRERROW91clFkNU1tSHl4ZEcxWWVIcGhNWWNqVFhpeVI2OFNGRy8yY29VTjA5ZWx5bHF5aU1DelByYi8wNklrS0l3WURjVkZUbUt6SGJvSnRPSnR0aGU0c2hVSGpGSWI5MEt2Mkl2eFo4RFljSGxKVXAzZHZ2WnFjd2IxeUJkV1ZKTlVib2pHZi9WVlJEcSt3YU42QW9qcHRUZGl0YVl5aUs0cmVLR3QwTi9CM0x1aU1IOXgvUjdJMW5TSG00U1NQYUI4dE4wd1NWUkdhSWlaY0NMTzlnb0NRRUJLQ2tnZ1hsb2NkQWdSeEpXcHpvT2kvU1A4SmtLalQrd2xkbHJPYnZjTFlMc2NOSys4OVliRVVsdWVaM0NWcmZyYm0wRnZici9uM3I1K000R2R0Vy92WTQ3dlAzUzE0NWkxT2NCVTFnWklTcjlFZjNQbTdXdys4dGZPOWUrWW8vZDZQQUNaYXd3ZFFFN3BjRVhGWUsxY2FNS1BIV3NIU09FenF2ZEs0Q21kSUd3c240VjVHUEpLNUtLZTBTUXZESkM5RUUyeUNXRVFMdzhwakpzcnpKYUxneFJuME1XazZRMm1TcG12a25rUEZ4U2FMV0dTeDNUaDBFMDVRZlBKRFhLd0NTRFZIZlBJa09YN3k1REUrMEdUMGUwcWtxaUFmZXJpVjFvaW41eURrTTZSRGVzN3BsOGxha2RkeGo0QXNhMUVIdWtONUNpR0llYjIyVmlJSWxKbG51VkdUZ1p3YU51b1kybU9vMS9QRDlEa3pyUlUzU3RRL25qTmFjMVhLcFVQb29oZUMxNnFyQTB2U1VkYytKVTdhNUFOaWtSaFV2WlpiYVJVZmwwWk85NlFSLzVTelBNWjFYbTRsUnZQUENvUDYvL0xudnRlWDErVGxCNHJ6ekM5Y2VlMG1NSzAzdmJweDQ2czNOVzdac2p3NTB0WTJBblptWHZkTXpXeU8xYjM2Rzc4M1AxNFVxNjdrV3RhdVg1ZG92ZmJYWC83eXI2OTk3OGJ0MjI5TWJPN3QzWndBUFFCNHhqMEU5bVk2Mm55Q0pjOGZxVStoU3NoZ1VCb1BwSFNyYkdSODNhRTBLUkJ0TWlBajllK1REMUlVYWpxaTFRbWFVTkE2RGRUQ3ltU1JDSEhvVnV6Rm41OHN3NDk3cjNsMDJTMWRxZHpLUTNXOG8zbERSM1h1d1l6WG9aNm01T1M4TzFmTHd6bXF0YVozM3ZDRGcwZHk4bUo3dFFEc3dnVzYvdWJ3Q3dzRXRCNmhBZ2F0c3lyUFVUOGdyMlB2cGNmWDBxZW8xNkZuNlhwdGd2RUhnYmRUMFJWSlkwZk1iT0pJZ0sveFYxMXlVc3BBYzVLZ1hZR1V5VWhZaDRaZ29TcU5Nd0lZSms0UFR2emlneFQrVGtWSnFZRVdMNlJHd2wrcFVEWEFJVlovcVpJZ2lDSWdxcUJlN2ZuUU8rcTVIUjd5MUdPZDUvdytyVU5zMVhoV2dpSGc2aWp3djU5OFZuenlqN1kzS3R1QWV4VjR4Y2k4eVJnSmRqRDJxMkE4RVF3bTRzRWZ5azhUUHQwSGZPb0FQdm5STElVNWJyQzYzQkI1Qms1S01Xa1BSRkNOQ3c2Q2orZlk5ZG5IbGNmay9NaEhLbmpxWTNLWHFGTXpQL0pxTnVpOCtxd250cDFUZDQ0cXJtVnlSY0FYUG9ENUhnQzcwNEVPMHdkdW5tbE5NRVN5Z1BCYU1hOUxBUGFnQ0k4OGl3T1lYakVuQmoycjB3VlNITU1vb3RYOE9lbUgxRTZTNEgyU29Va2ZHVFdFdENGcXcwWWtQV0pBSzErMWd4TnVETUQvbVk0TitzU0tUV25adU5qWHpCUDFwTEdaMmlieS9MS3cwU3ZzRkx6RnBkV0ozQjIxT2VFWWhKWTM5bnd0RXJ0dUZudjg3bStNblNFUktHTnVyTHZqZ1B6NGhQM2JOUVc0L1lvcmY3eG12Ym8rbmdBK1RrY2pKNmFSZUYwMTNCN1NwMjhZTmhrWmd5RXd2Z2V5TkJra3B4VW5SeUlRR0RxRUpobW8yWjNPdUdaNHpHcWk2UC9aNGlqOEFaODI3MzltY3o0VXZEZC9INnp6RjdFNERLUHg2ZUQ3NE9PMkFsNVpEanpLUjc3Y3VsNWtRbDNQVjFCV1ZKaXA2NDEvdXB6SndWcU0vSWZyci8vRG9VUDBjL2JHcHFhTnM1VlA5amdCcEcvdFZEN2ZVeENVaHJrWkZKQjNjcGZCZkdwUUV0MmNORVV4eDVzd1N2dGN5VVRTbFR6eHRUeFBYYVl5eFV4ZUtrVGNSalVkbHVWa1ZXTjRzU3ZBeTVLSHZtcVR0UjBRRzlhZ2FpSlR0V2lWaVV4c2w1YmRSRWF3SFJyS1ZGdGNaWVBxY1hPdzZJYXNVSVU5cmlGTitad2lyUEUyRHNEb2U3blJDc1gyd0x0SE1yd2p5Q0tRaFZla3lYRktPRk5KQ0xFcTd6NGZvT1JlTVlGM0l1a1F1QWhDbVl5RG42TkVPUWlsUDVkL2o2U0R2OElzME00ZXp3cnR6bCtuYkpWUDdOYWl2L2ZHNDNhSTljQldFTDJMbzJkb0wrQ0pldkxzVzA4cDJXSk1ySzJGbGt5Sk9hVTFxVUNLNUpUU1g3S3JNYXJ0cmNxMFRtWXV5aFM0eGwyVEFkc1pZMHdiNlVpMUo1SXpka0I1K1VZY05TcW14MDBMS0puSDRsVkw0NytFVjZiYXluN1lYV1czUjR1dEJWTmFVM3ZuWXpXTk1iWklyVnZ2VUYyV1hmQjJ2N0tHUFQ2bHZNRWZqY1lNdmxXUGJ4eWEzSzc4NjhIN0ZKNGVCZHNTby9hM0p6a25DWVNYamF2eFJiSnFmSkhQcWZHQmtZMkpBYWxhREdpdkdhRjlWMnFGVHlud2FjczA5K1VpUkpsSWZZOVcrSUxab2ZXUDZBdEZXZzZ0YWVuc0NxMVlmbjFpM3RMbFQrL2FmN1gyVHBHNnc4dS9HYTBxWHJiMllNdStGUSt0Ly9xTzJnNzJ1UElta1k3R1NySFNiakthQ3d2OVZ3MFA3ZStlbFg2UFNFZnp3dUl5RTU5bjhmbDdqdlovYWNZY2svcjhNNG03RjlQZTdIaXlIbHdSU1l1TzZ1anpsU3g5dmxKdGtNenR4cGJFQ2xHUUpLMUFsbTc2dERuVnZJRWFFcXFWUGpVc0l0bGJ4bG52eE50cE1IVHJUYkhyRnhUbXVhUUN1OHYxazY4Zk8va1NPZnhTMnl6dUZGbE83OU1nNk04UGh3TkdzU0xxS2ZTYU43eDhHb3NrRE1JbFN0OGp6UDFyN0dFMEJhMCtZY3Z5b3lVa3g4T1I2aDdIa1pmeVpPY0lrdExFazBxY3oyZkgrVlNScDZDNEZBRGNIaGUxMG1WdWdLK2JVQStrK1RwaUp0cXlxZ2ZzWDd5cTAzeVgrTU1NYnNjZ0h1byt0V2F5SUhzWWNPTGxHVWNJbmhNL29HZ3pZSGRydHRja2RSSFM3d3IwWDZ3T0dQamZxZ1Blb05ZQmY1Yy9mZWJNYWZueTc2ZmxkcjkxUHZWMFFqMHl5aDVXNDdCQnNheE1aSTdtVkRwbTRWUGo2NEF3L3c1U0IyeW9LcUIxSGFUakVLZER1WFhBUUZZZGtEUXJTY1FMaXVQcmdEaVRMZy8rVDh1QTRUc01qYTNOVS9JTzNHYWQwdEphYi9pcW9CS2tQaDJ5dUh1ZnVTb2NpWmh2NloydFpXVXlwSktTSjE0dDN5ZVdlYVZ4Sk8vRUN6M2VvaEw1WVh4emRrMkxQQmV5RjJqL25CcGc0R0kxd0ptMEJpZ1dqcThCNnI5d0RkQVJ1bFFOY0xIU3kvWmZtSzNQTGZoWmQrKzBxVWZ1VjdaeCtlT0czUHAyM3VpMWhlcVJWUnFUUHBNL3lUYkxlL2ZtQUVMRHA5bE0yNzA3WFErcmtOZFNIVStRZm9NcU4yMTgwNm1xb2E1aFJEcmV5T3RTdFBJOU1FZHlqU3ZmWXl1ajE5RVhFYlF6aVMrbzhFbjVwcGszSHJsSkNwUVd6MTA5djBuK1NYZXUycmNlT3hZZnIvYm4vM25yblcwY250SlZYOFh3ZFp1M01EdHl0T0ZtdkRQVDkwaHJmVUJiaE5UNnJCZXY5UVcrWUswdk1MSFdGMEZoMFIyZjdQMEZPYTJkY2EzY0Y4UFVRZEY2bjlVKzloR2UwVEN6T3BhdlZ2eXNkc1lzLzVRZThRbHNDWHNZYUNtVkhHUG5kb29lUzBteC9FOWE5WU1qakh1YmNrUXNnMGsrSkQvTnZzOFBRcXkrS1dsdGdVQTJINllmQmdlanZmcXJOUDJxQXBLVVpOYlN6RFdoaUw3VXhrOWVwWUk0SG8xa2hvSEl5Vk9ReEY1alpuNDZGWkJvckk1S2dyYzBvRmRmd21HbENXMGZBM1M3Q1BuNVdLY2dPZTJaZWRMTXBUd3JyNlZxNFZzMURpcSsyR01wTFZwMVdZamo4YWJycjkrS2pUaTJjV2xScWNVamZ2WUJtNGV2dmx5dHJXekhKdmFEOC94Z3BEMFdLNGdzNngwdUdibEZOQW43MWpsTnV5MUZuZk5DK2JGWWU5VlRwNzIrcnhvS0ZpKzN4YXFxb3JiQnhRWEd6V1dlRThkb2ZmS2NmQi96SGsvZWFSSlhlSkw3L2hIdFJVZ0RFMTZFbEhuaGlTdXJkWWI1VG56YXRDVDg4ZHU4d2lmZkpwMHd1bjYvVW9ORjc4dFBjeUdReHpRMGtyU0MyK05xNEo1dURFcVZsZ2NNWThrYjFwUUhnNUgyTnF0S1RwTUhyYkJraGdFSUhFREthL3hZSWcvU1dUd05UVzF0RG9TRFlYMzZCVDVLY1VxRFJQRE5od3MxT2JTcitGcGhmcUl4aHFsa1l1bDZGK1AvZ0RYaDdSclRyOFo1N0FlZmlVUkVTemZHUURaYnI5ODlvdU54ZE1NZ0ZSRS9lT3lFcDJ5enNXRHhvQzFhVlJXekxWOWNZUGlxejN2NnFTb1FVMzVvWG1lUlpiZkp1VzZmWUFyY2ZlV3d5ZDQ1TjFnQWNvcFFIdDJFRDNEZHpCZ3cvM0pTeDN4R3NJSmpKUUREb3ZDSFpkQ0FqaWV2UEFERVJCakJRSFRLSUdZK0FjekFIMkRyS0t4VGh1VUFPQ3VqNFNncERTcURFUm1yMWVPRG9oUVM2YXVBMVBMdnhQcUwyamVtMTE3T1FkNVU4ZDZLYVkxZFVxaXQzRjdvRDFmbnRleGZHaDlPeG1lTDJVZVlNVkh3ZU1zRlJ5QWNzTG42bDBpQ3g1UDVwc1JuYnpHTjdFcTFoelpCcTdaVkhLa3FLYVJCVU1ZTXFERTNnK1pQMGtxYlhTeWU3S1Z1ekk2djlmZHIvMkpUcDhiSUgzZXFQK3ZvTDVXRHNhbXcwQUVYQkxuMytPMFErZGVpZWVEeW5xTnpjcGd4dy9yQlN5Nm9aSGpUZEt3M2MrcXJlcVlBZjlrOXhCTHNRYnpKYk9MTm96cU81TWtnUXQrQVRMekJOR0MxNUxGbUk5WWJ6UG9SWkRJWlZpR0R5YkNBUEUybVhLcURTM1ZZbDc2ZXZwenlVcGNQSkQzejU5ZlZ6Vjg0ZjJIZHZMcTVQVjFUazJLd3FGZ0VXZGFTSjJrb1g3UUdBdlZ0T0ZSNDJydHc0RU5TWHhRVVV0OFVWT2UycTIyOTJoTlY5T3FFK29aUFc3MlkwRE4rcDFzT0Z6bWM3dnV1ek1zcmMrZVZnbnV6dTMySDNFNW1zZk44djhWUTZpMXlzdDhtMjhzaER1bjJWZFpVeW04N0JKMEJ4NjBSTVJydC9qdC9ML01Ud1I4TSt2SGxyZnJhVXBjbjczcDlpWHZzbjBMQVdPaXdqUDAzSDVWZ3l4ajU2Rml0RUFqNHIzSTVuTTZycG9yNUlJYnI3UGJpUXZuV0gvd0FzU0NyRVBlT0txc2g3S0tTeXRja05STWtaU0JHcFJpa2xCekhhaVBtRFJZRGJ4bk53eGF6MlhKNUZzdVJnVGNaUnBCWnJ6ZjNJN05adnhMcHpmcDVhbjF2NWdTUkdZd0czamlLakJhRDBiTHJDOTh0T2V2U056Sll6THN1ZVNjSWU0dnE2dXFHNmxZc1c3cG9RZmVjY0VMVkFldi9odzZvYnhjaUF5ZDl0VkNkOGxCOHZXSVl2N2crREZUWVhiSyt5bzF0TlpHR1dIdU5MeHlwS0ludm1YcnR6WE43SHZxK0wzd3hyV2dacHhYbmp6dWR0N25zaTZMMlg0a0pYMFhNMVVVVTVLRGI2aW03YnUzVWpZbHJRaTRIV2NzZjA3VzhEVFdoYnJRUmJVYnZVdzBwaXBJWEtZS1dkT1FEb05zOG16SGtyY1ltSTYvYTE1bnBMZ3BEbmpIUFlCd0Z6NEhJdTQyb1F3SzdOS0luUXNuRGFLUUE1eG5NZVFOV2JMUmdrOWxvSWdmeXpLdVFPYzhNeXp1VnZwR2VJVlcveVcrb2h4dWlMM0MvZ2FUWTA0UFFwc3Q2TnZhTXJCd2FYTnEvZVA3Y0dkTmJXMmpaVUd5b2o0WnRFRjRwTmp6ek1xV3N5cGNhOW1mZXBwUWxXVld3U0RYNkdZV3dxMnB5RWF2QTFpZndYZnZYTmJaODQwRGJuaHF2MFZScVpYWFY2NnQyeHFwU1RwZkwyYmFoS1Q2bHVheHlRVW5qbnVtc2llcENSaWRpMGU3Q1NVekVPM2Z6L0xhdHExYlhPdWMxalZ4VzdNenoyNG84Wll5amFMWVlFSUpCb1VjSXVtcGRqb3JSRW91N1pPeVBWQzB5NmlGL2k5aUhTY3lHdk9JSDlKMXI2OWg3QWZjS0tKYU1wTjlXcFpVK0F1a0ViNVMrcFVwQTVZSlVGTkRLRzVOeE5PdkJObmFYOStTeHZsUExvblo3c05qcVduQjk3Q1paZmRNdDAwekM2L043VHI5Y0d5dU1laW9yUTRaQStHSG1YUzNXd09lNFdzQmdDd0ZTaGFpV2VpWmlyaXpBcFlnNTV5MXpqelkxenB6WjFEQ1RYK2dWanBMVXkxSFJvOWF2NXdDOWZoUktTbGwwWnBkeS9zZDFuRjlOVXNmNXRicHp1NUpIbUN3Tmh2NHZFZjV0Q2dBQUFIamFqWkxCVGhzeEVJWi9Md0hSQTZpdGVrSTlXS2dIT0xCT29FZ1JPWVZJdVJRSklnRnFqN0MxZGhjbDhXSjdEN3hFSDZJdjBodXEraDU5aHg3NzIzRkxxRXJWWGEzOWVUei96S3pIQUo3akhnS0w1eU8rSlJiWUVPOFNaK2lJSXZFS1hvdlBpVHQ0S2I0blhzVkc5aXJ4R2w1azQ4U2IyTW8rVVNVNno3ajZHaU1FRnRnU0tuR0dkZkVoOFFyNm9rcmN3UnZ4SmZFcS9YOGtYc04ydHAxNEUyK3o5eGpCb01FZExHcVVxT0Foc1k4dWVqZ2tuZE9pT1Fldk52cG9qaEpua1dkeEw3REJEYm1JNmlFOVBYV0dkc2YxVG96cW1jWGhDSXB2U1czd2FIR05uQ3JEU0FxM1hCdmFOZWY1MHVxS3lxQlZmMVR4VU1NdW8yQmttanRibDVXWCs5M2VvVHl2dEJ5WjF0YmF5ak5ienpSSGM2TUxMNGV0cjR4MWNxZnl2bkZIU3BXMXI5cnJ2REF6ZGRzYXI5dDVuSzZheHFrVUlrYllEVm1lUEFnOHlnWWMwM1BLYTRGak0rVjR3QnJEcWZZeHdBUVgvSWFrcC81bzcwRitrSGQ3L2NIa1lqSWNMQmV6dHdqN3I4YjhEdkg0SEJiQ3l5aHdkRFk4YmJsVUh5NjFkYldaeTVnWi8xUGpYd3I3MWZORnh4MjdISFFOYlk2WlF0NHA1M0JIU3U2Zllvd1RpdGdSTnNRVnRtNjh5MTA5elkwdDFlbjRCRDhCK3JHb2VRQUFlTnBsaXRkT3dtQUFSczlmUmhHY0RNVXRibEd4eFZsWFhDaTRCU2VvcFRGZ0x3ZzFCV084MVVmMVBZeW1pVEhSYzNPK25IeElPSHgrOFBZdHdWOU1wMHE0Y09QQmk0eVBCdndFYUtTSlpscG9wWTBnSWNKRWFLZURLSjEwMFUwUHZmVFJ6d0F4QmhsaW1CRkdHV09jQ2VKTU1zVTBDV1pRVUVreXl4enpMTERJRWhyTHJMREtHdXRzc01rVzIreVFZcGM5MG1UWTU0QkRqamptaEZQT3lKTGpuQXN1dWVLYUcvSVV1T1dPZTNTS0dMd0xTYmlFVzNpRVY4Z2hxMXJTYXhXalp1cGw2OWxPbEczaklmamI2aStXa3lKMTB5NzlPOHFQbGRjblU5TjhqbFZGK1JucUZ6TEhOVzRBQVFBQi8vOEFEM2phWTJCa1lHRGdBV0lsSUdaaVlBYkNSQVpHaGlTR0ZDQXZsU0VkeUdZQnl6QUFBQ2ZVQWpWNDJtTmdaR0JnNEdJSVlVaGlZSFp4OHdsaEVFa3ZTczFtVU1oSkxNbGowR0ZnQWNveS9QL1BBRktGekJaallIWjJERkZnRVBQMTl3R1NRZjYrUUJJdXk1aFdsSmpNd0FGaWdURUxXQzhqVUlRUmFDWVQwRDRGSU1uR3dNZVF6TURNSU1RZ0NySWRTSXVEMWFiQTJVd01JZ3hpQUxXMkV4bDQybU5nWkdCZzRHS3dZYkJqWUhaeDh3bGhFRWt2U3MxbWtNdEpMTWxqMEdCZ0Fjb3kvUDhQSkxDeGdBQUFXeG9MYXdBQUFBQUFBUUFBQUFEVnBDY0lBQUFBQU5tY2crRUFBQUFBMmZ0Sk5BPT0nKSBmb3JtYXQoJ3dvZmYnKTtcclxuICBmb250LXdlaWdodDogYm9sZDtcclxuICBmb250LXN0eWxlOiBub3JtYWw7XHJcbiAgZm9udC1kaXNwbGF5OiBzd2FwO1xyXG59XHJcbiJ9fQ==`,"base64").toString("utf8"));return t(`metrics/setup > setup > success`),a}async function a({login:e,imports:t,q:r},{enabled:n=!1,token:a=""}={}){try{if(!n||!r.music)return null;const o={get provider(){return x[s]?.name??""},get mode(){return v[l]??"Unconfigured music plugin"}};let i=null,{"music.provider":s="","music.mode":l="","music.playlist":d=null,"music.limit":p=4}=r;if(d&&!l&&(l="playlist"),d&&!s)for(const[e,{embed:t}]of Object.entries(x))t.test(d)&&(s=e);if(l||(l="recent"),!(s in x))throw{error:{message:s?`Unsupported provider "${s}"`:`Missing provider`},...o};if(!(l in v))throw{error:{message:`Unsupported mode "${l}"`},...o};if("playlist"===l){if(!d)throw{error:{message:`Missing playlist url`},...o};if(!x[s].embed.test(d))throw{error:{message:`Unsupported playlist url format`},...o}}switch(p=_Mathmax(1,_Mathmin(100,+p)),l){case"playlist":{console.debug(`metrics/compute/${e}/plugins > music > starting browser`);const r=await t.puppeteer.launch({headless:!0,executablePath:process.env.PUPPETEER_BROWSER_PATH,args:["--no-sandbox","--disable-extensions","--disable-setuid-sandbox","--disable-dev-shm-usage"]});console.debug(`metrics/compute/${e}/plugins > music > loaded ${await r.version()}`);const n=await r.newPage();console.debug(`metrics/compute/${e}/plugins > music > loading page`),await n.goto(d);const a=n.mainFrame();switch(s){case"apple":{await a.waitForSelector(".tracklist.playlist"),i=[...(await a.evaluate(()=>[...document.querySelectorAll(".tracklist li")].map(e=>({name:e.querySelector(".tracklist__track__name").innerText,artist:e.querySelector(".tracklist__track__sub").innerText,artwork:e.querySelector(".tracklist__track__artwork img").src}))))];break}case"spotify":{await a.waitForSelector("table"),i=[...(await a.evaluate(()=>[...document.querySelectorAll("table tr")].map(e=>({name:e.querySelector("td:nth-child(2) div:nth-child(1)").innerText,artist:e.querySelector("td:nth-child(2) div:nth-child(2)").innerText,artwork:window.getComputedStyle(document.querySelector("button[title=Play]").parentNode,null).backgroundImage.match(/^url\("(https:...+)"\)$/)[1]}))))];break}default:throw{error:{message:`Unsupported mode "${l}" for provider "${s}"`},...o};}console.debug(`metrics/compute/${e}/plugins > music > closing browser`),await r.close(),Array.isArray(i)&&(console.debug(`metrics/compute/${e}/plugins > music > found ${i.length} tracks`),console.debug(JSON.stringify(i)),i=t.shuffle(i));break}case"recent":{const r=Date.now()-86400000;switch(s){case"spotify":{const[n,s,l]=a.split(",").map(e=>e.trim());if(!n||!s||!l)throw{error:`Spotify token must contain client id/secret and refresh token`};try{console.debug(`metrics/compute/${e}/plugins > music > requesting access token with refresh token for spotify`);const{data:{access_token:a}}=await t.axios.post("https://accounts.spotify.com/api/token",`${new t.url.URLSearchParams({grant_type:"refresh_token",refresh_token:l,client_id:n,client_secret:s})}`,{headers:{"Content-Type":"application/x-www-form-urlencoded"}});console.log(a),console.debug(`metrics/compute/${e}/plugins > music > got new access token`),i=(await t.axios(`https://api.spotify.com/v1/me/player/recently-played?limit=${p}&after=${r}`,{headers:{Accept:"application/json","Content-Type":"application/json",Authorization:`Bearer ${a}`}})).data.items.map(({track:e})=>({name:e.name,artist:e.artists[0].name,artwork:e.album.images[0].url}))}catch(e){if(e.response?.status)throw{error:{message:`API returned ${e.response.status}`},...o};throw e}break}default:throw{error:{message:`Unsupported mode "${l}" for provider "${s}"`},...o};}break}default:throw{error:{message:`Unsupported mode "${l}"`},...o};}if(Array.isArray(i)){0 music > keeping only ${p} tracks`),i=i.slice(0,p)),console.debug(`metrics/compute/${e}/plugins > music > loading artworks`);for(const r of i)console.debug(`metrics/compute/${e}/plugins > music > processing ${r.name}`),r.artwork=await t.imgb64(r.artwork);return console.debug(`metrics/compute/${e}/plugins > music > success`),{...o,tracks:i}}throw{error:{message:`An error occured (could not retrieve tracks)`}}}catch(e){if(e.error?.message)throw e;throw console.debug(e),{error:{message:`An error occured`}}}}async function o({login:e,q:t},{conf:r,data:n,rest:a,graphql:o,plugins:i},{s:l,pending:s,imports:d}){const p=n.computed={commits:0,sponsorships:0,licenses:{favorite:"",used:{}},token:{},repositories:{watchers:0,stargazers:0,issues_open:0,issues_closed:0,pr_open:0,pr_merged:0,forks:0,releases:0},plugins:{}},c=d.imgb64(n.user.avatarUrl);for(const c of Object.keys(d.plugins))s.push((async()=>{try{p.plugins[c]=await d.plugins[c]({login:e,q:t,imports:d,data:n,computed:p,rest:a,graphql:o},i[c])}catch(e){p.plugins[c]=e}finally{return{name:c,result:p.plugins[c]}}})());for(const c of n.user.repositories.nodes){for(const e of["watchers","stargazers","issues_open","issues_closed","pr_open","pr_merged","releases"])p.repositories[e]+=c[e].totalCount;p.repositories.forks+=c.forkCount,c.licenseInfo&&(p.licenses.used[c.licenseInfo.spdxId]=(p.licenses.used[c.licenseInfo.spdxId]||0)+1)}p.diskUsage=`${d.bytes(1e3*n.user.repositories.totalDiskUsage)}`,p.licenses.favorite=Object.entries(p.licenses.used).sort(([e,t],[r,n])=>n-t).slice(0,1).map(([e,t])=>e)||"",p.commits+=n.user.contributionsCollection.totalCommitContributions+n.user.contributionsCollection.restrictedContributionsCount;const u=(Date.now()-new Date(n.user.createdAt).getTime())/31536000000,m=_Mathfloor(u),g=_Mathceil(12*(u-m));p.registration=m?`${m} year${l(m)} ago`:`${g} month${l(g)} ago`,p.calendar=n.user.calendar.contributionCalendar.weeks.flatMap(({contributionDays:e})=>e).slice(0,14).reverse(),p.avatar=(await c)||"iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mNk+M9QDwADhgGAWjR9awAAAABJRU5ErkJggg==",p.token.scopes=(await a.request("HEAD /")).headers["x-oauth-scopes"].split(", "),n.meta={version:r.package.version,author:r.package.author}}async function i({login:e,q:t},{graphql:r,rest:n,plugins:a,conf:o,die:i=!1}){try{console.debug(`metrics/compute/${e} > start`),console.debug(JSON.stringify(t));const u=t.template||o.settings.templates.default,m=_Mathmax(0,+t.repositories)||o.settings.repositories||100,g=[],h=(e,t="")=>1t[`base.${e}`]=!1);for(const e of o.settings.plugins.base.parts)E.base[e]=!(`base.${e}`in t)||!!t[`base.${e}`];if("placeholder"===e)c({data:E,conf:o,q:t});else{console.debug(`metrics/compute/${e} > graphql query`),Object.assign(E,await r(s.replace(/[$]login/,`"${e}"`).replace(/[$]repositories/,`${m}`).replace(/[$]calendar.to/,`"${new Date().toISOString()}"`).replace(/[$]calendar.from/,`"${new Date(Date.now()-1209600000).toISOString()}"`))),console.debug(`metrics/compute/${e} > compute`);const c=C[u].default||C[u];await c({login:e,q:t},{conf:o,data:E,rest:n,graphql:r,plugins:a},{s:h,pending:g,imports:{plugins:k,url:_,imgb64:b,axios:S,puppeteer:w,format:l,bytes:d,shuffle:p}});const f=await Promise.all(g);if(o.settings.debug)for(const{name:e,result:t=null}of f)console.debug(`plugin ${e} ${t?t.error?"failed":"success":"ignored"} : ${JSON.stringify(t).replace(/^(.{888}).+/,"$1...")}`);if(i){const e=f.filter(({result:e=null})=>!!e?.error).length;if(e)throw new Error(`${e} error${h(e)} found...`)}}console.debug(`metrics/compute/${e} > render`);let A=await f.render(x,{...E,s:h,style:v,fonts:T},{async:!0});if(o.optimize&&!t.raw){console.debug(`metrics/compute/${e} > optimize`);const t=new y({full:!0,plugins:[{cleanupAttrs:!0},{inlineStyles:!1}]}),{data:r}=await t.optimize(A);A=r}return console.debug(`metrics/compute/${e} > success`),A}catch(e){if(Array.isArray(e.errors)&&"NOT_FOUND"===e.errors[0].type)throw new Error("user not found");throw e}}function l(e){for(const{u:t,v:r}of[{u:"b",v:1000000000},{u:"m",v:1000000},{u:"k",v:1000}])if(1<=e/r)return`${(e/r).toFixed(2).substr(0,4).replace(/[.]0*$/,"")}${t}`;return e}function d(e){for(const{u:t,v:r}of[{u:"E",v:1000000000000000000},{u:"P",v:1000000000000000},{u:"T",v:1000000000000},{u:"G",v:1000000000},{u:"M",v:1000000},{u:"k",v:1000}])if(1<=e/r)return`${(e/r).toFixed(2).substr(0,4).replace(/[.]0*$/,"")} ${t}B`;return`${e} byte${1"object"==typeof e?new Proxy(e,{get(e,t){return t===Symbol.toPrimitive?()=>"##":t===Symbol.iterator?Reflect.get(e,t):/^plugins$/.test(t)?Reflect.get(e,t):/^error/.test(t)?void 0:n(t in e?Reflect.get(e,t):{})}}):e,a=Object.entries(t.settings.plugins).filter(([e,t])=>t.enabled).map(([e])=>e).filter(e=>e in r&&r[e]);Object.assign(e,{s(e,t){return"y"===t?"ies":"s"},meta:{version:t.package.version,author:t.package.author,placeholder:!0},user:n({name:`############`,websiteUrl:`########################`}),computed:n({avatar:"iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mOcOnfpfwAGfgLYttYINwAAAABJRU5ErkJggg==",registration:"## years ago",calendar:Array(14).fill({color:"#ebedf0"}),licenses:{favorite:`########`},plugins:Object.fromEntries(a.map(e=>[e,n({posts:{source:"########",posts:Array("posts.limit"in r?_Mathmax(+r["posts.limit"]||0,0):2).fill({title:"###### ###### ####### ######",date:"####"})},music:{provider:"########",tracks:Array("music.limit"in r?_Mathmax(+r["music.limit"]||0,0):4).fill({name:"##########",artist:"######",artwork:"iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mOcOnfpfwAGfgLYttYINwAAAABJRU5ErkJggg=="})},pagespeed:{scores:["Performance","Accessibility","Best Practices","SEO"].map(e=>({title:e,score:NaN}))},followup:{issues:{count:0},pr:{count:0}},habits:{indents:{style:`########`}},languages:{favorites:Array(7).fill(null).map((e,t)=>({x:t,name:`######`,color:"#ebedf0",value:1/(t+1)}))}}[e]??{})])),token:{scopes:[]}})})}r.r(t);var u={};r.r(u),r.d(u,{default:()=>n});var m={};r.r(m),r.d(m,{default:()=>i});var g=r(35747),h=r(85622),f=r(58509),y=r(20485),b=r(67192),S=r(2390);const x={apple:{name:"Apple Music",embed:/^https:..embed.music.apple.com.\w+.playlist/},spotify:{name:"Spotify",embed:/^https:..open.spotify.com.embed.playlist/}},v={playlist:"Suggested tracks",recent:"Recently played"},k={followup:async function({computed:e,q:t},{enabled:r=!1}={}){try{if(!r||!t.followup)return null;const n={issues:{get count(){return this.open+this.closed},get open(){return e.repositories.issues_open},get closed(){return e.repositories.issues_closed}},pr:{get count(){return this.open+this.merged},get open(){return e.repositories.pr_open},get merged(){return e.repositories.pr_merged}}};return n}catch(e){throw console.debug(e),{error:{message:`An error occured`}}}},gists:async function({login:e,graphql:t,q:r},{enabled:n=!1}={}){try{if(!n||!r.gists)return null;const{user:{gists:a}}=await t(` + query Gists { + user(login: "${e}") { + gists(last: 100) { + totalCount + nodes { + stargazerCount + isFork + forks { + totalCount + } + comments { + totalCount + } + } + } } - }) - } - } - } - else { - logger(`metrics/setup > load templates from build`) - conf.templates = JSON.parse(Buffer.from(`eyJjbGFzc2ljIjp7InF1ZXJ5IjoicXVlcnkgTWV0cmljcyB7XHJcbiAgdXNlcihsb2dpbjogJGxvZ2luKSB7XHJcbiAgICBkYXRhYmFzZUlkXHJcbiAgICBuYW1lXHJcbiAgICBsb2dpblxyXG4gICAgY3JlYXRlZEF0XHJcbiAgICBhdmF0YXJVcmxcclxuICAgIHdlYnNpdGVVcmxcclxuICAgIGdpc3RzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgcmVwb3NpdG9yaWVzKGxhc3Q6ICRyZXBvc2l0b3JpZXMsIGlzRm9yazogZmFsc2UsIG93bmVyQWZmaWxpYXRpb25zOiBPV05FUikge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICAgIHRvdGFsRGlza1VzYWdlXHJcbiAgICAgIG5vZGVzIHtcclxuICAgICAgICBuYW1lXHJcbiAgICAgICAgd2F0Y2hlcnMge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBzdGFyZ2F6ZXJzIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgbGFuZ3VhZ2VzKGZpcnN0OiA0KSB7XHJcbiAgICAgICAgICBlZGdlcyB7XHJcbiAgICAgICAgICAgIHNpemVcclxuICAgICAgICAgICAgbm9kZSB7XHJcbiAgICAgICAgICAgICAgY29sb3JcclxuICAgICAgICAgICAgICBuYW1lXHJcbiAgICAgICAgICAgIH1cclxuICAgICAgICAgIH1cclxuICAgICAgICB9XHJcbiAgICAgICAgaXNzdWVzX29wZW46IGlzc3VlcyhzdGF0ZXM6IE9QRU4pIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgaXNzdWVzX2Nsb3NlZDogaXNzdWVzKHN0YXRlczogQ0xPU0VEKSB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHByX29wZW46IHB1bGxSZXF1ZXN0cyhzdGF0ZXM6IE9QRU4pIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgcHJfbWVyZ2VkOiBwdWxsUmVxdWVzdHMoc3RhdGVzOiBNRVJHRUQpIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgZm9ya0NvdW50XHJcbiAgICAgICAgbGljZW5zZUluZm8ge1xyXG4gICAgICAgICAgc3BkeElkXHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICBwYWNrYWdlcyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHN0YXJyZWRSZXBvc2l0b3JpZXMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICB3YXRjaGluZyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHNwb25zb3JzaGlwc0FzU3BvbnNvciB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHNwb25zb3JzaGlwc0FzTWFpbnRhaW5lciB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIGNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uIHtcclxuICAgICAgdG90YWxSZXBvc2l0b3JpZXNXaXRoQ29udHJpYnV0ZWRDb21taXRzXHJcbiAgICAgIHRvdGFsQ29tbWl0Q29udHJpYnV0aW9uc1xyXG4gICAgICByZXN0cmljdGVkQ29udHJpYnV0aW9uc0NvdW50XHJcbiAgICAgIHRvdGFsSXNzdWVDb250cmlidXRpb25zXHJcbiAgICAgIHRvdGFsUHVsbFJlcXVlc3RDb250cmlidXRpb25zXHJcbiAgICAgIHRvdGFsUHVsbFJlcXVlc3RSZXZpZXdDb250cmlidXRpb25zXHJcbiAgICB9XHJcbiAgICBjYWxlbmRhcjpjb250cmlidXRpb25zQ29sbGVjdGlvbihmcm9tOiAkY2FsZW5kYXIuZnJvbSwgdG86ICRjYWxlbmRhci50bykge1xyXG4gICAgICBjb250cmlidXRpb25DYWxlbmRhciB7XHJcbiAgICAgICAgd2Vla3Mge1xyXG4gICAgICAgICAgY29udHJpYnV0aW9uRGF5cyB7XHJcbiAgICAgICAgICAgIGNvbG9yXHJcbiAgICAgICAgICB9XHJcbiAgICAgICAgfVxyXG4gICAgICB9XHJcbiAgICB9XHJcbiAgICByZXBvc2l0b3JpZXNDb250cmlidXRlZFRvIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgZm9sbG93ZXJzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgZm9sbG93aW5nIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgaXNzdWVDb21tZW50cyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIG9yZ2FuaXphdGlvbnMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgfVxyXG59XHJcbiIsImltYWdlIjoiPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgd2lkdGg9XCI0ODBcIiBoZWlnaHQ9XCI8JT0gMTJcclxuICArICghIWJhc2UuaGVhZGVyKSo4MFxyXG4gICsgKCEhYmFzZS5tZXRhZGF0YSkqMzhcclxuICArICgoISFiYXNlLmFjdGl2aXR5KXx8KCEhYmFzZS5jb21tdW5pdHkpKSoxMjhcclxuICArICghIWJhc2UucmVwb3NpdG9yaWVzKSo5MlxyXG4gICsgKCghIWJhc2UucmVwb3NpdG9yaWVzKSooKCEhY29tcHV0ZWQucGx1Z2lucy50cmFmZmljKXx8KCEhY29tcHV0ZWQucGx1Z2lucy5saW5lcykpKSoxNlxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cCkqNjhcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkKSoxMjZcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzKSo2OFxyXG4gICsgKCEhY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMpKjk2XHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLm11c2ljKSo2NCArIChjb21wdXRlZC5wbHVnaW5zLm11c2ljID8gY29tcHV0ZWQucGx1Z2lucy5tdXNpYy50cmFja3MgPyAxNCtNYXRoLm1heCgwLCBjb21wdXRlZC5wbHVnaW5zLm11c2ljLnRyYWNrcy5sZW5ndGgtMSkqMzYgOiAwIDogMClcclxuICArICghIWNvbXB1dGVkLnBsdWdpbnMucG9zdHMpKjY0ICsgKGNvbXB1dGVkLnBsdWdpbnMucG9zdHMgPyBjb21wdXRlZC5wbHVnaW5zLnBvc3RzLnBvc3RzID8gTWF0aC5tYXgoMCwgY29tcHV0ZWQucGx1Z2lucy5wb3N0cy5wb3N0cy5sZW5ndGgpKjQwIDogMCA6IDApXHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyKSoxODBcclxuICArIE1hdGgubWF4KDAsICgoKCEhYmFzZS5tZXRhZGF0YSkrKCEhYmFzZS5oZWFkZXIpKygoISFiYXNlLmFjdGl2aXR5KXx8KCEhYmFzZS5jb21tdW5pdHkpKSsoISFiYXNlLnJlcG9zaXRvcmllcykrKCghIWNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzKSkrKCEhY29tcHV0ZWQucGx1Z2lucy5wYWdlc3BlZWQpKyghIWNvbXB1dGVkLnBsdWdpbnMubGFuZ3VhZ2VzKSsoISFjb21wdXRlZC5wbHVnaW5zLm11c2ljKSsoISFjb21wdXRlZC5wbHVnaW5zLnBvc3RzKSsoISFjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyKSktMSkpKjRcclxuJT5cIj5cclxuXHJcbiAgPGRlZnM+PHN0eWxlPjwlPSBmb250cyAlPjwvc3R5bGU+PC9kZWZzPlxyXG5cclxuICA8c3R5bGU+XHJcbiAgICA8JT0gc3R5bGUgJT5cclxuICA8L3N0eWxlPlxyXG5cclxuICA8Zm9yZWlnbk9iamVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCIxMDAlXCIgaGVpZ2h0PVwiMTAwJVwiPlxyXG4gICAgPGRpdiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGh0bWxcIiB4bWxuczp4bGluaz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmtcIj5cclxuXHJcbiAgICAgIDwlIGlmIChiYXNlLmhlYWRlcikgeyAlPlxyXG4gICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgPGgxIGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgPGltZyBjbGFzcz1cImF2YXRhclwiIHNyYz1cImRhdGE6aW1hZ2UvcG5nO2Jhc2U2NCw8JT0gY29tcHV0ZWQuYXZhdGFyICU+XCIgd2lkdGg9XCIyMFwiIGhlaWdodD1cIjIwXCIgLz5cclxuICAgICAgICAgICAgPHNwYW4+PCU9IHVzZXIubmFtZSB8fCB1c2VyLmxvZ2luICU+PC9zcGFuPlxyXG4gICAgICAgICAgPC9oMT5cclxuICAgICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMS41IDhhNi41IDYuNSAwIDExMTMgMCA2LjUgNi41IDAgMDEtMTMgMHpNOCAwYTggOCAwIDEwMCAxNkE4IDggMCAwMDggMHptLjUgNC43NWEuNzUuNzUgMCAwMC0xLjUgMHYzLjVhLjc1Ljc1IDAgMDAuNDcxLjY5NmwyLjUgMWEuNzUuNzUgMCAwMC41NTctMS4zOTJMOC41IDcuNzQyVjQuNzV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgSm9pbmVkIEdpdEh1YiA8JT0gY29tcHV0ZWQucmVnaXN0cmF0aW9uICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNS41IDMuNWEyIDIgMCAxMDAgNCAyIDIgMCAwMDAtNHpNMiA1LjVhMy41IDMuNSAwIDExNS44OTggMi41NDkgNS41MDcgNS41MDcgMCAwMTMuMDM0IDQuMDg0Ljc1Ljc1IDAgMTEtMS40ODIuMjM1IDQuMDAxIDQuMDAxIDAgMDAtNy45IDAgLjc1Ljc1IDAgMDEtMS40ODItLjIzNkE1LjUwNyA1LjUwNyAwIDAxMy4xMDIgOC4wNSAzLjQ5IDMuNDkgMCAwMTIgNS41ek0xMSA0YS43NS43NSAwIDEwMCAxLjUgMS41IDEuNSAwIDAxLjY2NiAyLjg0NC43NS43NSAwIDAwLS40MTYuNjcydi4zNTJhLjc1Ljc1IDAgMDAuNTc0LjczYzEuMi4yODkgMi4xNjIgMS4yIDIuNTIyIDIuMzcyYS43NS43NSAwIDEwMS40MzQtLjQ0IDUuMDEgNS4wMSAwIDAwLTIuNTYtMy4wMTJBMyAzIDAgMDAxMSA0elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIEZvbGxvd2VkIGJ5IDwlPSB1c2VyLmZvbGxvd2Vycy50b3RhbENvdW50ICU+IHVzZXI8JT0gcyh1c2VyLmZvbGxvd2Vycy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjYWxlbmRhclwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCA8JT0gY29tcHV0ZWQuY2FsZW5kYXIubGVuZ3RoKjE1ICU+IDExXCIgd2lkdGg9XCI8JT0gY29tcHV0ZWQuY2FsZW5kYXIubGVuZ3RoKjE1ICU+XCIgaGVpZ2h0PVwiMTZcIj5cclxuICAgICAgICAgICAgICAgICAgPGc+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCBbeCwge2NvbG9yfV0gb2YgT2JqZWN0LmVudHJpZXMoY29tcHV0ZWQuY2FsZW5kYXIpKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8cmVjdCBjbGFzcz1cImRheVwiIHg9XCI8JT0geCoxNSAlPlwiIHk9XCIwXCIgd2lkdGg9XCIxMVwiIGhlaWdodD1cIjExXCIgZmlsbD1cIjwlPSBjb2xvciAlPlwiIHJ4PVwiMlwiIHJ5PVwiMlwiIC8+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICAgICAgICA8L2c+XHJcbiAgICAgICAgICAgICAgICA8L3N2Zz5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xIDIuNUEyLjUgMi41IDAgMDEzLjUgMGg4Ljc1YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMFYxLjVoLThhMSAxIDAgMDAtMSAxdjYuNzA4QTIuNDkyIDIuNDkyIDAgMDEzLjUgOWgzLjI1YS43NS43NSAwIDAxMCAxLjVIMy41YTEgMSAwIDEwMCAyaDUuNzVhLjc1Ljc1IDAgMDEwIDEuNUgzLjVBMi41IDIuNSAwIDAxMSAxMS41di05em0xMy4yMyA3Ljc5YS43NS43NSAwIDAwMS4wNi0xLjA2bC0yLjUwNS0yLjUwNWEuNzUuNzUgMCAwMC0xLjA2IDBMOS4yMiA5LjIyOWEuNzUuNzUgMCAwMDEuMDYgMS4wNjFsMS4yMjUtMS4yMjR2Ni4xODRhLjc1Ljc1IDAgMDAxLjUgMFY5LjA2NmwxLjIyNCAxLjIyNHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICBDb250cmlidXRlZCB0byA8JT0gdXNlci5yZXBvc2l0b3JpZXNDb250cmlidXRlZFRvLnRvdGFsQ291bnQgJT4gcmVwb3NpdG9yPCU9IHModXNlci5yZXBvc2l0b3JpZXNDb250cmlidXRlZFRvLnRvdGFsQ291bnQsIFwieVwiKSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICA8JSBpZiAoYmFzZS5hY3Rpdml0eSkgeyAlPlxyXG4gICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgIDxoMiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNSAxLjc1YS43NS43NSAwIDAwLTEuNSAwdjEyLjVjMCAuNDE0LjMzNi43NS43NS43NWgxNC41YS43NS43NSAwIDAwMC0xLjVIMS41VjEuNzV6bTE0LjI4IDIuNTNhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2TDEwIDcuOTQgNy41MyA1LjQ3YS43NS43NSAwIDAwLTEuMDYgMEwzLjIyIDguNzJhLjc1Ljc1IDAgMDAxLjA2IDEuMDZMNyA3LjA2bDIuNDcgMi40N2EuNzUuNzUgMCAwMDEuMDYgMGw1LjI1LTUuMjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIEFjdGl2aXR5XHJcbiAgICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xMC41IDcuNzVhMi41IDIuNSAwIDExLTUgMCAyLjUgMi41IDAgMDE1IDB6bTEuNDMuNzVhNC4wMDIgNC4wMDIgMCAwMS03Ljg2IDBILjc1YS43NS43NSAwIDExMC0xLjVoMy4zMmE0LjAwMSA0LjAwMSAwIDAxNy44NiAwaDMuMzJhLjc1Ljc1IDAgMTEwIDEuNWgtMy4zMnpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLmNvbW1pdHMgJT4gQ29tbWl0PCU9IHMoY29tcHV0ZWQuY29tbWl0cykgJT5cclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjUgMS43NWEuMjUuMjUgMCAwMS4yNS0uMjVoOC41YS4yNS4yNSAwIDAxLjI1LjI1djcuNzM2YS43NS43NSAwIDEwMS41IDBWMS43NUExLjc1IDEuNzUgMCAwMDExLjI1IDBoLTguNUExLjc1IDEuNzUgMCAwMDEgMS43NXYxMS41YzAgLjk2Ni43ODQgMS43NSAxLjc1IDEuNzVoMy4xN2EuNzUuNzUgMCAwMDAtMS41SDIuNzVhLjI1LjI1IDAgMDEtLjI1LS4yNVYxLjc1ek00Ljc1IDRhLjc1Ljc1IDAgMDAwIDEuNWg0LjVhLjc1Ljc1IDAgMDAwLTEuNWgtNC41ek00IDcuNzVBLjc1Ljc1IDAgMDE0Ljc1IDdoMmEuNzUuNzUgMCAwMTAgMS41aC0yQS43NS43NSAwIDAxNCA3Ljc1em0xMS43NzQgMy41MzdhLjc1Ljc1IDAgMDAtMS4wNDgtMS4wNzRMMTAuNyAxNC4xNDUgOS4yODEgMTIuNzJhLjc1Ljc1IDAgMDAtMS4wNjIgMS4wNThsMS45NDMgMS45NWEuNzUuNzUgMCAwMDEuMDU1LjAwOGw0LjU1Ny00LjQ1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0UmV2aWV3Q29udHJpYnV0aW9ucyAlPiBQdWxsIHJlcXVlc3Q8JT0gcyh1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsUHVsbFJlcXVlc3RSZXZpZXdDb250cmlidXRpb25zKSAlPiByZXZpZXdlZFxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTcuMTc3IDMuMDczTDkuNTczLjY3N0EuMjUuMjUgMCAwMTEwIC44NTR2NC43OTJhLjI1LjI1IDAgMDEtLjQyNy4xNzdMNy4xNzcgMy40MjdhLjI1LjI1IDAgMDEwLS4zNTR6TTMuNzUgMi41YS43NS43NSAwIDEwMCAxLjUuNzUuNzUgMCAwMDAtMS41em0tMi4yNS43NWEyLjI1IDIuMjUgMCAxMTMgMi4xMjJ2NS4yNTZhMi4yNTEgMi4yNTEgMCAxMS0xLjUgMFY1LjM3MkEyLjI1IDIuMjUgMCAwMTEuNSAzLjI1ek0xMSAyLjVoLTFWNGgxYTEgMSAwIDAxMSAxdjUuNjI4YTIuMjUxIDIuMjUxIDAgMTAxLjUgMFY1QTIuNSAyLjUgMCAwMDExIDIuNXptMSAxMC4yNWEuNzUuNzUgMCAxMTEuNSAwIC43NS43NSAwIDAxLTEuNSAwek0zLjc1IDEyYS43NS43NSAwIDEwMCAxLjUuNzUuNzUgMCAwMDAtMS41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0Q29udHJpYnV0aW9ucyAlPiBQdWxsIHJlcXVlc3Q8JT0gcyh1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsUHVsbFJlcXVlc3RDb250cmlidXRpb25zKSAlPiBvcGVuZWRcclxuICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04IDEuNWE2LjUgNi41IDAgMTAwIDEzIDYuNSA2LjUgMCAwMDAtMTN6TTAgOGE4IDggMCAxMTE2IDBBOCA4IDAgMDEwIDh6bTkgM2ExIDEgMCAxMS0yIDAgMSAxIDAgMDEyIDB6bS0uMjUtNi4yNWEuNzUuNzUgMCAwMC0xLjUgMHYzLjVhLjc1Ljc1IDAgMDAxLjUgMHYtMy41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbElzc3VlQ29udHJpYnV0aW9ucyAlPiBJc3N1ZTwlPSBzKHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxJc3N1ZUNvbnRyaWJ1dGlvbnMpICU+IG9wZW5lZFxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuNzUgMi41YS4yNS4yNSAwIDAwLS4yNS4yNXY3LjVjMCAuMTM4LjExMi4yNS4yNS4yNWgyYS43NS43NSAwIDAxLjc1Ljc1djIuMTlsMi43Mi0yLjcyYS43NS43NSAwIDAxLjUzLS4yMmg0LjVhLjI1LjI1IDAgMDAuMjUtLjI1di03LjVhLjI1LjI1IDAgMDAtLjI1LS4yNUgyLjc1ek0xIDIuNzVDMSAxLjc4NCAxLjc4NCAxIDIuNzUgMWgxMC41Yy45NjYgMCAxLjc1Ljc4NCAxLjc1IDEuNzV2Ny41QTEuNzUgMS43NSAwIDAxMTMuMjUgMTJIOS4wNmwtMi41NzMgMi41NzNBMS40NTcgMS40NTcgMCAwMTQgMTMuNTQzVjEySDIuNzVBMS43NSAxLjc1IDAgMDExIDEwLjI1di03LjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIDwlPSB1c2VyLmlzc3VlQ29tbWVudHMudG90YWxDb3VudCAlPiBpc3N1ZSBjb21tZW50PCU9IHModXNlci5pc3N1ZUNvbW1lbnRzLnRvdGFsQ291bnQpICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgIDwlIH0gJT5cclxuICAgICAgICA8JSBpZiAoYmFzZS5jb21tdW5pdHkpIHsgJT5cclxuICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjc1IDBBMS43NSAxLjc1IDAgMDAwIDEuNzV2MTIuNUMwIDE1LjIxNi43ODQgMTYgMS43NSAxNmgxMi41QTEuNzUgMS43NSAwIDAwMTYgMTQuMjVWMS43NUExLjc1IDEuNzUgMCAwMDE0LjI1IDBIMS43NXpNMS41IDEuNzVhLjI1LjI1IDAgMDEuMjUtLjI1aDEyLjVhLjI1LjI1IDAgMDEuMjUuMjV2MTIuNWEuMjUuMjUgMCAwMS0uMjUuMjVIMS43NWEuMjUuMjUgMCAwMS0uMjUtLjI1VjEuNzV6TTExLjc1IDNhLjc1Ljc1IDAgMDAtLjc1Ljc1djcuNWEuNzUuNzUgMCAwMDEuNSAwdi03LjVhLjc1Ljc1IDAgMDAtLjc1LS43NXptLTguMjUuNzVhLjc1Ljc1IDAgMDExLjUgMHY1LjVhLjc1Ljc1IDAgMDEtMS41IDB2LTUuNXpNOCAzYS43NS43NSAwIDAwLS43NS43NXYzLjVhLjc1Ljc1IDAgMDAxLjUgMHYtMy41QS43NS43NSAwIDAwOCAzelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICBDb21tdW5pdHkgc3RhdHNcclxuICAgICAgICAgICAgPC9oMj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTUuNSAzLjVhMiAyIDAgMTAwIDQgMiAyIDAgMDAwLTR6TTIgNS41YTMuNSAzLjUgMCAxMTUuODk4IDIuNTQ5IDUuNTA3IDUuNTA3IDAgMDEzLjAzNCA0LjA4NC43NS43NSAwIDExLTEuNDgyLjIzNSA0LjAwMSA0LjAwMSAwIDAwLTcuOSAwIC43NS43NSAwIDAxLTEuNDgyLS4yMzZBNS41MDcgNS41MDcgMCAwMTMuMTAyIDguMDUgMy40OSAzLjQ5IDAgMDEyIDUuNXpNMTEgNGEuNzUuNzUgMCAxMDAgMS41IDEuNSAxLjUgMCAwMS42NjYgMi44NDQuNzUuNzUgMCAwMC0uNDE2LjY3MnYuMzUyYS43NS43NSAwIDAwLjU3NC43M2MxLjIuMjg5IDIuMTYyIDEuMiAyLjUyMiAyLjM3MmEuNzUuNzUgMCAxMDEuNDM0LS40NCA1LjAxIDUuMDEgMCAwMC0yLjU2LTMuMDEyQTMgMyAwIDAwMTEgNHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgRm9sbG93aW5nIDwlPSB1c2VyLmZvbGxvd2luZy50b3RhbENvdW50ICU+IHVzZXI8JT0gcyh1c2VyLmZvbGxvd2Vycy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTQuMjUgMi41Yy0xLjMzNiAwLTIuNzUgMS4xNjQtMi43NSAzIDAgMi4xNSAxLjU4IDQuMTQ0IDMuMzY1IDUuNjgyQTIwLjU2NSAyMC41NjUgMCAwMDggMTMuMzkzYTIwLjU2MSAyMC41NjEgMCAwMDMuMTM1LTIuMjExQzEyLjkyIDkuNjQ0IDE0LjUgNy42NSAxNC41IDUuNWMwLTEuODM2LTEuNDE0LTMtMi43NS0zLTEuMzczIDAtMi42MDkuOTg2LTMuMDI5IDIuNDU2YS43NS43NSAwIDAxLTEuNDQyIDBDNi44NTkgMy40ODYgNS42MjMgMi41IDQuMjUgMi41ek04IDE0LjI1bC0uMzQ1LjY2Ni0uMDAyLS4wMDEtLjAwNi0uMDAzLS4wMTgtLjAxYTcuNjQzIDcuNjQzIDAgMDEtLjMxLS4xNyAyMi4wNzUgMjIuMDc1IDAgMDEtMy40MzQtMi40MTRDMi4wNDUgMTAuNzMxIDAgOC4zNSAwIDUuNSAwIDIuODM2IDIuMDg2IDEgNC4yNSAxIDUuNzk3IDEgNy4xNTMgMS44MDIgOCAzLjAyIDguODQ3IDEuODAyIDEwLjIwMyAxIDExLjc1IDEgMTMuOTE0IDEgMTYgMi44MzYgMTYgNS41YzAgMi44NS0yLjA0NSA1LjIzMS0zLjg4NSA2LjgxOGEyMi4wOCAyMi4wOCAwIDAxLTMuNzQ0IDIuNTg0bC0uMDE4LjAxLS4wMDYuMDAzaC0uMDAyTDggMTQuMjV6bTAgMGwuMzQ1LjY2NmEuNzUyLjc1MiAwIDAxLS42OSAwTDggMTQuMjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgIFNwb25zb3JpbmcgPCU9IGNvbXB1dGVkLnNwb25zb3JzaGlwcyAlPiByZXBvc2l0b3I8JT0gcyhjb21wdXRlZC5zcG9uc29yc2hpcHMsIFwieVwiKSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTggLjI1YS43NS43NSAwIDAxLjY3My40MThsMS44ODIgMy44MTUgNC4yMS42MTJhLjc1Ljc1IDAgMDEuNDE2IDEuMjc5bC0zLjA0NiAyLjk3LjcxOSA0LjE5MmEuNzUuNzUgMCAwMS0xLjA4OC43OTFMOCAxMi4zNDdsLTMuNzY2IDEuOThhLjc1Ljc1IDAgMDEtMS4wODgtLjc5bC43Mi00LjE5NEwuODE4IDYuMzc0YS43NS43NSAwIDAxLjQxNi0xLjI4bDQuMjEtLjYxMUw3LjMyNy42NjhBLjc1Ljc1IDAgMDE4IC4yNXptMCAyLjQ0NUw2LjYxNSA1LjVhLjc1Ljc1IDAgMDEtLjU2NC40MWwtMy4wOTcuNDUgMi4yNCAyLjE4NGEuNzUuNzUgMCAwMS4yMTYuNjY0bC0uNTI4IDMuMDg0IDIuNzY5LTEuNDU2YS43NS43NSAwIDAxLjY5OCAwbDIuNzcgMS40NTYtLjUzLTMuMDg0YS43NS43NSAwIDAxLjIxNi0uNjY0bDIuMjQtMi4xODMtMy4wOTYtLjQ1YS43NS43NSAwIDAxLS41NjQtLjQxTDggMi42OTR2LjAwMXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgU3RhcnJlZCA8JT0gdXNlci5zdGFycmVkUmVwb3NpdG9yaWVzLnRvdGFsQ291bnQgJT4gcmVwb3NpdG9yPCU9IHModXNlci5zdGFycmVkUmVwb3NpdG9yaWVzLnRvdGFsQ291bnQsIFwieVwiKSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNjc5IDcuOTMyYy40MTItLjYyMSAxLjI0Mi0xLjc1IDIuMzY2LTIuNzE3QzUuMTc1IDQuMjQyIDYuNTI3IDMuNSA4IDMuNWMxLjQ3MyAwIDIuODI0Ljc0MiAzLjk1NSAxLjcxNSAxLjEyNC45NjcgMS45NTQgMi4wOTYgMi4zNjYgMi43MTdhLjExOS4xMTkgMCAwMTAgLjEzNmMtLjQxMi42MjEtMS4yNDIgMS43NS0yLjM2NiAyLjcxN0MxMC44MjUgMTEuNzU4IDkuNDczIDEyLjUgOCAxMi41Yy0xLjQ3MyAwLTIuODI0LS43NDItMy45NTUtMS43MTVDMi45MiA5LjgxOCAyLjA5IDguNjkgMS42NzkgOC4wNjhhLjExOS4xMTkgMCAwMTAtLjEzNnpNOCAyYy0xLjk4MSAwLTMuNjcuOTkyLTQuOTMzIDIuMDc4QzEuNzk3IDUuMTY5Ljg4IDYuNDIzLjQzIDcuMWExLjYxOSAxLjYxOSAwIDAwMCAxLjc5OGMuNDUuNjc4IDEuMzY3IDEuOTMyIDIuNjM3IDMuMDI0QzQuMzI5IDEzLjAwOCA2LjAxOSAxNCA4IDE0YzEuOTgxIDAgMy42Ny0uOTkyIDQuOTMzLTIuMDc4IDEuMjctMS4wOTEgMi4xODctMi4zNDUgMi42MzctMy4wMjNhMS42MTkgMS42MTkgMCAwMDAtMS43OThjLS40NS0uNjc4LTEuMzY3LTEuOTMyLTIuNjM3LTMuMDIzQzExLjY3MSAyLjk5MiA5Ljk4MSAyIDggMnptMCA4YTIgMiAwIDEwMC00IDIgMiAwIDAwMCA0elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICBXYXRjaGluZyA8JT0gdXNlci53YXRjaGluZy50b3RhbENvdW50ICU+IHJlcG9zaXRvcjwlPSBzKHVzZXIud2F0Y2hpbmcudG90YWxDb3VudCwgXCJ5XCIpICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMS41IDE0LjI1YzAgLjEzOC4xMTIuMjUuMjUuMjVINHYtMS4yNWEuNzUuNzUgMCAwMS43NS0uNzVoMi41YS43NS43NSAwIDAxLjc1Ljc1djEuMjVoMi4yNWEuMjUuMjUgMCAwMC4yNS0uMjVWMS43NWEuMjUuMjUgMCAwMC0uMjUtLjI1aC04LjVhLjI1LjI1IDAgMDAtLjI1LjI1djEyLjV6TTEuNzUgMTZBMS43NSAxLjc1IDAgMDEwIDE0LjI1VjEuNzVDMCAuNzg0Ljc4NCAwIDEuNzUgMGg4LjVDMTEuMjE2IDAgMTIgLjc4NCAxMiAxLjc1djEyLjVjMCAuMDg1LS4wMDYuMTY4LS4wMTguMjVoMi4yNjhhLjI1LjI1IDAgMDAuMjUtLjI1VjguMjg1YS4yNS4yNSAwIDAwLS4xMTEtLjIwOGwtMS4wNTUtLjcwM2EuNzUuNzUgMCAxMS44MzItMS4yNDhsMS4wNTUuNzAzYy40ODcuMzI1Ljc3OS44NzEuNzc5IDEuNDU2djUuOTY1QTEuNzUgMS43NSAwIDAxMTQuMjUgMTZoLTMuNWEuNzUuNzUgMCAwMS0uMTk3LS4wMjZjLS4wOTkuMDE3LS4yLjAyNi0uMzAzLjAyNmgtM2EuNzUuNzUgMCAwMS0uNzUtLjc1VjE0aC0xdjEuMjVhLjc1Ljc1IDAgMDEtLjc1Ljc1aC0zek0zIDMuNzVBLjc1Ljc1IDAgMDEzLjc1IDNoLjVhLjc1Ljc1IDAgMDEwIDEuNWgtLjVBLjc1Ljc1IDAgMDEzIDMuNzV6TTMuNzUgNmEuNzUuNzUgMCAwMDAgMS41aC41YS43NS43NSAwIDAwMC0xLjVoLS41ek0zIDkuNzVBLjc1Ljc1IDAgMDEzLjc1IDloLjVhLjc1Ljc1IDAgMDEwIDEuNWgtLjVBLjc1Ljc1IDAgMDEzIDkuNzV6TTcuNzUgOWEuNzUuNzUgMCAwMDAgMS41aC41YS43NS43NSAwIDAwMC0xLjVoLS41ek03IDYuNzVBLjc1Ljc1IDAgMDE3Ljc1IDZoLjVhLjc1Ljc1IDAgMDEwIDEuNWgtLjVBLjc1Ljc1IDAgMDE3IDYuNzV6TTcuNzUgM2EuNzUuNzUgMCAwMDAgMS41aC41YS43NS43NSAwIDAwMC0xLjVoLS41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICBNZW1iZXIgb2YgPCU9IHVzZXIub3JnYW5pemF0aW9ucy50b3RhbENvdW50ICU+IG9yZ2FuaXphdGlvbjwlPSBzKHVzZXIub3JnYW5pemF0aW9ucy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgICA8JSB9ICU+XHJcbiAgICAgIDwvZGl2PlxyXG5cclxuICAgICAgPCUgaWYgKGJhc2UucmVwb3NpdG9yaWVzKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMiAyLjVBMi41IDIuNSAwIDAxNC41IDBoOC43NWEuNzUuNzUgMCAwMS43NS43NXYxMi41YS43NS43NSAwIDAxLS43NS43NWgtMi41YS43NS43NSAwIDExMC0xLjVoMS43NXYtMmgtOGExIDEgMCAwMC0uNzE0IDEuNy43NS43NSAwIDAxLTEuMDcyIDEuMDVBMi40OTUgMi40OTUgMCAwMTIgMTEuNXYtOXptMTAuNS0xVjloLThjLS4zNTYgMC0uNjk0LjA3NC0xIC4yMDhWMi41YTEgMSAwIDAxMS0xaDh6TTUgMTIuMjV2My4yNWEuMjUuMjUgMCAwMC40LjJsMS40NS0xLjA4N2EuMjUuMjUgMCAwMS4zIDBMOC42IDE1LjdhLjI1LjI1IDAgMDAuNC0uMnYtMy4yNWEuMjUuMjUgMCAwMC0uMjUtLjI1aC0zLjVhLjI1LjI1IDAgMDAtLjI1LjI1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgPCU9IHVzZXIucmVwb3NpdG9yaWVzLnRvdGFsQ291bnQgJT4gUmVwb3NpdG9yPCU9IHModXNlci5yZXBvc2l0b3JpZXMudG90YWxDb3VudCwgXCJ5XCIpICU+XHJcbiAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04Ljc1Ljc1YS43NS43NSAwIDAwLTEuNSAwVjJoLS45ODRjLS4zMDUgMC0uNjA0LjA4LS44NjkuMjNsLTEuMjg4LjczN0EuMjUuMjUgMCAwMTMuOTg0IDNIMS43NWEuNzUuNzUgMCAwMDAgMS41aC40MjhMLjA2NiA5LjE5MmEuNzUuNzUgMCAwMC4xNTQuODM4bC41My0uNTMtLjUzLjUzdi4wMDFsLjAwMi4wMDIuMDAyLjAwMi4wMDYuMDA2LjAxNi4wMTUuMDQ1LjA0YTMuNTE0IDMuNTE0IDAgMDAuNjg2LjQ1QTQuNDkyIDQuNDkyIDAgMDAzIDExYy44OCAwIDEuNTU2LS4yMiAyLjAyMy0uNDU0YTMuNTE1IDMuNTE1IDAgMDAuNjg2LS40NWwuMDQ1LS4wNC4wMTYtLjAxNS4wMDYtLjAwNi4wMDItLjAwMi4wMDEtLjAwMkw1LjI1IDkuNWwuNTMuNTNhLjc1Ljc1IDAgMDAuMTU0LS44MzhMMy44MjIgNC41aC4xNjJjLjMwNSAwIC42MDQtLjA4Ljg2OS0uMjNsMS4yODktLjczN2EuMjUuMjUgMCAwMS4xMjQtLjAzM2guOTg0VjEzaC0yLjVhLjc1Ljc1IDAgMDAwIDEuNWg2LjVhLjc1Ljc1IDAgMDAwLTEuNWgtMi41VjMuNWguOTg0YS4yNS4yNSAwIDAxLjEyNC4wMzNsMS4yOS43MzZjLjI2NC4xNTIuNTYzLjIzMS44NjguMjMxaC4xNjJsLTIuMTEyIDQuNjkyYS43NS43NSAwIDAwLjE1NC44MzhsLjUzLS41My0uNTMuNTN2LjAwMWwuMDAyLjAwMi4wMDIuMDAyLjAwNi4wMDYuMDE2LjAxNS4wNDUuMDRhMy41MTcgMy41MTcgMCAwMC42ODYuNDVBNC40OTIgNC40OTIgMCAwMDEzIDExYy44OCAwIDEuNTU2LS4yMiAyLjAyMy0uNDU0YTMuNTEyIDMuNTEyIDAgMDAuNjg2LS40NWwuMDQ1LS4wNC4wMS0uMDEuMDA2LS4wMDUuMDA2LS4wMDYuMDAyLS4wMDIuMDAxLS4wMDItLjUyOS0uNTMxLjUzLjUzYS43NS43NSAwIDAwLjE1NC0uODM4TDEzLjgyMyA0LjVoLjQyN2EuNzUuNzUgMCAwMDAtMS41aC0yLjIzNGEuMjUuMjUgMCAwMS0uMTI0LS4wMzNsLTEuMjktLjczNkExLjc1IDEuNzUgMCAwMDkuNzM1IDJIOC43NVYuNzV6TTEuNjk1IDkuMjI3Yy4yODUuMTM1LjcxOC4yNzMgMS4zMDUuMjczczEuMDItLjEzOCAxLjMwNS0uMjczTDMgNi4zMjdsLTEuMzA1IDIuOXptMTAgMGMuMjg1LjEzNS43MTguMjczIDEuMzA1LjI3M3MxLjAyLS4xMzggMS4zMDUtLjI3M0wxMyA2LjMyN2wtMS4zMDUgMi45elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5saWNlbnNlcy5mYXZvcml0ZS5sZW5ndGgpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgUHJlZmVyIDwlPSBjb21wdXRlZC5saWNlbnNlcy5mYXZvcml0ZSAlPiBsaWNlbnNlXHJcbiAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICBObyBsaWNlbnNlIHByZWZlcmVuY2VcclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04Ljg3OC4zOTJhMS43NSAxLjc1IDAgMDAtMS43NTYgMGwtNS4yNSAzLjA0NUExLjc1IDEuNzUgMCAwMDEgNC45NTF2Ni4wOThjMCAuNjI0LjMzMiAxLjIuODcyIDEuNTE0bDUuMjUgMy4wNDVhMS43NSAxLjc1IDAgMDAxLjc1NiAwbDUuMjUtMy4wNDVjLjU0LS4zMTMuODcyLS44OS44NzItMS41MTRWNC45NTFjMC0uNjI0LS4zMzItMS4yLS44NzItMS41MTRMOC44NzguMzkyek03Ljg3NSAxLjY5YS4yNS4yNSAwIDAxLjI1IDBsNC42MyAyLjY4NUw4IDcuMTMzIDMuMjQ1IDQuMzc1bDQuNjMtMi42ODV6TTIuNSA1LjY3N3Y1LjM3MmMwIC4wOS4wNDcuMTcxLjEyNS4yMTZsNC42MjUgMi42ODNWOC40MzJMMi41IDUuNjc3em02LjI1IDguMjcxbDQuNjI1LTIuNjgzYS4yNS4yNSAwIDAwLjEyNS0uMjE2VjUuNjc3TDguNzUgOC40MzJ2NS41MTZ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgPCU9IHVzZXIucGFja2FnZXMudG90YWxDb3VudCAlPiBQYWNrYWdlPCU9IHModXNlci5wYWNrYWdlcy50b3RhbENvdW50KSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjUgMy41YzAtLjEzMy4wNTgtLjMxOC4yODItLjU1LjIyNy0uMjM3LjU5Mi0uNDg0IDEuMS0uNzA4QzQuODk5IDEuNzk1IDYuMzU0IDEuNSA4IDEuNWMxLjY0NyAwIDMuMTAyLjI5NSA0LjExNy43NDIuNTEuMjI0Ljg3NC40NyAxLjEwMS43MDcuMjI0LjIzMy4yODIuNDE4LjI4Mi41NTEgMCAuMTMzLS4wNTguMzE4LS4yODIuNTUtLjIyNy4yMzctLjU5Mi40ODQtMS4xLjcwOEMxMS4xMDEgNS4yMDUgOS42NDYgNS41IDggNS41Yy0xLjY0NyAwLTMuMTAyLS4yOTUtNC4xMTctLjc0Mi0uNTEtLjIyNC0uODc0LS40Ny0xLjEwMS0uNzA3LS4yMjQtLjIzMy0uMjgyLS40MTgtLjI4Mi0uNTUxek0xIDMuNWMwLS42MjYuMjkyLTEuMTY1LjctMS41OS40MDYtLjQyMi45NTYtLjc2NyAxLjU3OS0xLjA0MUM0LjUyNS4zMiA2LjE5NSAwIDggMGMxLjgwNSAwIDMuNDc1LjMyIDQuNzIyLjg2OS42MjIuMjc0IDEuMTcyLjYyIDEuNTc4IDEuMDQuNDA4LjQyNi43Ljk2NS43IDEuNTkxdjljMCAuNjI2LS4yOTIgMS4xNjUtLjcgMS41OS0uNDA2LjQyMi0uOTU2Ljc2Ny0xLjU3OSAxLjA0MUMxMS40NzYgMTUuNjggOS44MDYgMTYgOCAxNmMtMS44MDUgMC0zLjQ3NS0uMzItNC43MjEtLjg2OS0uNjIzLS4yNzQtMS4xNzMtLjYyLTEuNTc5LTEuMDQtLjQwOC0uNDI2LS43LS45NjUtLjctMS41OTF2LTl6TTIuNSA4VjUuNzI0Yy4yNDEuMTUuNTAzLjI4Ni43NzkuNDA3QzQuNTI1IDYuNjggNi4xOTUgNyA4IDdjMS44MDUgMCAzLjQ3NS0uMzIgNC43MjItLjg2OS4yNzUtLjEyMS41MzctLjI1Ny43NzgtLjQwN1Y4YzAgLjEzMy0uMDU4LjMxOC0uMjgyLjU1LS4yMjcuMjM3LS41OTIuNDg0LTEuMS43MDhDMTEuMTAxIDkuNzA1IDkuNjQ2IDEwIDggMTBjLTEuNjQ3IDAtMy4xMDItLjI5NS00LjExNy0uNzQyLS41MS0uMjI0LS44NzQtLjQ3LTEuMTAxLS43MDdDMi41NTggOC4zMTggMi41IDguMTMzIDIuNSA4em0wIDIuMjI1VjEyLjVjMCAuMTMzLjA1OC4zMTguMjgyLjU1LjIyNy4yMzcuNTkyLjQ4NCAxLjEuNzA4IDEuMDE2LjQ0NyAyLjQ3MS43NDIgNC4xMTguNzQyIDEuNjQ3IDAgMy4xMDItLjI5NSA0LjExNy0uNzQyLjUxLS4yMjQuODc0LS40NyAxLjEwMS0uNzA3LjIyNC0uMjMzLjI4Mi0uNDE4LjI4Mi0uNTUxdi0yLjI3NWMtLjI0MS4xNS0uNTAzLjI4NS0uNzc4LjQwNi0xLjI0Ny41NDktMi45MTcuODY5LTQuNzIyLjg2OS0xLjgwNSAwLTMuNDc1LS4zMi00LjcyMS0uODY5YTYuMjM2IDYuMjM2IDAgMDEtLjc3OS0uNDA2elwiLz48L3N2Zz5cclxuICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5kaXNrVXNhZ2UgJT4gdXNlZFxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmxpbmVzKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCA8JT0gY29tcHV0ZWQucGx1Z2lucy5saW5lcy5lcnJvciA/ICdlcnJvcicgOiAnJyAlPlwiPlxyXG4gICAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk00LjcyIDMuMjJhLjc1Ljc1IDAgMDExLjA2IDEuMDZMMi4wNiA4bDMuNzIgMy43MmEuNzUuNzUgMCAxMS0xLjA2IDEuMDZMLjQ3IDguNTNhLjc1Ljc1IDAgMDEwLTEuMDZsNC4yNS00LjI1em02LjU2IDBhLjc1Ljc1IDAgMTAtMS4wNiAxLjA2TDEzLjk0IDhsLTMuNzIgMy43MmEuNzUuNzUgMCAxMDEuMDYgMS4wNmw0LjI1LTQuMjVhLjc1Ljc1IDAgMDAwLTEuMDZsLTQuMjUtNC4yNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLmxpbmVzLmVycm9yLm1lc3NhZ2UgJT5cclxuICAgICAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuYWRkZWQgJT4gYWRkZWQsIDwlPSBjb21wdXRlZC5wbHVnaW5zLmxpbmVzLmRlbGV0ZWQgJT4gcmVtb3ZlZFxyXG4gICAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTggLjI1YS43NS43NSAwIDAxLjY3My40MThsMS44ODIgMy44MTUgNC4yMS42MTJhLjc1Ljc1IDAgMDEuNDE2IDEuMjc5bC0zLjA0NiAyLjk3LjcxOSA0LjE5MmEuNzUuNzUgMCAwMS0xLjA4OC43OTFMOCAxMi4zNDdsLTMuNzY2IDEuOThhLjc1Ljc1IDAgMDEtMS4wODgtLjc5bC43Mi00LjE5NEwuODE4IDYuMzc0YS43NS43NSAwIDAxLjQxNi0xLjI4bDQuMjEtLjYxMUw3LjMyNy42NjhBLjc1Ljc1IDAgMDE4IC4yNXptMCAyLjQ0NUw2LjYxNSA1LjVhLjc1Ljc1IDAgMDEtLjU2NC40MWwtMy4wOTcuNDUgMi4yNCAyLjE4NGEuNzUuNzUgMCAwMS4yMTYuNjY0bC0uNTI4IDMuMDg0IDIuNzY5LTEuNDU2YS43NS43NSAwIDAxLjY5OCAwbDIuNzcgMS40NTYtLjUzLTMuMDg0YS43NS43NSAwIDAxLjIxNi0uNjY0bDIuMjQtMi4xODMtMy4wOTYtLjQ1YS43NS43NSAwIDAxLS41NjQtLjQxTDggMi42OTR2LjAwMXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucmVwb3NpdG9yaWVzLnN0YXJnYXplcnMgJT4gU3RhcmdhemVyPCU9IHMoY29tcHV0ZWQucmVwb3NpdG9yaWVzLnN0YXJnYXplcnMpICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNSAzLjI1YS43NS43NSAwIDExLTEuNSAwIC43NS43NSAwIDAxMS41IDB6bTAgMi4xMjJhMi4yNSAyLjI1IDAgMTAtMS41IDB2Ljg3OEEyLjI1IDIuMjUgMCAwMDUuNzUgOC41aDEuNXYyLjEyOGEyLjI1MSAyLjI1MSAwIDEwMS41IDBWOC41aDEuNWEyLjI1IDIuMjUgMCAwMDIuMjUtMi4yNXYtLjg3OGEyLjI1IDIuMjUgMCAxMC0xLjUgMHYuODc4YS43NS43NSAwIDAxLS43NS43NWgtNC41QS43NS43NSAwIDAxNSA2LjI1di0uODc4em0zLjc1IDcuMzc4YS43NS43NSAwIDExLTEuNSAwIC43NS43NSAwIDAxMS41IDB6bTMtOC43NWEuNzUuNzUgMCAxMDAtMS41Ljc1Ljc1IDAgMDAwIDEuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucmVwb3NpdG9yaWVzLmZvcmtzICU+IEZvcms8JT0gcyhjb21wdXRlZC5yZXBvc2l0b3JpZXMuZm9ya3MpICU+XHJcbiAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMS42NzkgNy45MzJjLjQxMi0uNjIxIDEuMjQyLTEuNzUgMi4zNjYtMi43MTdDNS4xNzUgNC4yNDIgNi41MjcgMy41IDggMy41YzEuNDczIDAgMi44MjQuNzQyIDMuOTU1IDEuNzE1IDEuMTI0Ljk2NyAxLjk1NCAyLjA5NiAyLjM2NiAyLjcxN2EuMTE5LjExOSAwIDAxMCAuMTM2Yy0uNDEyLjYyMS0xLjI0MiAxLjc1LTIuMzY2IDIuNzE3QzEwLjgyNSAxMS43NTggOS40NzMgMTIuNSA4IDEyLjVjLTEuNDczIDAtMi44MjQtLjc0Mi0zLjk1NS0xLjcxNUMyLjkyIDkuODE4IDIuMDkgOC42OSAxLjY3OSA4LjA2OGEuMTE5LjExOSAwIDAxMC0uMTM2ek04IDJjLTEuOTgxIDAtMy42Ny45OTItNC45MzMgMi4wNzhDMS43OTcgNS4xNjkuODggNi40MjMuNDMgNy4xYTEuNjE5IDEuNjE5IDAgMDAwIDEuNzk4Yy40NS42NzggMS4zNjcgMS45MzIgMi42MzcgMy4wMjRDNC4zMjkgMTMuMDA4IDYuMDE5IDE0IDggMTRjMS45ODEgMCAzLjY3LS45OTIgNC45MzMtMi4wNzggMS4yNy0xLjA5MSAyLjE4Ny0yLjM0NSAyLjYzNy0zLjAyM2ExLjYxOSAxLjYxOSAwIDAwMC0xLjc5OGMtLjQ1LS42NzgtMS4zNjctMS45MzItMi42MzctMy4wMjNDMTEuNjcxIDIuOTkyIDkuOTgxIDIgOCAyem0wIDhhMiAyIDAgMTAwLTQgMiAyIDAgMDAwIDR6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnJlcG9zaXRvcmllcy53YXRjaGVycyAlPiBXYXRjaGVyPCU9IHMoY29tcHV0ZWQucmVwb3NpdG9yaWVzLndhdGNoZXJzKSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIDwlPSBjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMuZXJyb3IgPyAnZXJyb3InIDogJycgJT5cIj5cclxuICAgICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMCAxLjc1QS43NS43NSAwIDAxLjc1IDFoNC4yNTNjMS4yMjcgMCAyLjMxNy41OSAzIDEuNTAxQTMuNzQ0IDMuNzQ0IDAgMDExMS4wMDYgMWg0LjI0NWEuNzUuNzUgMCAwMS43NS43NXYxMC41YS43NS43NSAwIDAxLS43NS43NWgtNC41MDdhMi4yNSAyLjI1IDAgMDAtMS41OTEuNjU5bC0uNjIyLjYyMWEuNzUuNzUgMCAwMS0xLjA2IDBsLS42MjItLjYyMUEyLjI1IDIuMjUgMCAwMDUuMjU4IDEzSC43NWEuNzUuNzUgMCAwMS0uNzUtLjc1VjEuNzV6bTguNzU1IDNhMi4yNSAyLjI1IDAgMDEyLjI1LTIuMjVIMTQuNXY5aC0zLjc1N2MtLjcxIDAtMS40LjIwMS0xLjk5Mi41NzJsLjAwNC03LjMyMnptLTEuNTA0IDcuMzI0bC4wMDQtNS4wNzMtLjAwMi0yLjI1M0EyLjI1IDIuMjUgMCAwMDUuMDAzIDIuNUgxLjV2OWgzLjc1N2EzLjc1IDMuNzUgMCAwMTEuOTk0LjU3NHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgICAgICAgICAgICAgIDwlPSBjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMudmlld3MuY291bnQgJT4gdmlldzwlPSBzKGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy52aWV3cy5jb3VudCkgJT4gaW4gbGFzdCB0d28gd2Vla3NcclxuICAgICAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICA8JSB9ICU+XHJcblxyXG4gICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cCkgeyAlPlxyXG4gICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuXHJcbiAgICAgICAgICA8c2VjdGlvbiBjbGFzcz1cImNvbHVtblwiPlxyXG4gICAgICAgICAgICA8aDM+SXNzdWVzPC9oMz5cclxuICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC40Ny4yMkEuNzUuNzUgMCAwMTUgMGg2YS43NS43NSAwIDAxLjUzLjIybDQuMjUgNC4yNWMuMTQxLjE0LjIyLjMzMS4yMi41M3Y2YS43NS43NSAwIDAxLS4yMi41M2wtNC4yNSA0LjI1QS43NS43NSAwIDAxMTEgMTZINWEuNzUuNzUgMCAwMS0uNTMtLjIyTC4yMiAxMS41M0EuNzUuNzUgMCAwMTAgMTFWNWEuNzUuNzUgMCAwMS4yMi0uNTNMNC40Ny4yMnptLjg0IDEuMjhMMS41IDUuMzF2NS4zOGwzLjgxIDMuODFoNS4zOGwzLjgxLTMuODFWNS4zMUwxMC42OSAxLjVINS4zMXpNOCA0YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMHYtMy41QS43NS43NSAwIDAxOCA0em0wIDhhMSAxIDAgMTAwLTIgMSAxIDAgMDAwIDJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImJhclwiIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB3aWR0aD1cIjIyMFwiIGhlaWdodD1cIjhcIj5cclxuICAgICAgICAgICAgICAgIDxtYXNrIGlkPVwiaXNzdWVzLWJhclwiPlxyXG4gICAgICAgICAgICAgICAgICA8cmVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCIyMjBcIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIndoaXRlXCIgcng9XCI1XCIvPlxyXG4gICAgICAgICAgICAgICAgPC9tYXNrPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjaXNzdWVzLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5pc3N1ZXMuY291bnQgPyAwIDogMjIwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCIjZDFkNWRhXCIvPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjaXNzdWVzLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiNkNzNhNDlcIi8+XHJcbiAgICAgICAgICAgICAgICA8cmVjdCBtYXNrPVwidXJsKCNpc3N1ZXMtYmFyKVwiIHg9XCI8JT0gKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiB5PVwiMFwiIHdpZHRoPVwiPCU9ICgxLWNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZC9jb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jb3VudCkqMjIwIHx8IDAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiMyOGE3NDVcIi8+XHJcbiAgICAgICAgICAgICAgPC9zdmc+XHJcbiAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGhvcml6b250YWwgZmlsbC13aWR0aFwiPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGNlbnRlclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbD1cIiNkNzNhNDlcIiBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjUgOGE2LjUgNi41IDAgMDExMC42NS01LjAwMy43NS43NSAwIDAwLjk1OS0xLjE1MyA4IDggMCAxMDIuNTkyIDguMzMuNzUuNzUgMCAxMC0xLjQ0NC0uNDA3QTYuNSA2LjUgMCAwMTEuNSA4ek04IDEyYTEgMSAwIDEwMC0yIDEgMSAwIDAwMCAyem0wLThhLjc1Ljc1IDAgMDEuNzUuNzV2My41YS43NS43NSAwIDExLTEuNSAwdi0zLjVBLjc1Ljc1IDAgMDE4IDR6bTQuNzggNC4yOGwzLTNhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2bC0yLjQ3IDIuNDctLjk3LS45N2EuNzQ5Ljc0OSAwIDEwLTEuMDYgMS4wNmwxLjUgMS41YS43NS43NSAwIDAwMS4wNiAwelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPHNwYW4gY2xhc3M9XCJuby13cmFwXCI+PCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNsb3NlZCAlPiBDbG9zZWQ8L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjZW50ZXJcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGw9XCIjMjhhNzQ1XCIgZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNOCAxLjVhNi41IDYuNSAwIDEwMCAxMyA2LjUgNi41IDAgMDAwLTEzek0wIDhhOCA4IDAgMTExNiAwQTggOCAwIDAxMCA4em05IDNhMSAxIDAgMTEtMiAwIDEgMSAwIDAxMiAwem0tLjI1LTYuMjVhLjc1Ljc1IDAgMDAtMS41IDB2My41YS43NS43NSAwIDAwMS41IDB2LTMuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwibm8td3JhcFwiPjwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5vcGVuICU+IE9wZW48L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG5cclxuICAgICAgICAgIDxzZWN0aW9uIGNsYXNzPVwiY29sdW1uXCI+XHJcbiAgICAgICAgICAgIDxoMz5QdWxsIHJlcXVlc3RzPC9oMz5cclxuICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC40Ny4yMkEuNzUuNzUgMCAwMTUgMGg2YS43NS43NSAwIDAxLjUzLjIybDQuMjUgNC4yNWMuMTQxLjE0LjIyLjMzMS4yMi41M3Y2YS43NS43NSAwIDAxLS4yMi41M2wtNC4yNSA0LjI1QS43NS43NSAwIDAxMTEgMTZINWEuNzUuNzUgMCAwMS0uNTMtLjIyTC4yMiAxMS41M0EuNzUuNzUgMCAwMTAgMTFWNWEuNzUuNzUgMCAwMS4yMi0uNTNMNC40Ny4yMnptLjg0IDEuMjhMMS41IDUuMzF2NS4zOGwzLjgxIDMuODFoNS4zOGwzLjgxLTMuODFWNS4zMUwxMC42OSAxLjVINS4zMXpNOCA0YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMHYtMy41QS43NS43NSAwIDAxOCA0em0wIDhhMSAxIDAgMTAwLTIgMSAxIDAgMDAwIDJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImJhclwiIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB3aWR0aD1cIjIyMFwiIGhlaWdodD1cIjhcIj5cclxuICAgICAgICAgICAgICAgIDxtYXNrIGlkPVwicHItYmFyXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxyZWN0IHg9XCIwXCIgeT1cIjBcIiB3aWR0aD1cIjIyMFwiIGhlaWdodD1cIjhcIiBmaWxsPVwid2hpdGVcIiByeD1cIjVcIi8+XHJcbiAgICAgICAgICAgICAgICA8L21hc2s+XHJcbiAgICAgICAgICAgICAgICA8cmVjdCBtYXNrPVwidXJsKCNwci1iYXIpXCIgeD1cIjBcIiB5PVwiMFwiIHdpZHRoPVwiPCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIuY291bnQgPyAwIDogMjIwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCIjZDFkNWRhXCIvPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjcHItYmFyKVwiIHg9XCIwXCIgeT1cIjBcIiB3aWR0aD1cIjwlPSAoY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5tZXJnZWQvY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5jb3VudCkqMjIwIHx8IDAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiM2ZjQyYzFcIi8+XHJcbiAgICAgICAgICAgICAgICA8cmVjdCBtYXNrPVwidXJsKCNwci1iYXIpXCIgeD1cIjwlPSAoY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5tZXJnZWQvY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5jb3VudCkqMjIwIHx8IDAgJT5cIiB5PVwiMFwiIHdpZHRoPVwiPCU9ICgxLWNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIubWVyZ2VkL2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAucHIuY291bnQpKjIyMCB8fCAwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCIjMjhhNzQ1XCIvPlxyXG4gICAgICAgICAgICAgIDwvc3ZnPlxyXG4gICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBob3Jpem9udGFsIGZpbGwtd2lkdGhcIj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjZW50ZXJcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGw9XCIjNmY0MmMxXCIgZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNSAzLjI1NFYzLjI1di4wMDVhLjc1Ljc1IDAgMTEwLS4wMDV2LjAwNHptLjQ1IDEuOWEyLjI1IDIuMjUgMCAxMC0xLjk1LjIxOHY1LjI1NmEyLjI1IDIuMjUgMCAxMDEuNSAwVjcuMTIzQTUuNzM1IDUuNzM1IDAgMDA5LjI1IDloMS4zNzhhMi4yNTEgMi4yNTEgMCAxMDAtMS41SDkuMjVhNC4yNSA0LjI1IDAgMDEtMy44LTIuMzQ2ek0xMi43NSA5YS43NS43NSAwIDEwMC0xLjUuNzUuNzUgMCAwMDAgMS41em0tOC41IDQuNWEuNzUuNzUgMCAxMDAtMS41Ljc1Ljc1IDAgMDAwIDEuNXpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICAgIDxzcGFuIGNsYXNzPVwibm8td3JhcFwiPjwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm1lcmdlZCAlPiBNZXJnZWQ8L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBjZW50ZXJcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGw9XCIjMjhhNzQ1XCIgZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNy4xNzcgMy4wNzNMOS41NzMuNjc3QS4yNS4yNSAwIDAxMTAgLjg1NHY0Ljc5MmEuMjUuMjUgMCAwMS0uNDI3LjE3N0w3LjE3NyAzLjQyN2EuMjUuMjUgMCAwMTAtLjM1NHpNMy43NSAyLjVhLjc1Ljc1IDAgMTAwIDEuNS43NS43NSAwIDAwMC0xLjV6bS0yLjI1Ljc1YTIuMjUgMi4yNSAwIDExMyAyLjEyMnY1LjI1NmEyLjI1MSAyLjI1MSAwIDExLTEuNSAwVjUuMzcyQTIuMjUgMi4yNSAwIDAxMS41IDMuMjV6TTExIDIuNWgtMVY0aDFhMSAxIDAgMDExIDF2NS42MjhhMi4yNTEgMi4yNTEgMCAxMDEuNSAwVjVBMi41IDIuNSAwIDAwMTEgMi41em0xIDEwLjI1YS43NS43NSAwIDExMS41IDAgLjc1Ljc1IDAgMDEtMS41IDB6TTMuNzUgMTJhLjc1Ljc1IDAgMTAwIDEuNS43NS43NSAwIDAwMC0xLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cIm5vLXdyYXBcIj48JT0gY29tcHV0ZWQucGx1Z2lucy5mb2xsb3d1cC5wci5vcGVuICU+IE9wZW48L3NwYW4+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG5cclxuICAgICAgICA8L2Rpdj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGFuZ3VhZ2VzKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24gY2xhc3M9XCJjb2x1bW5cIj5cclxuICAgICAgICAgIDxoMz5Nb3N0IHVzZWQgbGFuZ3VhZ2VzPC9oMz5cclxuICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk00LjQ3LjIyQS43NS43NSAwIDAxNSAwaDZhLjc1Ljc1IDAgMDEuNTMuMjJsNC4yNSA0LjI1Yy4xNDEuMTQuMjIuMzMxLjIyLjUzdjZhLjc1Ljc1IDAgMDEtLjIyLjUzbC00LjI1IDQuMjVBLjc1Ljc1IDAgMDExMSAxNkg1YS43NS43NSAwIDAxLS41My0uMjJMLjIyIDExLjUzQS43NS43NSAwIDAxMCAxMVY1YS43NS43NSAwIDAxLjIyLS41M0w0LjQ3LjIyem0uODQgMS4yOEwxLjUgNS4zMXY1LjM4bDMuODEgMy44MWg1LjM4bDMuODEtMy44MVY1LjMxTDEwLjY5IDEuNUg1LjMxek04IDRhLjc1Ljc1IDAgMDEuNzUuNzV2My41YS43NS43NSAwIDAxLTEuNSAwdi0zLjVBLjc1Ljc1IDAgMDE4IDR6bTAgOGExIDEgMCAxMDAtMiAxIDEgMCAwMDAgMnpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICA8c3ZnIGNsYXNzPVwiYmFyXCIgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHdpZHRoPVwiNDYwXCIgaGVpZ2h0PVwiOFwiPlxyXG4gICAgICAgICAgICAgIDxtYXNrIGlkPVwibGFuZ3VhZ2VzLWJhclwiPlxyXG4gICAgICAgICAgICAgICAgPHJlY3QgeD1cIjBcIiB5PVwiMFwiIHdpZHRoPVwiNDYwXCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCJ3aGl0ZVwiIHJ4PVwiNVwiLz5cclxuICAgICAgICAgICAgICA8L21hc2s+XHJcbiAgICAgICAgICAgICAgPHJlY3QgbWFzaz1cInVybCgjbGFuZ3VhZ2VzLWJhcilcIiB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZmF2b3JpdGVzLmxlbmd0aCA/IDAgOiA0NjAgJT5cIiBoZWlnaHQ9XCI4XCIgZmlsbD1cIiNkMWQ1ZGFcIi8+XHJcbiAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7bmFtZSwgdmFsdWUsIGNvbG9yLCB4fSBvZiBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5mYXZvcml0ZXMpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxyZWN0IG1hc2s9XCJ1cmwoI2xhbmd1YWdlcy1iYXIpXCIgeD1cIjwlPSB4KjQ2MCAlPlwiIHk9XCIwXCIgd2lkdGg9XCI8JT0gdmFsdWUqNDYwICU+XCIgaGVpZ2h0PVwiOFwiIGZpbGw9XCI8JT0gY29sb3IgJT5cIi8+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3N2Zz5cclxuICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIGNlbnRlciBob3Jpem9udGFsLXdyYXAgZmlsbC13aWR0aFwiPlxyXG4gICAgICAgICAgICAgIDwlIGZvciAoY29uc3Qge25hbWUsIHZhbHVlLCBjb2xvcn0gb2YgY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZmF2b3JpdGVzKSB7ICU+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgY2VudGVyIG5vLXdyYXAgbGFuZ3VhZ2VcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGw9XCI8JT0gY29sb3IgJT5cIiBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk04IDRhNCA0IDAgMTAwIDggNCA0IDAgMDAwLTh6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gbmFtZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkgeyAlPlxyXG4gICAgICAgIDxkaXYgY2xhc3M9XCJyb3dcIj5cclxuICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xNC4wNjQgMGE4Ljc1IDguNzUgMCAwMC02LjE4NyAyLjU2M2wtLjQ1OS40NThjLS4zMTQuMzE0LS42MTYuNjQxLS45MDQuOTc5SDMuMzFhMS43NSAxLjc1IDAgMDAtMS40OS44MzNMLjExIDcuNjA3YS43NS43NSAwIDAwLjQxOCAxLjExbDMuMTAyLjk1NGMuMDM3LjA1MS4wNzkuMS4xMjQuMTQ1bDIuNDI5IDIuNDI4Yy4wNDYuMDQ2LjA5NC4wODguMTQ1LjEyNWwuOTU0IDMuMTAyYS43NS43NSAwIDAwMS4xMS40MThsMi43NzQtMS43MDdhMS43NSAxLjc1IDAgMDAuODMzLTEuNDlWOS40ODVjLjMzOC0uMjg4LjY2NS0uNTkuOTc5LS45MDRsLjQ1OC0uNDU5QTguNzUgOC43NSAwIDAwMTYgMS45MzZWMS43NUExLjc1IDEuNzUgMCAwMDE0LjI1IDBoLS4xODZ6TTEwLjUgMTAuNjI1Yy0uMDg4LjA2LS4xNzcuMTE4LS4yNjYuMTc1bC0yLjM1IDEuNTIxLjU0OCAxLjc4MyAxLjk0OS0xLjJhLjI1LjI1IDAgMDAuMTE5LS4yMTN2LTIuMDY2ek0zLjY3OCA4LjExNkw1LjIgNS43NjZjLjA1OC0uMDkuMTE3LS4xNzguMTc2LS4yNjZIMy4zMDlhLjI1LjI1IDAgMDAtLjIxMy4xMTlsLTEuMiAxLjk1IDEuNzgyLjU0N3ptNS4yNi00LjQ5M0E3LjI1IDcuMjUgMCAwMTE0LjA2MyAxLjVoLjE4NmEuMjUuMjUgMCAwMS4yNS4yNXYuMTg2YTcuMjUgNy4yNSAwIDAxLTIuMTIzIDUuMTI3bC0uNDU5LjQ1OGExNS4yMSAxNS4yMSAwIDAxLTIuNDk5IDIuMDJsLTIuMzE3IDEuNS0yLjE0My0yLjE0MyAxLjUtMi4zMTdhMTUuMjUgMTUuMjUgMCAwMTIuMDItMi41bC40NTgtLjQ1OGguMDAyek0xMiA1YTEgMSAwIDExLTIgMCAxIDEgMCAwMTIgMHptLTguNDQgOS41NmExLjUgMS41IDAgMTAtMi4xMi0yLjEyYy0uNzM0LjczLTEuMDQ3IDIuMzMyLTEuMTUgMy4wMDNhLjIzLjIzIDAgMDAuMjY1LjI2NWMuNjcxLS4xMDMgMi4yNzMtLjQxNiAzLjAwNS0xLjE0OHpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgUGFnZVNwZWVkIEluc2lnaHRzXHJcbiAgICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk03Ljc3NSAzLjI3NWEuNzUuNzUgMCAwMDEuMDYgMS4wNmwxLjI1LTEuMjVhMiAyIDAgMTEyLjgzIDIuODNsLTIuNSAyLjVhMiAyIDAgMDEtMi44MyAwIC43NS43NSAwIDAwLTEuMDYgMS4wNiAzLjUgMy41IDAgMDA0Ljk1IDBsMi41LTIuNWEzLjUgMy41IDAgMDAtNC45NS00Ljk1bC0xLjI1IDEuMjV6bS00LjY5IDkuNjRhMiAyIDAgMDEwLTIuODNsMi41LTIuNWEyIDIgMCAwMTIuODMgMCAuNzUuNzUgMCAwMDEuMDYtMS4wNiAzLjUgMy41IDAgMDAtNC45NSAwbC0yLjUgMi41YTMuNSAzLjUgMCAwMDQuOTUgNC45NWwxLjI1LTEuMjVhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2bC0xLjI1IDEuMjVhMiAyIDAgMDEtMi44MyAwelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICA8JT0gdXNlci53ZWJzaXRlVXJsICU+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgIDwvZGl2PlxyXG4gICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZC5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG4gICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk00LjQ3LjIyQS43NS43NSAwIDAxNSAwaDZhLjc1Ljc1IDAgMDEuNTMuMjJsNC4yNSA0LjI1Yy4xNDEuMTQuMjIuMzMxLjIyLjUzdjZhLjc1Ljc1IDAgMDEtLjIyLjUzbC00LjI1IDQuMjVBLjc1Ljc1IDAgMDExMSAxNkg1YS43NS43NSAwIDAxLS41My0uMjJMLjIyIDExLjUzQS43NS43NSAwIDAxMCAxMVY1YS43NS43NSAwIDAxLjIyLS41M0w0LjQ3LjIyem0uODQgMS4yOEwxLjUgNS4zMXY1LjM4bDMuODEgMy44MWg1LjM4bDMuODEtMy44MVY1LjMxTDEwLjY5IDEuNUg1LjMxek04IDRhLjc1Ljc1IDAgMDEuNzUuNzV2My41YS43NS43NSAwIDAxLTEuNSAwdi0zLjVBLjc1Ljc1IDAgMDE4IDR6bTAgOGExIDEgMCAxMDAtMiAxIDEgMCAwMDAgMnpcIj48L3BhdGg+PC9zdmc+XHJcbiAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5wYWdlc3BlZWQuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJyb3cgZmlsbC13aWR0aFwiPlxyXG4gICAgICAgICAgICAgIDxzZWN0aW9uIGNsYXNzPVwiY2F0ZWdvcmllc1wiPlxyXG4gICAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7c2NvcmUsIHRpdGxlfSBvZiBjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZC5zY29yZXMpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImNhdGVnb3JpZSBjb2x1bW5cIj5cclxuICAgICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDEyMCAxMjBcIiB3aWR0aD1cIjUwXCIgaGVpZ2h0PVwiNTBcIiBjbGFzcz1cImdhdWdlIDwlPSAhTnVtYmVyLmlzTmFOKHNjb3JlKSA/IChzY29yZSA+PSAwLjkgPyAnaGlnaCcgOiBzY29yZSA+PSAwLjUgPyAnYXZlcmFnZScgOiAnbG93JykgOiAnJyAlPlwiPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPGNpcmNsZSBjbGFzcz1cImdhdWdlLWJhc2VcIiByPVwiNTNcIiBjeD1cIjYwXCIgY3k9XCI2MFwiPjwvY2lyY2xlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPCUgaWYgKCFOdW1iZXIuaXNOYU4oc2NvcmUpKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxjaXJjbGUgY2xhc3M9XCJnYXVnZS1hcmNcIiB0cmFuc2Zvcm09XCJyb3RhdGUoLTkwIDYwIDYwKVwiIHI9XCI1M1wiIGN4PVwiNjBcIiBjeT1cIjYwXCIgc3Ryb2tlLWRhc2hhcnJheT1cIjwlPSBzY29yZSAqIDMyOSAlPiAzMjlcIj48L2NpcmNsZT5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPHRleHQgeD1cIjYwXCIgeT1cIjYwXCIgZG9taW5hbnQtYmFzZWxpbmU9XCJjZW50cmFsXCIgPjwlPSBNYXRoLnJvdW5kKHNjb3JlKjEwMCkgJT48L3RleHQ+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgICA8dGV4dCB4PVwiNjBcIiB5PVwiNjBcIiBkb21pbmFudC1iYXNlbGluZT1cImNlbnRyYWxcIiA+LTwvdGV4dD5cclxuICAgICAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgICAgICA8L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgICA8c3BhbiBjbGFzcz1cInRpdGxlXCI+PCU9IHRpdGxlICU+PC9zcGFuPlxyXG4gICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgIDwlIH0gJT5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNOCAxLjVjLTIuMzYzIDAtNCAxLjY5LTQgMy43NSAwIC45ODQuNDI0IDEuNjI1Ljk4NCAyLjMwNGwuMjE0LjI1M2MuMjIzLjI2NC40Ny41NTYuNjczLjg0OC4yODQuNDExLjUzNy44OTYuNjIxIDEuNDlhLjc1Ljc1IDAgMDEtMS40ODQuMjExYy0uMDQtLjI4Mi0uMTYzLS41NDctLjM3LS44NDdhOC42OTUgOC42OTUgMCAwMC0uNTQyLS42OGMtLjA4NC0uMS0uMTczLS4yMDUtLjI2OC0uMzJDMy4yMDEgNy43NSAyLjUgNi43NjYgMi41IDUuMjUgMi41IDIuMzEgNC44NjMgMCA4IDBzNS41IDIuMzEgNS41IDUuMjVjMCAxLjUxNi0uNzAxIDIuNS0xLjMyOCAzLjI1OS0uMDk1LjExNS0uMTg0LjIyLS4yNjguMzE5LS4yMDcuMjQ1LS4zODMuNDUzLS41NDEuNjgxLS4yMDguMy0uMzMuNTY1LS4zNy44NDdhLjc1Ljc1IDAgMDEtMS40ODUtLjIxMmMuMDg0LS41OTMuMzM3LTEuMDc4LjYyMS0xLjQ4OS4yMDMtLjI5Mi40NS0uNTg0LjY3My0uODQ4LjA3NS0uMDg4LjE0Ny0uMTczLjIxMy0uMjUzLjU2MS0uNjc5Ljk4NS0xLjMyLjk4NS0yLjMwNCAwLTIuMDYtMS42MzctMy43NS00LTMuNzV6TTYgMTUuMjVhLjc1Ljc1IDAgMDEuNzUtLjc1aDIuNWEuNzUuNzUgMCAwMTAgMS41aC0yLjVhLjc1Ljc1IDAgMDEtLjc1LS43NXpNNS43NSAxMmEuNzUuNzUgMCAwMDAgMS41aDQuNWEuNzUuNzUgMCAwMDAtMS41aC00LjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICBDb2RpbmcgaGFiaXRzXHJcbiAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvd1wiPlxyXG4gICAgICAgICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5oYWJpdHMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICA8c2VjdGlvbj5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC40Ny4yMkEuNzUuNzUgMCAwMTUgMGg2YS43NS43NSAwIDAxLjUzLjIybDQuMjUgNC4yNWMuMTQxLjE0LjIyLjMzMS4yMi41M3Y2YS43NS43NSAwIDAxLS4yMi41M2wtNC4yNSA0LjI1QS43NS43NSAwIDAxMTEgMTZINWEuNzUuNzUgMCAwMS0uNTMtLjIyTC4yMiAxMS41M0EuNzUuNzUgMCAwMTAgMTFWNWEuNzUuNzUgMCAwMS4yMi0uNTNMNC40Ny4yMnptLjg0IDEuMjhMMS41IDUuMzF2NS4zOGwzLjgxIDMuODFoNS4zOGwzLjgxLTMuODFWNS4zMUwxMC42OSAxLjVINS4zMXpNOCA0YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMHYtMy41QS43NS43NSAwIDAxOCA0em0wIDhhMSAxIDAgMTAwLTIgMSAxIDAgMDAwIDJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5oYWJpdHMuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgIDx1bCBjbGFzcz1cImhhYml0c1wiPlxyXG4gICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaGFiaXRzLmluZGVudHMuc3R5bGUpIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGxpPlVzZSA8JT0gY29tcHV0ZWQucGx1Z2lucy5oYWJpdHMuaW5kZW50cy5zdHlsZSAlPiBmb3IgaW5kZW50czwvbGk+XHJcbiAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgICA8JSBpZiAoIU51bWJlci5pc05hTihjb21wdXRlZC5wbHVnaW5zLmhhYml0cy5jb21taXRzLmhvdXIpKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDxsaT5Nb3N0bHkgcHVzaCBjb2RlIGFyb3VuZCA8JT0gY29tcHV0ZWQucGx1Z2lucy5oYWJpdHMuY29tbWl0cy5ob3VyICU+OjAwPC9saT5cclxuICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICA8L3VsPlxyXG4gICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLm11c2ljKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNMS41IDhhNi41IDYuNSAwIDExMTMgMCA2LjUgNi41IDAgMDEtMTMgMHpNOCAwYTggOCAwIDEwMCAxNkE4IDggMCAwMDggMHpNNi4zNzkgNS4yMjdBLjI1LjI1IDAgMDA2IDUuNDQydjUuMTE3YS4yNS4yNSAwIDAwLjM3OS4yMTRsNC4yNjQtMi41NTlhLjI1LjI1IDAgMDAwLS40MjhMNi4zNzkgNS4yMjd6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5tdXNpYy5tb2RlICU+XHJcbiAgICAgICAgICA8L2gyPlxyXG4gICAgICAgICAgPGRpdiBjbGFzcz1cInJvdyBmaWxsLXdpZHRoXCI+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLm11c2ljLnByb3ZpZGVyKSB7ICU+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTIuMDAyIDIuNzI1YS43NS43NSAwIDAxLjc5Ny0uNjk5QzguNzkgMi40MiAxMy41OCA3LjIxIDEzLjk3NCAxMy4yMDFhLjc1Ljc1IDAgMTEtMS40OTcuMDk4IDEwLjUwMiAxMC41MDIgMCAwMC05Ljc3Ni05Ljc3Ni43NS43NSAwIDAxLS43LS43OTh6TTIgMTNhMSAxIDAgMTEyIDAgMSAxIDAgMDEtMiAwem0uODQtNS45NWEuNzUuNzUgMCAwMC0uMTc5IDEuNDg5YzIuNTA5LjMgNC41IDIuMjkxIDQuOCA0LjhhLjc1Ljc1IDAgMTAxLjQ5LS4xNzhBNy4wMDMgNy4wMDMgMCAwMDIuODM4IDcuMDV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICBGcm9tIDwlPSBjb21wdXRlZC5wbHVnaW5zLm11c2ljLnByb3ZpZGVyICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubXVzaWMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC40Ny4yMkEuNzUuNzUgMCAwMTUgMGg2YS43NS43NSAwIDAxLjUzLjIybDQuMjUgNC4yNWMuMTQxLjE0LjIyLjMzMS4yMi41M3Y2YS43NS43NSAwIDAxLS4yMi41M2wtNC4yNSA0LjI1QS43NS43NSAwIDAxMTEgMTZINWEuNzUuNzUgMCAwMS0uNTMtLjIyTC4yMiAxMS41M0EuNzUuNzUgMCAwMTAgMTFWNWEuNzUuNzUgMCAwMS4yMi0uNTNMNC40Ny4yMnptLjg0IDEuMjhMMS41IDUuMzF2NS4zOGwzLjgxIDMuODFoNS4zOGwzLjgxLTMuODFWNS4zMUwxMC42OSAxLjVINS4zMXpNOCA0YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMHYtMy41QS43NS43NSAwIDAxOCA0em0wIDhhMSAxIDAgMTAwLTIgMSAxIDAgMDAwIDJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5tdXNpYy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubXVzaWMudHJhY2tzLmxlbmd0aCkgeyAlPlxyXG4gICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwidHJhY2tsaXN0XCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPCUgZm9yIChjb25zdCB7bmFtZSA9IFwiXCIsIGFydGlzdCA9IFwiXCIsIGFydHdvcmsgPSBcIlwifSBvZiBjb21wdXRlZC5wbHVnaW5zLm11c2ljLnRyYWNrcykgeyAlPlxyXG4gICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cInRyYWNrXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxpbWcgc3JjPVwiZGF0YTppbWFnZS9wbmc7YmFzZTY0LDwlPSBhcnR3b3JrICU+XCIgd2lkdGg9XCIzMlwiIGhlaWdodD1cIjMyXCIgYWx0PVwiXCIvPlxyXG4gICAgICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiaW5mb3NcIj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwibmFtZVwiPjwlPSBuYW1lICU+PC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImFydGlzdFwiPjwlPSBhcnRpc3QgJT48L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgICAgPCUgfSBlbHNlIHsgJT5cclxuICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNzUgMS41YS4yNS4yNSAwIDAwLS4yNS4yNXY5LjVjMCAuMTM4LjExMi4yNS4yNS4yNWgyYS43NS43NSAwIDAxLjc1Ljc1djIuMTlsMi43Mi0yLjcyYS43NS43NSAwIDAxLjUzLS4yMmg2LjVhLjI1LjI1IDAgMDAuMjUtLjI1di05LjVhLjI1LjI1IDAgMDAtLjI1LS4yNUgxLjc1ek0wIDEuNzVDMCAuNzg0Ljc4NCAwIDEuNzUgMGgxMi41QzE1LjIxNiAwIDE2IC43ODQgMTYgMS43NXY5LjVBMS43NSAxLjc1IDAgMDExNC4yNSAxM0g4LjA2bC0yLjU3MyAyLjU3M0ExLjQ1NyAxLjQ1NyAwIDAxMyAxNC41NDNWMTNIMS43NUExLjc1IDEuNzUgMCAwMTAgMTEuMjV2LTkuNXpNOSA5YTEgMSAwIDExLTIgMCAxIDEgMCAwMTIgMHptLS4yNS01LjI1YS43NS43NSAwIDAwLTEuNSAwdjIuNWEuNzUuNzUgMCAwMDEuNSAwdi0yLjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICAgIE5vIG11c2ljIHJlY2VudGx5IGxpc3RlbmVkXHJcbiAgICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgPC9zZWN0aW9uPlxyXG4gICAgICA8JSB9ICU+XHJcblxyXG4gICAgICA8JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5wb3N0cykgeyAlPlxyXG4gICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgPGgyIGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTYgMmEuNzUuNzUgMCAwMS42OTYuNDcxTDEwIDEwLjczMWwxLjMwNC0zLjI2QS43NS43NSAwIDAxMTIgN2gzLjI1YS43NS43NSAwIDAxMCAxLjVoLTIuNzQybC0xLjgxMiA0LjUyOGEuNzUuNzUgMCAwMS0xLjM5MiAwTDYgNC43NyA0LjY5NiA4LjAzQS43NS43NSAwIDAxNCA4LjVILjc1YS43NS43NSAwIDAxMC0xLjVoMi43NDJsMS44MTItNC41MjlBLjc1Ljc1IDAgMDE2IDJ6XCIvPjwvc3ZnPlxyXG4gICAgICAgICAgICBSZWNlbnQgYXJ0aWNsZXNcclxuICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwicm93IGZpbGwtd2lkdGhcIj5cclxuICAgICAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMucG9zdHMuZXJyb3IpIHsgJT5cclxuICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZCBlcnJvclwiPlxyXG4gICAgICAgICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC40Ny4yMkEuNzUuNzUgMCAwMTUgMGg2YS43NS43NSAwIDAxLjUzLjIybDQuMjUgNC4yNWMuMTQxLjE0LjIyLjMzMS4yMi41M3Y2YS43NS43NSAwIDAxLS4yMi41M2wtNC4yNSA0LjI1QS43NS43NSAwIDAxMTEgMTZINWEuNzUuNzUgMCAwMS0uNTMtLjIyTC4yMiAxMS41M0EuNzUuNzUgMCAwMTAgMTFWNWEuNzUuNzUgMCAwMS4yMi0uNTNMNC40Ny4yMnptLjg0IDEuMjhMMS41IDUuMzF2NS4zOGwzLjgxIDMuODFoNS4zOGwzLjgxLTMuODFWNS4zMUwxMC42OSAxLjVINS4zMXpNOCA0YS43NS43NSAwIDAxLjc1Ljc1djMuNWEuNzUuNzUgMCAwMS0xLjUgMHYtMy41QS43NS43NSAwIDAxOCA0em0wIDhhMSAxIDAgMTAwLTIgMSAxIDAgMDAwIDJ6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICA8JT0gY29tcHV0ZWQucGx1Z2lucy5wb3N0cy5lcnJvci5tZXNzYWdlICU+XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8JSB9IGVsc2UgeyAlPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0yLjAwMiAyLjcyNWEuNzUuNzUgMCAwMS43OTctLjY5OUM4Ljc5IDIuNDIgMTMuNTggNy4yMSAxMy45NzQgMTMuMjAxYS43NS43NSAwIDExLTEuNDk3LjA5OCAxMC41MDIgMTAuNTAyIDAgMDAtOS43NzYtOS43NzYuNzUuNzUgMCAwMS0uNy0uNzk4ek0yIDEzYTEgMSAwIDExMiAwIDEgMSAwIDAxLTIgMHptLjg0LTUuOTVhLjc1Ljc1IDAgMDAtLjE3OSAxLjQ4OWMyLjUwOS4zIDQuNSAyLjI5MSA0LjggNC44YS43NS43NSAwIDEwMS40OS0uMTc4QTcuMDAzIDcuMDAzIDAgMDAyLjgzOCA3LjA1elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgRnJvbSA8JT0gY29tcHV0ZWQucGx1Z2lucy5wb3N0cy5zb3VyY2UgJT5cclxuICAgICAgICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMucG9zdHMucG9zdHMubGVuZ3RoKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDwlIGZvciAoY29uc3Qge3RpdGxlLCBkYXRlfSBvZiBjb21wdXRlZC5wbHVnaW5zLnBvc3RzLnBvc3RzKSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkIHBvc3RcIj5cclxuICAgICAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk00Ljc1IDBhLjc1Ljc1IDAgMDEuNzUuNzVWMmg1Vi43NWEuNzUuNzUgMCAwMTEuNSAwVjJoMS4yNWMuOTY2IDAgMS43NS43ODQgMS43NSAxLjc1djEwLjVBMS43NSAxLjc1IDAgMDExMy4yNSAxNkgyLjc1QTEuNzUgMS43NSAwIDAxMSAxNC4yNVYzLjc1QzEgMi43ODQgMS43ODQgMiAyLjc1IDJINFYuNzVBLjc1Ljc1IDAgMDE0Ljc1IDB6bTAgMy41aDguNWEuMjUuMjUgMCAwMS4yNS4yNVY2aC0xMVYzLjc1YS4yNS4yNSAwIDAxLjI1LS4yNWgyem0tMi4yNSA0djYuNzVjMCAuMTM4LjExMi4yNS4yNS4yNWgxMC41YS4yNS4yNSAwIDAwLjI1LS4yNVY3LjVoLTExelwiLz48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJpbmZvc1wiPlxyXG4gICAgICAgICAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZGF0ZVwiPjwlPSBkYXRlICU+PC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJ0aXRsZVwiPjwlPSB0aXRsZSAlPjwvZGl2PlxyXG4gICAgICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgICAgICAgIDwlIH0gZWxzZSB7ICU+XHJcbiAgICAgICAgICAgICAgICAgIDxkaXYgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk0xLjc1IDEuNWEuMjUuMjUgMCAwMC0uMjUuMjV2OS41YzAgLjEzOC4xMTIuMjUuMjUuMjVoMmEuNzUuNzUgMCAwMS43NS43NXYyLjE5bDIuNzItMi43MmEuNzUuNzUgMCAwMS41My0uMjJoNi41YS4yNS4yNSAwIDAwLjI1LS4yNXYtOS41YS4yNS4yNSAwIDAwLS4yNS0uMjVIMS43NXpNMCAxLjc1QzAgLjc4NC43ODQgMCAxLjc1IDBoMTIuNUMxNS4yMTYgMCAxNiAuNzg0IDE2IDEuNzV2OS41QTEuNzUgMS43NSAwIDAxMTQuMjUgMTNIOC4wNmwtMi41NzMgMi41NzNBMS40NTcgMS40NTcgMCAwMTMgMTQuNTQzVjEzSDEuNzVBMS43NSAxLjc1IDAgMDEwIDExLjI1di05LjV6TTkgOWExIDEgMCAxMS0yIDAgMSAxIDAgMDEyIDB6bS0uMjUtNS4yNWEuNzUuNzUgMCAwMC0xLjUgMHYyLjVhLjc1Ljc1IDAgMDAxLjUgMHYtMi41elwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgICBObyByZWNlbnQgcG9zdHNcclxuICAgICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8JSB9ICU+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyKSB7ICU+XHJcbiAgICAgICAgPHNlY3Rpb24+XHJcbiAgICAgICAgICA8aDIgY2xhc3M9XCJmaWVsZFwiPlxyXG4gICAgICAgICAgICA8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDE2IDE2XCIgd2lkdGg9XCIxNlwiIGhlaWdodD1cIjE2XCI+PHBhdGggZmlsbC1ydWxlPVwiZXZlbm9kZFwiIGQ9XCJNNC43NSAwYS43NS43NSAwIDAxLjc1Ljc1VjJoNVYuNzVhLjc1Ljc1IDAgMDExLjUgMFYyaDEuMjVjLjk2NiAwIDEuNzUuNzg0IDEuNzUgMS43NXYxMC41QTEuNzUgMS43NSAwIDAxMTMuMjUgMTZIMi43NUExLjc1IDEuNzUgMCAwMTEgMTQuMjVWMy43NUMxIDIuNzg0IDEuNzg0IDIgMi43NSAySDRWLjc1QS43NS43NSAwIDAxNC43NSAwem0wIDMuNWg4LjVhLjI1LjI1IDAgMDEuMjUuMjVWNmgtMTFWMy43NWEuMjUuMjUgMCAwMS4yNS0uMjVoMnptLTIuMjUgNHY2Ljc1YzAgLjEzOC4xMTIuMjUuMjUuMjVoMTAuNWEuMjUuMjUgMCAwMC4yNS0uMjVWNy41aC0xMXpcIi8+PC9zdmc+XHJcbiAgICAgICAgICAgIENvbnRyaWJ1dGlvbnMgY2FsZW5kYXJcclxuICAgICAgICAgIDwvaDI+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwicm93XCI+XHJcbiAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgIDwlIGlmIChjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyLmVycm9yKSB7ICU+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGQgZXJyb3JcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTQuNDcuMjJBLjc1Ljc1IDAgMDE1IDBoNmEuNzUuNzUgMCAwMS41My4yMmw0LjI1IDQuMjVjLjE0MS4xNC4yMi4zMzEuMjIuNTN2NmEuNzUuNzUgMCAwMS0uMjIuNTNsLTQuMjUgNC4yNUEuNzUuNzUgMCAwMTExIDE2SDVhLjc1Ljc1IDAgMDEtLjUzLS4yMkwuMjIgMTEuNTNBLjc1Ljc1IDAgMDEwIDExVjVhLjc1Ljc1IDAgMDEuMjItLjUzTDQuNDcuMjJ6bS44NCAxLjI4TDEuNSA1LjMxdjUuMzhsMy44MSAzLjgxaDUuMzhsMy44MS0zLjgxVjUuMzFMMTAuNjkgMS41SDUuMzF6TTggNGEuNzUuNzUgMCAwMS43NS43NXYzLjVhLjc1Ljc1IDAgMDEtMS41IDB2LTMuNUEuNzUuNzUgMCAwMTggNHptMCA4YTEgMSAwIDEwMC0yIDEgMSAwIDAwMCAyelwiPjwvcGF0aD48L3N2Zz5cclxuICAgICAgICAgICAgICAgICAgPCU9IGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuZXJyb3IubWVzc2FnZSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIGlmICghY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhci5lcnJvcikgeyAlPlxyXG4gICAgICAgICAgICAgIDxzZWN0aW9uPlxyXG4gICAgICAgICAgICAgICAgPGRpdiBjbGFzcz1cImZpZWxkXCI+XHJcbiAgICAgICAgICAgICAgICAgIDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTYgMTZcIiB3aWR0aD1cIjE2XCIgaGVpZ2h0PVwiMTZcIj48cGF0aCBmaWxsLXJ1bGU9XCJldmVub2RkXCIgZD1cIk03Ljk5OCAxNC41YzIuODMyIDAgNS0xLjk4IDUtNC41IDAtMS40NjMtLjY4LTIuMTktMS44NzktMy4zODNsLS4wMzYtLjAzN2MtMS4wMTMtMS4wMDgtMi4zLTIuMjktMi44MzQtNC40MzQtLjMyMi4yNTYtLjYzLjU3OS0uODY0Ljk1My0uNDMyLjY5Ni0uNjIxIDEuNTgtLjA0NiAyLjczLjQ3My45NDcuNjcgMi4yODQtLjI3OCAzLjIzMi0uNjEuNjEtMS41NDUuODQtMi40MDMuNjMzYTIuNzg4IDIuNzg4IDAgMDEtMS40MzYtLjg3NEEzLjIxIDMuMjEgMCAwMDMgMTBjMCAyLjUzIDIuMTY0IDQuNSA0Ljk5OCA0LjV6TTkuNTMzLjc1M0M5LjQ5Ni4zNCA5LjE2LjAwOSA4Ljc3LjE0NiA3LjAzNS43NSA0LjM0IDMuMTg3IDUuOTk3IDYuNWMuMzQ0LjY4OS4yODUgMS4yMTguMDAzIDEuNS0uNDE5LjQxOS0xLjU0LjQ4Ny0yLjA0LS44MzItLjE3My0uNDU0LS42NTktLjc2Mi0xLjAzNS0uNDU0QzIuMDM2IDcuNDQgMS41IDguNzAyIDEuNSAxMGMwIDMuNTEyIDIuOTk4IDYgNi40OTggNnM2LjUtMi41IDYuNS02YzAtMi4xMzctMS4xMjgtMy4yNi0yLjMxMi00LjQzOC0xLjE5LTEuMTg0LTIuNDM2LTIuNDI1LTIuNjUzLTQuODF6XCIvPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICBDdXJyZW50IHN0cmVhayA8JT0gY29tcHV0ZWQucGx1Z2lucy5pc29jYWxlbmRhci5zdHJlYWsuY3VycmVudCAlPiBkYXk8JT0gcyhjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyLnN0cmVhay5jdXJyZW50KSAlPlxyXG4gICAgICAgICAgICAgICAgPC9kaXY+XHJcbiAgICAgICAgICAgICAgICA8ZGl2IGNsYXNzPVwiZmllbGRcIj5cclxuICAgICAgICAgICAgICAgICAgPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxNiAxNlwiIHdpZHRoPVwiMTZcIiBoZWlnaHQ9XCIxNlwiPjxwYXRoIGZpbGwtcnVsZT1cImV2ZW5vZGRcIiBkPVwiTTEuNSAxLjc1YS43NS43NSAwIDAwLTEuNSAwdjEyLjVjMCAuNDE0LjMzNi43NS43NS43NWgxNC41YS43NS43NSAwIDAwMC0xLjVIMS41VjEuNzV6bTE0LjI4IDIuNTNhLjc1Ljc1IDAgMDAtMS4wNi0xLjA2TDEwIDcuOTQgNy41MyA1LjQ3YS43NS43NSAwIDAwLTEuMDYgMEwzLjIyIDguNzJhLjc1Ljc1IDAgMDAxLjA2IDEuMDZMNyA3LjA2bDIuNDcgMi40N2EuNzUuNzUgMCAwMDEuMDYgMGw1LjI1LTUuMjV6XCI+PC9wYXRoPjwvc3ZnPlxyXG4gICAgICAgICAgICAgICAgICB+IDwlPSBjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyLmF2ZXJhZ2UgJT4gY29tbWl0cyBwZXIgZGF5XHJcbiAgICAgICAgICAgICAgICA8L2Rpdj5cclxuICAgICAgICAgICAgICA8L3NlY3Rpb24+XHJcbiAgICAgICAgICAgIDwlIH0gJT5cclxuICAgICAgICAgIDwvZGl2PlxyXG4gICAgICAgICAgPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuaXNvY2FsZW5kYXIuc3ZnKSB7ICU+XHJcbiAgICAgICAgICAgIDwlLSBjb21wdXRlZC5wbHVnaW5zLmlzb2NhbGVuZGFyLnN2ZyAlPlxyXG4gICAgICAgICAgPCUgfSAlPlxyXG4gICAgICAgIDwvc2VjdGlvbj5cclxuICAgICAgPCUgfSAlPlxyXG5cclxuICAgICAgPCUgaWYgKGJhc2UubWV0YWRhdGEpIHsgJT5cclxuICAgICAgICA8Zm9vdGVyPlxyXG4gICAgICAgICAgPHNwYW4+VGhlc2UgbWV0cmljcyA8JT0gIWNvbXB1dGVkLnRva2VuLnNjb3Blcy5pbmNsdWRlcyhcInJlcG9cIikgPyBcImRvZXMgbm90IGluY2x1ZGVcIiA6IFwiaW5jbHVkZXNcIiAlPiBwcml2YXRlIGNvbnRyaWJ1dGlvbnM8L3NwYW4+XHJcbiAgICAgICAgICA8c3Bhbj5MYXN0IHVwZGF0ZWQgPCU9IG5ldyBEYXRlKCkgJT48L3NwYW4+XHJcbiAgICAgICAgPC9mb290ZXI+XHJcbiAgICAgIDwlIH0gJT5cclxuXHJcbiAgICA8L2Rpdj5cclxuICA8L2ZvcmVpZ25PYmplY3Q+XHJcbjwvc3ZnPiIsInN0eWxlIjoiLyogU1ZHIGdsb2JhbCBjb250ZXh0ICovXHJcbiAgc3ZnIHtcclxuICAgIGZvbnQtZmFtaWx5OiAtYXBwbGUtc3lzdGVtLCBCbGlua01hY1N5c3RlbUZvbnQsIFNlZ29lIFVJLCBIZWx2ZXRpY2EsIEFyaWFsLCBzYW5zLXNlcmlmLCBBcHBsZSBDb2xvciBFbW9qaSwgU2Vnb2UgVUkgRW1vamk7XHJcbiAgICBmb250LXNpemU6IDE0cHg7XHJcbiAgICBjb2xvcjogIzc3Nzc3NztcclxuICB9XHJcblxyXG4vKiBIZWFkZXJzICovXHJcbiAgaDEsIGgyLCBoMyB7XHJcbiAgICBtYXJnaW46IDhweCAwIDJweDtcclxuICAgIHBhZGRpbmc6IDA7XHJcbiAgICBjb2xvcjogIzAzNjZkNjtcclxuICAgIGZvbnQtd2VpZ2h0OiBub3JtYWw7XHJcbiAgfVxyXG4gIGgxIHN2ZywgaDIgc3ZnLCBoMyBzdmcge1xyXG4gICAgZmlsbDogY3VycmVudENvbG9yO1xyXG4gIH1cclxuICBoMSB7XHJcbiAgICBmb250LXNpemU6IDIwcHg7XHJcbiAgICBmb250LXdlaWdodDogYm9sZDtcclxuICB9XHJcbiAgaDIge1xyXG4gICAgZm9udC1zaXplOiAxNnB4O1xyXG4gIH1cclxuICBoMyB7XHJcbiAgICBmb250LXNpemU6IDE0cHg7XHJcbiAgfVxyXG5cclxuLyogRmllbGRzICovXHJcbiAgc2VjdGlvbiA+IC5maWVsZCB7XHJcbiAgICBtYXJnaW4tbGVmdDogNXB4O1xyXG4gICAgbWFyZ2luLXJpZ2h0OiA1cHg7XHJcbiAgfVxyXG4gIC5maWVsZCB7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcclxuICAgIG1hcmdpbi1ib3R0b206IDJweDtcclxuICAgIHdoaXRlLXNwYWNlOiBub3dyYXA7XHJcbiAgfVxyXG4gIC5maWVsZCBzdmcge1xyXG4gICAgbWFyZ2luOiAwIDhweDtcclxuICAgIGZpbGw6ICM5NTlkYTU7XHJcbiAgICBmbGV4LXNocmluazogMDtcclxuICB9XHJcbiAgLmZpZWxkLmVycm9yIHtcclxuICAgIGNvbG9yOiAjY2IyNDMxO1xyXG4gIH1cclxuICAuZmllbGQuZXJyb3Igc3ZnIHtcclxuICAgIGZpbGw6ICNjYjI0MzE7XHJcbiAgfVxyXG5cclxuLyogRGlzcGxheXMgKi9cclxuICAucm93IHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgfVxyXG4gIC5yb3cgc2VjdGlvbiB7XHJcbiAgICBmbGV4OiAxIDEgMDtcclxuICB9XHJcbiAgLmNvbHVtbiB7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgfVxyXG4gIC5jZW50ZXIge1xyXG4gICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgfVxyXG4gIC5ob3Jpem9udGFsIHtcclxuICAgIGp1c3RpZnktY29udGVudDogc3BhY2UtYXJvdW5kO1xyXG4gIH1cclxuICAuaG9yaXpvbnRhbC13cmFwIHtcclxuICAgIGZsZXgtd3JhcDogd3JhcDtcclxuICB9XHJcbiAgLmhvcml6b250YWwgLmZpZWxkIHtcclxuICAgIGZsZXg6IDEgMSAwO1xyXG4gIH1cclxuICAubm8td3JhcCB7XHJcbiAgICB3aGl0ZS1zcGFjZTogbm93cmFwO1xyXG4gIH1cclxuICAuZmlsbC13aWR0aCB7XHJcbiAgICB3aWR0aDogMTAwJTtcclxuICB9XHJcblxyXG4vKiBVc2VyIGF2YXRhciAqL1xyXG4gIC5hdmF0YXIge1xyXG4gICAgYmFja2dyb3VuZC1jb2xvcjogIzAwMDAwMDtcclxuICAgIGJvcmRlci1yYWRpdXM6IDUwJTtcclxuICAgIG1hcmdpbjogMCA2cHg7XHJcbiAgfVxyXG5cclxuLyogQ29tbWl0IGNhbGVuZGFyICovXHJcbiAgLmNhbGVuZGFyLmZpZWxkIHtcclxuICAgIG1hcmdpbjogNHB4IDA7XHJcbiAgICBtYXJnaW4tbGVmdDogN3B4O1xyXG4gIH1cclxuICAuY2FsZW5kYXIgLmRheSB7XHJcbiAgICBvdXRsaW5lOiAxcHggc29saWQgcmdiYSgyNywzMSwzNSwuMDQpO1xyXG4gICAgb3V0bGluZS1vZmZzZXQ6IC0xcHg7XHJcbiAgfVxyXG5cclxuLyogUHJvZ3Jlc3MgYmFycyAqL1xyXG4gIHN2Zy5iYXIge1xyXG4gICAgbWFyZ2luOiA0cHggMDtcclxuICB9XHJcblxyXG4vKiBMYW5ndWFnZSAqL1xyXG4gIC5maWVsZC5sYW5ndWFnZSB7XHJcbiAgICBtYXJnaW46IDAgOHB4O1xyXG4gICAgZmxleC1ncm93OiAwO1xyXG4gIH1cclxuXHJcbiAgLmZpZWxkLmxhbmd1YWdlIHNtYWxsIHtcclxuICAgIG1hcmdpbi1sZWZ0OiA0cHg7XHJcbiAgICBvcGFjaXR5OiAuNztcclxuICB9XHJcblxyXG4vKiBIYWJpdHMgKi9cclxuICAuaGFiaXRzIHtcclxuICAgIG1hcmdpbjogMDtcclxuICAgIGxpc3Qtc3R5bGUtdHlwZTogbm9uZTtcclxuICAgIHBhZGRpbmctbGVmdDogMzdweDtcclxuICB9XHJcblxyXG4vKiBGb290ZXIgKi9cclxuICBmb290ZXIge1xyXG4gICAgbWFyZ2luLXRvcDogOHB4O1xyXG4gICAgZm9udC1zaXplOiAxMHB4O1xyXG4gICAgZm9udC1zdHlsZTogaXRhbGljO1xyXG4gICAgb3BhY2l0eTogMC41O1xyXG4gICAgdGV4dC1hbGlnbjogcmlnaHQ7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAgIGp1c3RpZnktY29udGVudDogZmxleC1lbmQ7XHJcbiAgfVxyXG5cclxuLyogU3BlZWQgdGVzdCBjYXRlZ29yaWVzICovXHJcbiAgLmNhdGVnb3JpZXMge1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWFyb3VuZDtcclxuICAgIG1hcmdpbi10b3A6IDRweDtcclxuICB9XHJcbiAgLmNhdGVnb3JpZSB7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAgZmxleC1kaXJlY3Rpb246IGNvbHVtbjtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICBmbGV4OiAxIDEgMDtcclxuICB9XHJcblxyXG4vKiBHYXVnZXMgKi9cclxuICAuZ2F1Z2Uge1xyXG4gICAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kO1xyXG4gICAgZmlsbDogbm9uZTtcclxuICB9XHJcbiAgLmdhdWdlLmhpZ2gge1xyXG4gICAgY29sb3I6ICMxOGI2NjM7XHJcbiAgfVxyXG4gIC5nYXVnZS5hdmVyYWdlIHtcclxuICAgIGNvbG9yOiAjZmI4YzAwO1xyXG4gIH1cclxuICAuZ2F1Z2UubG93IHtcclxuICAgIGNvbG9yOiAjZTUzOTM1O1xyXG4gIH1cclxuICAuZ2F1Z2UtYmFzZSwgLmdhdWdlLWFyYyB7XHJcbiAgICBzdHJva2U6IGN1cnJlbnRDb2xvcjtcclxuICAgIHN0cm9rZS13aWR0aDogMTA7XHJcbiAgfVxyXG4gIC5nYXVnZS1iYXNlIHtcclxuICAgIHN0cm9rZS1vcGFjaXR5OiAuMjtcclxuICB9XHJcbiAgLmdhdWdlLWFyYyB7XHJcbiAgICBmaWxsOiBub25lO1xyXG4gICAgc3Ryb2tlLWRhc2hvZmZzZXQ6IDA7XHJcbiAgICBhbmltYXRpb24tZGVsYXk6IDI1MG1zO1xyXG4gICAgYW5pbWF0aW9uOiBhbmltYXRpb24tZ2F1Z2UgMXMgZWFzZSBmb3J3YXJkc1xyXG4gIH1cclxuICAuZ2F1Z2UgdGV4dCB7XHJcbiAgICBmaWxsOiBjdXJyZW50Q29sb3I7XHJcbiAgICBmb250LXNpemU6IDQwcHg7XHJcbiAgICBmb250LWZhbWlseTogbW9ub3NwYWNlO1xyXG4gICAgdGV4dC1hbmNob3I6IG1pZGRsZTtcclxuICAgIGZvbnQtd2VpZ2h0OiA2MDA7XHJcbiAgfVxyXG4gIC5nYXVnZSAudGl0bGUge1xyXG4gICAgZm9udC1zaXplOiAxOHB4O1xyXG4gICAgY29sb3I6ICM3Nzc3Nzc7XHJcbiAgfVxyXG4gIEBrZXlmcmFtZXMgYW5pbWF0aW9uLWdhdWdlIHtcclxuICAgIGZyb20ge1xyXG4gICAgICBzdHJva2UtZGFzaGFycmF5OiAwIDMyOTtcclxuICAgIH1cclxuICB9XHJcblxyXG4vKiBNdXNpYyBwbHVnaW4gKi9cclxuICAudHJhY2tsaXN0IHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xyXG4gICAgYWxpZ24taXRlbXM6IGZsZXgtc3RhcnQ7XHJcbiAgICBtYXJnaW4tbGVmdDogMjhweDtcclxuICAgIG1hcmdpbi10b3A6IDRweDtcclxuICAgIHdpZHRoOiAxMDAlO1xyXG4gIH1cclxuICAudHJhY2sge1xyXG4gICAgZGlzcGxheTogZmxleDtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcclxuICAgIG1hcmdpbi1ib3R0b206IDRweDtcclxuICB9XHJcbiAgLnRyYWNrIGltZyB7XHJcbiAgICBtYXJnaW46IDAgMTBweDtcclxuICAgIGJvcmRlci1yYWRpdXM6IDdweDtcclxuICB9XHJcbiAgLnRyYWNrIC5uYW1lIHtcclxuICAgIGZvbnQtc2l6ZTogMTRweDtcclxuICAgIGxpbmUtaGVpZ2h0OiAxNHB4O1xyXG4gIH1cclxuICAudHJhY2sgLmFydGlzdCB7XHJcbiAgICBmb250LXNpemU6IDEycHg7XHJcbiAgICBvcGFjaXR5OiAuNztcclxuICB9XHJcblxyXG4vKiBQb3N0cyBwbHVnaW4gKi9cclxuICAucG9zdCB7XHJcbiAgICBhbGlnbi1pdGVtczogZmxleC1zdGFydDtcclxuICB9XHJcbiAgLnBvc3QgLmluZm9zIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBtYXJnaW4tYm90dG9tOiA0cHg7XHJcbiAgfVxyXG4gIC5wb3N0IC5pbmZvcyAudGl0bGUge1xyXG4gICAgZm9udC1zaXplOiAxNHB4O1xyXG4gICAgd2lkdGg6IDQwMHB4O1xyXG4gICAgd2hpdGUtc3BhY2U6IG5vcm1hbDtcclxuICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICB0ZXh0LW92ZXJmbG93OiBlbGxpcHNpcztcclxuICAgIG1heC1oZWlnaHQ6IDQwcHg7O1xyXG4gIH1cclxuICAucG9zdCAuaW5mb3MgLmRhdGUge1xyXG4gICAgZmxleC1zaHJpbms6IDA7XHJcbiAgICBmb250LXNpemU6IDEycHg7XHJcbiAgICBvcGFjaXR5OiAuNztcclxuICAgIHdpZHRoOiA0MHB4O1xyXG4gICAgcGFkZGluZy10b3A6IDFweDtcclxuICB9XHJcblxyXG4vKiBGYWRlIGFuaW1hdGlvbiAqL1xyXG4gIC5hZiB7XHJcbiAgICBvcGFjaXR5OiAwO1xyXG4gICAgYW5pbWF0aW9uOiBhbmltYXRpb24tZmFkZSAxcyBlYXNlIGZvcndhcmRzO1xyXG4gIH1cclxuICBAa2V5ZnJhbWVzIGFuaW1hdGlvbi1mYWRlIHtcclxuICAgIGZyb20ge1xyXG4gICAgICBvcGFjaXR5OiAwO1xyXG4gICAgfVxyXG4gICAgdG8ge1xyXG4gICAgICBvcGFjaXR5OiAxO1xyXG4gICAgfVxyXG4gIH1cclxuXHJcbi8qIENhbGVuZGFyICovXHJcbiAgOnJvb3Qge1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktYmc6ICNlYmVkZjA7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1ib3JkZXI6IHJnYmEoMjcsMzEsMzUsMC4wNik7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1MMS1iZzogIzliZTlhODtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwyLWJnOiAjNDBjNDYzO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDMtYmc6ICMzMGExNGU7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1MNC1iZzogIzIxNmUzOTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItaGFsbG93ZWVuLWdyYXBoLWRheS1MMS1iZzogI2ZmZWU0YTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItaGFsbG93ZWVuLWdyYXBoLWRheS1MMi1iZzogI2ZmYzUwMTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItaGFsbG93ZWVuLWdyYXBoLWRheS1MMy1iZzogI2ZlOTYwMDtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItaGFsbG93ZWVuLWdyYXBoLWRheS1MNC1iZzogIzAzMDAxYztcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUw0LWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwzLWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwyLWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwxLWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICB9IiwiZm9udHMiOiIifSwidGVybWluYWwiOnsicXVlcnkiOiJxdWVyeSBNZXRyaWNzIHtcclxuICB1c2VyKGxvZ2luOiAkbG9naW4pIHtcclxuICAgIGRhdGFiYXNlSWRcclxuICAgIG5hbWVcclxuICAgIGxvZ2luXHJcbiAgICBjcmVhdGVkQXRcclxuICAgIGF2YXRhclVybFxyXG4gICAgd2Vic2l0ZVVybFxyXG4gICAgZ2lzdHMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICByZXBvc2l0b3JpZXMobGFzdDogJHJlcG9zaXRvcmllcywgaXNGb3JrOiBmYWxzZSwgb3duZXJBZmZpbGlhdGlvbnM6IE9XTkVSKSB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgICAgdG90YWxEaXNrVXNhZ2VcclxuICAgICAgbm9kZXMge1xyXG4gICAgICAgIG5hbWVcclxuICAgICAgICB3YXRjaGVycyB7XHJcbiAgICAgICAgICB0b3RhbENvdW50XHJcbiAgICAgICAgfVxyXG4gICAgICAgIHN0YXJnYXplcnMge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBsYW5ndWFnZXMoZmlyc3Q6IDQpIHtcclxuICAgICAgICAgIGVkZ2VzIHtcclxuICAgICAgICAgICAgc2l6ZVxyXG4gICAgICAgICAgICBub2RlIHtcclxuICAgICAgICAgICAgICBjb2xvclxyXG4gICAgICAgICAgICAgIG5hbWVcclxuICAgICAgICAgICAgfVxyXG4gICAgICAgICAgfVxyXG4gICAgICAgIH1cclxuICAgICAgICBpc3N1ZXNfb3BlbjogaXNzdWVzKHN0YXRlczogT1BFTikge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBpc3N1ZXNfY2xvc2VkOiBpc3N1ZXMoc3RhdGVzOiBDTE9TRUQpIHtcclxuICAgICAgICAgIHRvdGFsQ291bnRcclxuICAgICAgICB9XHJcbiAgICAgICAgcHJfb3BlbjogcHVsbFJlcXVlc3RzKHN0YXRlczogT1BFTikge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBwcl9tZXJnZWQ6IHB1bGxSZXF1ZXN0cyhzdGF0ZXM6IE1FUkdFRCkge1xyXG4gICAgICAgICAgdG90YWxDb3VudFxyXG4gICAgICAgIH1cclxuICAgICAgICBmb3JrQ291bnRcclxuICAgICAgICBsaWNlbnNlSW5mbyB7XHJcbiAgICAgICAgICBzcGR4SWRcclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIHBhY2thZ2VzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3RhcnJlZFJlcG9zaXRvcmllcyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICAgIHdhdGNoaW5nIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3BvbnNvcnNoaXBzQXNTcG9uc29yIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgc3BvbnNvcnNoaXBzQXNNYWludGFpbmVyIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgY29udHJpYnV0aW9uc0NvbGxlY3Rpb24ge1xyXG4gICAgICB0b3RhbFJlcG9zaXRvcmllc1dpdGhDb250cmlidXRlZENvbW1pdHNcclxuICAgICAgdG90YWxDb21taXRDb250cmlidXRpb25zXHJcbiAgICAgIHJlc3RyaWN0ZWRDb250cmlidXRpb25zQ291bnRcclxuICAgICAgdG90YWxJc3N1ZUNvbnRyaWJ1dGlvbnNcclxuICAgICAgdG90YWxQdWxsUmVxdWVzdENvbnRyaWJ1dGlvbnNcclxuICAgICAgdG90YWxQdWxsUmVxdWVzdFJldmlld0NvbnRyaWJ1dGlvbnNcclxuICAgIH1cclxuICAgIGNhbGVuZGFyOmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uKGZyb206ICRjYWxlbmRhci5mcm9tLCB0bzogJGNhbGVuZGFyLnRvKSB7XHJcbiAgICAgIGNvbnRyaWJ1dGlvbkNhbGVuZGFyIHtcclxuICAgICAgICB3ZWVrcyB7XHJcbiAgICAgICAgICBjb250cmlidXRpb25EYXlzIHtcclxuICAgICAgICAgICAgY29sb3JcclxuICAgICAgICAgIH1cclxuICAgICAgICB9XHJcbiAgICAgIH1cclxuICAgIH1cclxuICAgIHJlcG9zaXRvcmllc0NvbnRyaWJ1dGVkVG8ge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBmb2xsb3dlcnMge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBmb2xsb3dpbmcge1xyXG4gICAgICB0b3RhbENvdW50XHJcbiAgICB9XHJcbiAgICBpc3N1ZUNvbW1lbnRzIHtcclxuICAgICAgdG90YWxDb3VudFxyXG4gICAgfVxyXG4gICAgb3JnYW5pemF0aW9ucyB7XHJcbiAgICAgIHRvdGFsQ291bnRcclxuICAgIH1cclxuICB9XHJcbn1cclxuIiwiaW1hZ2UiOiI8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB3aWR0aD1cIjQ4MFwiIGhlaWdodD1cIjwlPSA0OFxyXG4gICsgKCEhYmFzZS5oZWFkZXIpKjYyXHJcbiAgKyAoISFiYXNlLm1ldGFkYXRhKSoxMDhcclxuICArICghIWJhc2UuYWN0aXZpdHkpKjEwOFxyXG4gICsgKCEhYmFzZS5jb21tdW5pdHkpKjk0XHJcbiAgKyAoISFiYXNlLnJlcG9zaXRvcmllcykqMTQyXHJcbiAgKyAoKCEhYmFzZS5yZXBvc2l0b3JpZXMpKighIWNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYykpKjE4XHJcbiAgKyAoKCEhYmFzZS5yZXBvc2l0b3JpZXMpKighIWNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXApKSoxMDJcclxuICArICgoISFiYXNlLnJlcG9zaXRvcmllcykqKCEhY29tcHV0ZWQucGx1Z2lucy5saW5lcykpKjM0XHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkqMTEwXHJcbiAgKyAoISFjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcykqMTI0XHJcbiAgKyBNYXRoLm1heCgwLCAoKCghIWJhc2UubWV0YWRhdGEpKyghIWJhc2UuaGVhZGVyKSsoKCEhYmFzZS5hY3Rpdml0eSl8fCghIWJhc2UuY29tbXVuaXR5KSkrKCEhYmFzZS5yZXBvc2l0b3JpZXMpKyghIWNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkKSsoISFjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcykpLTEpKSoyMFxyXG4lPlwiPlxyXG4gIDwlXHJcbiAgICBtZXRhLiQgPSBgPHNwYW4gY2xhc3M9XCJwczEtcGF0aFwiPiR7YCR7dXNlci5sb2dpbn1gLnRvTG9jYWxlTG93ZXJDYXNlKCl9QG1ldHJpY3M8L3NwYW4+OjxzcGFuIGNsYXNzPVwicHMxLWxvY2F0aW9uXCI+fjwvc3Bhbj4ke2NvbXB1dGVkLnRva2VuLnNjb3Blcy5pbmNsdWRlcyhcInJlcG9cIikgPyBcIiNcIiA6IFwiJFwifWBcclxuICAgIG1ldGEuYW5pbWF0aW9ucyA9ICFtZXRhLnBsYWNlaG9sZGVyID8ge3N0ZGluOi4xNiwgc3Rkb3V0Oi4yOCwgbGVuZ3RoOigyK09iamVjdC5rZXlzKGJhc2UpLmxlbmd0aCtPYmplY3Qua2V5cyhjb21wdXRlZC5wbHVnaW5zKS5sZW5ndGgpfSA6IHtzdGRpbjowLCBzdGRvdXQ6MCwgbGVuZ3RoOjB9XHJcbiAgJT5cclxuXHJcbiAgPGRlZnM+PHN0eWxlPjwlPSBmb250cyAlPjwvc3R5bGU+PC9kZWZzPlxyXG5cclxuICA8c3R5bGU+XHJcbiAgICA8JT0gc3R5bGUgJT5cclxuICAgICAgLnN0ZGluLCAuc3Rkb3V0IHtcclxuICAgICAgICBhbmltYXRpb24tZHVyYXRpb246IDwlPSBtZXRhLmFuaW1hdGlvbnMuc3RkaW4gJT5zO1xyXG4gICAgICB9XHJcbiAgICAgIC5zdGRvdXQge1xyXG4gICAgICAgIGFuaW1hdGlvbi1kdXJhdGlvbjogPCU9IG1ldGEuYW5pbWF0aW9ucy5zdGRvdXQgJT5zO1xyXG4gICAgICB9XHJcbiAgICAgIDwlIGZvciAobGV0IGkgPSAwLCBkID0gMDsgaSA8IG1ldGEuYW5pbWF0aW9ucy5sZW5ndGg7IGkrKywgZCs9bWV0YS5hbmltYXRpb25zLnN0ZGluK21ldGEuYW5pbWF0aW9ucy5zdGRvdXQpIHsgJT5cclxuICAgICAgICAuc3RkaW46bnRoLW9mLXR5cGUoPCU9IGkrMSAlPikge1xyXG4gICAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiA8JT0gZCAlPnM7XHJcbiAgICAgICAgfVxyXG4gICAgICAgIC5zdGRvdXQ6bnRoLW9mLXR5cGUoPCU9IGkrMiAlPikge1xyXG4gICAgICAgICAgYW5pbWF0aW9uLWRlbGF5OiA8JT0gZCttZXRhLmFuaW1hdGlvbnMuc3RkaW4gJT5zO1xyXG4gICAgICAgIH1cclxuICAgICAgICA8JSBpZiAoaSA9PT0gbWV0YS5hbmltYXRpb25zLmxlbmd0aC0xKSB7ICU+XHJcbiAgICAgICAgICBmb290ZXIge1xyXG4gICAgICAgICAgICBhbmltYXRpb24tZGVsYXk6IDwlPSBkICU+cztcclxuICAgICAgICAgIH1cclxuICAgICAgICA8JSB9ICU+XHJcbiAgICAgIDwlIH0gJT5cclxuICA8L3N0eWxlPlxyXG5cclxuICA8Zm9yZWlnbk9iamVjdCB4PVwiMFwiIHk9XCIwXCIgd2lkdGg9XCIxMDAlXCIgaGVpZ2h0PVwiMTAwJVwiPlxyXG4gICAgPGRpdiB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGh0bWxcIiB4bWxuczp4bGluaz1cImh0dHA6Ly93d3cudzMub3JnLzE5OTkveGxpbmtcIj5cclxuXHJcbiAgICAgIDxkaXYgY2xhc3M9XCJoZWFkZXJcIj5cclxuICAgICAgICA8c3BhbiBjbGFzcz1cInRpdGxlXCI+PC9zcGFuPlxyXG4gICAgICAgIDxkaXYgY2xhc3M9XCJidXR0b25zXCI+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwiYnV0dG9uXCI+4pSAPC9kaXY+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwiYnV0dG9uXCI+4pahPC9kaXY+XHJcbiAgICAgICAgICA8ZGl2IGNsYXNzPVwiYnV0dG9uIGV4aXRcIj7inJU8L2Rpdj5cclxuICAgICAgICA8L2Rpdj5cclxuICAgICAgPC9kaXY+XHJcblxyXG48cHJlPjwlIyAtJT5cclxuPCUgaWYgKGJhc2UubWV0YWRhdGEpIHsgJT5cclxuPGRpdiBjbGFzcz1cImJhbm5lclwiPjwlIyAtJT5cclxuR2l0SHViIG1ldHJpY3MgZ2VuZXJhdG9yIDwlPSBtZXRhLnZlcnNpb24gJT5cclxuVGhlc2UgZ2VuZXJhdGVkIG1ldHJpY3MgY29tZXMgd2l0aCBBQlNPTFVURUxZIE5PXHJcbldBUlJBTlRZLCB0byB0aGUgZXh0ZW50IHBlcm1pdHRlZCBieSBhcHBsaWNhYmxlIGxhdy5cclxuXHJcbkxhc3QgZ2VuZXJhdGVkOiA8JT0gbmV3IERhdGUoKS50b0dNVFN0cmluZygpICU+XHJcbjwvZGl2PjwlIH0gLSU+XHJcbjwlIyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09IC0lPlxyXG48JSBpZiAoYmFzZS5oZWFkZXIpIHsgJT5cclxuPGRpdiBjbGFzcz1cInN0ZGluXCI+PCUtIG1ldGEuJCAlPiB3aG9hbWk8L2Rpdj48JSMgLSU+XHJcbjxkaXYgY2xhc3M9XCJzdGRvdXRcIj48JSMgLSU+XHJcbjxiPjwlPSB1c2VyLm5hbWUgfHwgdXNlci5sb2dpbiAlPjwvYj4gcmVnaXN0ZXJlZD08JT0gY29tcHV0ZWQucmVnaXN0cmF0aW9uLm1hdGNoKC9eLis/IFt5bV0vKVswXS5yZXBsYWNlKC8gL2csIFwiXCIpICU+LCB1aWQ9PCU9IGAke3VzZXIuZGF0YWJhc2VJZH1gLnN1YnN0cigtNCkgJT4sIGdpZD08JT0gdXNlci5vcmdhbml6YXRpb25zLnRvdGFsQ291bnQgJT5cclxuICBjb250cmlidXRlZCB0byA8JT0gdXNlci5yZXBvc2l0b3JpZXNDb250cmlidXRlZFRvLnRvdGFsQ291bnQgJT4gcmVwb3NpdG9yPCU9IHModXNlci5yZXBvc2l0b3JpZXNDb250cmlidXRlZFRvLnRvdGFsQ291bnQsIFwieVwiKSAlPiA8Yj48JSBmb3IgKGNvbnN0IFt4LCB7Y29sb3J9XSBvZiBPYmplY3QuZW50cmllcyhjb21wdXRlZC5jYWxlbmRhcikpIHsgLSU+PHNwYW4gc3R5bGU9XCJjb2xvcjo8JT0gY29sb3IgJT5cIj4jPC9zcGFuPjwlIH0gJT48L2I+XHJcbiAgZm9sbG93ZWQgYnkgPGI+PCU9IHVzZXIuZm9sbG93ZXJzLnRvdGFsQ291bnQgJT48L2I+IHVzZXI8JT0gcyh1c2VyLmZvbGxvd2Vycy50b3RhbENvdW50KSAlPlxyXG48L2Rpdj48JSB9IC0lPlxyXG48JSMgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSAtJT5cclxuPCUgaWYgKChiYXNlLmFjdGl2aXR5KXx8KGJhc2UuY29tbXVuaXR5KSkgeyAlPlxyXG48ZGl2IGNsYXNzPVwic3RkaW5cIj48JS0gbWV0YS4kICU+IGdpdCBzdGF0dXM8L2Rpdj48JSMgLSU+XHJcbjxkaXYgY2xhc3M9XCJzdGRvdXRcIj48JSMgLSU+XHJcbjwlIGlmIChiYXNlLmFjdGl2aXR5KSB7IC0lPlxyXG48Yj5SZWNlbnQgYWN0aXZpdHk8L2I+XHJcbiAgPGI+PCU9IGAke2NvbXB1dGVkLmNvbW1pdHN9YC5wYWRTdGFydCg1KSAlPjwvYj4gY29tbWl0PCU9IHMoY29tcHV0ZWQuY29tbWl0cykgJT5cclxuICA8Yj48JT0gYCR7dXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbFB1bGxSZXF1ZXN0UmV2aWV3Q29udHJpYnV0aW9uc31gLnBhZFN0YXJ0KDUpICU+PC9iPiBwdWxsIHJlcXVlc3Q8JT0gcyh1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsUHVsbFJlcXVlc3RSZXZpZXdDb250cmlidXRpb25zKSAlPiByZXZpZXdlZFxyXG4gIDxiPjwlPSBgJHt1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsUHVsbFJlcXVlc3RDb250cmlidXRpb25zfWAucGFkU3RhcnQoNSkgJT48L2I+IHB1bGwgcmVxdWVzdDwlPSBzKHVzZXIuY29udHJpYnV0aW9uc0NvbGxlY3Rpb24udG90YWxQdWxsUmVxdWVzdENvbnRyaWJ1dGlvbnMpICU+IG9wZW5lZFxyXG4gIDxiPjwlPSBgJHt1c2VyLmNvbnRyaWJ1dGlvbnNDb2xsZWN0aW9uLnRvdGFsSXNzdWVDb250cmlidXRpb25zfWAucGFkU3RhcnQoNSkgJT48L2I+IGlzc3VlPCU9IHModXNlci5jb250cmlidXRpb25zQ29sbGVjdGlvbi50b3RhbElzc3VlQ29udHJpYnV0aW9ucykgJT4gb3BlbmVkXHJcbiAgPGI+PCU9IGAke3VzZXIuaXNzdWVDb21tZW50cy50b3RhbENvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+IGlzc3VlIGNvbW1lbnQ8JT0gcyh1c2VyLmlzc3VlQ29tbWVudHMudG90YWxDb3VudCkgJT5cclxuPCUgfSAtJT5cclxuPCUgaWYgKChiYXNlLmFjdGl2aXR5KSYmKGJhc2UuY29tbXVuaXR5KSkgeyAtJT5cclxuXHJcbjwlIH0gLSU+XHJcbjwlIGlmIChiYXNlLmNvbW11bml0eSkgeyAtJT5cclxuPGI+VHJhY2tlZCBhY3Rpdml0eTwvYj5cclxuICA8Yj48JT0gYCR7dXNlci5mb2xsb3dpbmcudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiB1c2VyPCU9IHModXNlci5mb2xsb3dlcnMudG90YWxDb3VudCkgJT4gZm9sbG93ZWRcclxuICA8Yj48JT0gYCR7Y29tcHV0ZWQuc3BvbnNvcnNoaXBzfWAucGFkU3RhcnQoNSkgJT48L2I+IHJlcG9zaXRvcjwlPSBzKGNvbXB1dGVkLnNwb25zb3JzaGlwcywgXCJ5XCIpICU+IHNwb25zb3JlZFxyXG4gIDxiPjwlPSBgJHt1c2VyLnN0YXJyZWRSZXBvc2l0b3JpZXMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiByZXBvc2l0b3I8JT0gcyh1c2VyLnN0YXJyZWRSZXBvc2l0b3JpZXMudG90YWxDb3VudCwgXCJ5XCIpICU+IHN0YXJyZWRcclxuICA8Yj48JT0gYCR7dXNlci53YXRjaGluZy50b3RhbENvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+IHJlcG9zaXRvcjwlPSBzKHVzZXIud2F0Y2hpbmcudG90YWxDb3VudCwgXCJ5XCIpICU+IHdhdGNoZWRcclxuPCUgfSAtJT5cclxuPC9kaXY+PCUgfSAtJT5cclxuPCUjID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0gLSU+XHJcbjwlIGlmIChiYXNlLnJlcG9zaXRvcmllcykgeyAlPlxyXG48ZGl2IGNsYXNzPVwic3RkaW5cIj48JS0gbWV0YS4kICU+IGxzIC1saCBnaXRodWIvcmVwb3NpdG9yaWVzPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG5Ub3RhbCA8JT0gdXNlci5yZXBvc2l0b3JpZXMudG90YWxDb3VudCAlPiByZXBvc2l0b3I8JT0gcyh1c2VyLnJlcG9zaXRvcmllcy50b3RhbENvdW50LCBcInlcIikgJT4gLSA8JT0gY29tcHV0ZWQuZGlza1VzYWdlICU+XHJcbjwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMpIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMudHJhZmZpYy5lcnJvcikgeyAtJT5cclxuLS0tLSAgPGI+ICAgICA8L2I+ICB2aWV3cyA8c3BhbiBjbGFzcz1cImVycm9yXCI+KDwlPSBjb21wdXRlZC5wbHVnaW5zLnRyYWZmaWMuZXJyb3IubWVzc2FnZSAlPik8L3NwYW4+XHJcbjwlIH0gZWxzZSB7IC0lPlxyXG4tci0tICA8Yj48JT0gYCR7Y29tcHV0ZWQucGx1Z2lucy50cmFmZmljLnZpZXdzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICB2aWV3c1xyXG48JSB9fSAtJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy5zdGFyZ2F6ZXJzfWAucGFkU3RhcnQoNSkgJT48L2I+ICBzdGFyZ2F6ZXI8JT0gcyhjb21wdXRlZC5yZXBvc2l0b3JpZXMuc3RhcmdhemVycykgJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy5mb3Jrc31gLnBhZFN0YXJ0KDUpICU+PC9iPiAgZm9yazwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy5mb3JrcykgJT5cclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnJlcG9zaXRvcmllcy53YXRjaGVyc31gLnBhZFN0YXJ0KDUpICU+PC9iPiAgd2F0Y2hlcjwlPSBzKGNvbXB1dGVkLnJlcG9zaXRvcmllcy53YXRjaGVycykgJT5cclxuZHIteCAgPGI+PCU9IGAke3VzZXIucGFja2FnZXMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAgcGFja2FnZTwlPSBzKHVzZXIucGFja2FnZXMudG90YWxDb3VudCkgJT5cclxuZHIteCAgPGI+PCU9IGAke3VzZXIuZ2lzdHMudG90YWxDb3VudH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAgZ2lzdDwlPSBzKHVzZXIuZ2lzdHMudG90YWxDb3VudCkgJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXApIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IpIHsgLSU+XHJcbmQtLS0gIDxiPiAgICAgPC9iPiAgSVNTVUVTIDxzcGFuIGNsYXNzPVwiZXJyb3JcIj4oPCU9IGNvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuZXJyb3IubWVzc2FnZSAlPik8L3NwYW4+XHJcbmQtLS0gIDxiPiAgICAgPC9iPiAgUFVMTF9SRVFVRVNUUyA8c3BhbiBjbGFzcz1cImVycm9yXCI+KDwlPSBjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmVycm9yLm1lc3NhZ2UgJT4pPC9zcGFuPlxyXG48JSB9IGVsc2UgeyAtJT5cclxuZHIteCAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICBJU1NVRVNcclxuLXItLSAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLm9wZW59YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUnOKUgOKUgCBvcGVuXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLmlzc3Vlcy5jbG9zZWR9YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUlOKUgOKUgCBjbG9zZWRcclxuZHIteCAgPGI+PCU9IGAke2NvbXB1dGVkLnBsdWdpbnMuZm9sbG93dXAuaXNzdWVzLmNvdW50fWAucGFkU3RhcnQoNSkgJT48L2I+ICBQVUxMX1JFUVVFU1RTXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm9wZW59YC5wYWRTdGFydCg1KSAlPjwvYj4gIOKUnOKUgOKUgCBvcGVuXHJcbi1yLS0gIDxiPjwlPSBgJHtjb21wdXRlZC5wbHVnaW5zLmZvbGxvd3VwLnByLm1lcmdlZH1gLnBhZFN0YXJ0KDUpICU+PC9iPiAg4pSU4pSA4pSAIG1lcmdlZFxyXG48JSB9fSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLmxpY2Vuc2VzLmZhdm9yaXRlLmxlbmd0aCkgeyAtJT5cclxuZHIteCAgICAgICAgIExJQ0VOU0VcclxuLXItLSAgICAgICAgIOKUlOKUgOKUgCA8JT0gY29tcHV0ZWQubGljZW5zZXMuZmF2b3JpdGUgJT5cclxuPCUgfSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMpIHsgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IpIHsgJT5cclxuPHNwYW4gY2xhc3M9XCJkaWZmIGVycm9yXCI+QEAgPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZXJyb3IubWVzc2FnZSAlPiBAQDwvc3Bhbj48JSB9IGVsc2UgeyAlPlxyXG48c3BhbiBjbGFzcz1cImRpZmZcIj5AQCAtPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuZGVsZXRlZCAlPiArPCU9IGNvbXB1dGVkLnBsdWdpbnMubGluZXMuYWRkZWQgJT4gQEA8L3NwYW4+XHJcbjwlIH19IC0lPlxyXG48L2Rpdj48JSB9IC0lPlxyXG48JSMgPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PSAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMubGFuZ3VhZ2VzKSB7ICU+XHJcbjxkaXYgY2xhc3M9XCJzdGRpblwiPjwlLSBtZXRhLiQgJT4gbG9jYWxlPC9kaXY+PCUjIC0lPlxyXG48ZGl2IGNsYXNzPVwic3Rkb3V0XCI+PCUjIC0lPlxyXG48JSBpZiAoY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IpIHsgLSU+XHJcbjxzcGFuIGNsYXNzPVwiZXJyb3JcIj48JT0gY29tcHV0ZWQucGx1Z2lucy5sYW5ndWFnZXMuZXJyb3IubWVzc2FnZSAlPjwvc3Bhbj48JSMgLSU+XHJcbjwlIH0gZWxzZSB7IGZvciAoY29uc3Qge25hbWUsIHZhbHVlfSBvZiBjb21wdXRlZC5wbHVnaW5zLmxhbmd1YWdlcy5mYXZvcml0ZXMpIHsgLSU+XHJcbjxiPjwlPSBuYW1lLnRvTG9jYWxlVXBwZXJDYXNlKCkucGFkRW5kKDEyKSAlPjwvYj4gWzwlPSBcIiNcIi5yZXBlYXQoTWF0aC5jZWlsKDEwMCp2YWx1ZS81KSkucGFkRW5kKDIwKSAlPl0gPCU9ICgxMDAqdmFsdWUpLnRvRml4ZWQoMikucGFkRW5kKDUpICU+JVxyXG48JSB9fSAtJT5cclxuPC9kaXY+PCUgfSAtJT5cclxuPCUjID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0gLSU+XHJcbjwlIGlmIChjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZCkgeyAlPlxyXG48ZGl2IGNsYXNzPVwic3RkaW5cIj48JS0gbWV0YS4kICU+IGN1cmwgLUkgPCU9IHVzZXIud2Vic2l0ZVVybCAlPjwvZGl2PjwlIyAtJT5cclxuPGRpdiBjbGFzcz1cInN0ZG91dFwiPjwlIyAtJT5cclxuPCUgaWYgKGNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkLmVycm9yKSB7IC0lPlxyXG48c3BhbiBjbGFzcz1cImVycm9yXCI+PCU9IGNvbXB1dGVkLnBsdWdpbnMucGFnZXNwZWVkLmVycm9yLm1lc3NhZ2UgJT48L3NwYW4+PCUgfSBlbHNlIHsgLSU+XHJcbjxiPlVzZXItQWdlbnQ8L2I+OiBHb29nbGUgUGFnZVNwZWVkIEFQSVxyXG48Yj5Mb2NhdGlvbjwvYj46IDwlPSB1c2VyLndlYnNpdGVVcmwgJT5cclxuPCUgZm9yIChjb25zdCB7c2NvcmUsIHRpdGxlfSBvZiBjb21wdXRlZC5wbHVnaW5zLnBhZ2VzcGVlZC5zY29yZXMpIHsgLSU+XHJcbjxiPjwlPSBgWC0ke3RpdGxlLnJlcGxhY2UoLyAvZywgXCItXCIpfWAgJT48L2I+OiA8JT0gIU51bWJlci5pc05hTihzY29yZSkgPyBNYXRoLnJvdW5kKHNjb3JlKjEwMCkgOiBcIi1cIiAlPiVcclxuPCUgfX0gLSU+XHJcbjwvZGl2PjwlIH0gLSU+XHJcbjwlIyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09IC0lPlxyXG48JSBpZiAoYmFzZS5tZXRhZGF0YSkgeyAtJT5cclxuXHJcbjxmb290ZXI+Q29ubmVjdGlvbiByZXNldCBieSA8JT0gTWF0aC5mbG9vcigyNTYqTWF0aC5yYW5kb20oKSkgJT4uPCU9IE1hdGguZmxvb3IoMjU2Kk1hdGgucmFuZG9tKCkpICU+LjwlPSBNYXRoLmZsb29yKDI1NipNYXRoLnJhbmRvbSgpKSAlPi48JT0gTWF0aC5mbG9vcigyNTYqTWF0aC5yYW5kb20oKSkgJT48L2Zvb3Rlcj48JSMgLSU+XHJcbjwlIH0gLSU+PC9wcmU+XHJcblxyXG4gICAgPC9kaXY+XHJcbiAgPC9mb3JlaWduT2JqZWN0PlxyXG48L3N2Zz5cclxuXHJcbiIsInN0eWxlIjoiLyogU1ZHIGdsb2JhbCBjb250ZXh0ICovXHJcbiAgc3ZnIHtcclxuICAgIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgICBmb250LXNpemU6IDE0cHg7XHJcbiAgICBjb2xvcjogIzc3Nzc3NztcclxuICB9XHJcblxyXG4vKiBUaXRsZSBiYXIgKi9cclxuICAuaGVhZGVyIHtcclxuICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcclxuICAgIHRvcDogMDtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47XHJcbiAgICB3aWR0aDogMTAwJTtcclxuICAgIGhlaWdodDogMjBweDtcclxuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XHJcbiAgICBwYWRkaW5nOiAwIDhweDtcclxuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XHJcbiAgICBib3JkZXItdG9wLWxlZnQtcmFkaXVzOiA1cHg7XHJcbiAgICBib3JkZXItdG9wLXJpZ2h0LXJhZGl1czogNXB4O1xyXG4gICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KCM1MDRiNDUgMCUsIzNjM2IzNyAxMDAlKTtcclxuICB9XHJcblxyXG4gIC50aXRsZSB7XHJcbiAgICBjb2xvcjogI2Q1ZDBjZTtcclxuICAgIGZvbnQtc2l6ZTogMTZweDtcclxuICB9XHJcblxyXG4gIC5idXR0b25zIHtcclxuICAgIGRpc3BsYXk6IGZsZXg7XHJcbiAgICBhbGlnbi1pdGVtczogY2VudGVyO1xyXG4gIH1cclxuXHJcbiAgLmJ1dHRvbiB7XHJcbiAgICBjb2xvcjogYmxhY2s7XHJcbiAgICBkaXNwbGF5OiBmbGV4O1xyXG4gICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XHJcbiAgICBtYXJnaW4tcmlnaHQ6IDVweDtcclxuICAgIGZvbnQtc2l6ZTogOHB4O1xyXG4gICAgaGVpZ2h0OiAxMnB4O1xyXG4gICAgd2lkdGg6IDEycHg7XHJcbiAgICBib3JkZXItcmFkaXVzOiAxMDAlO1xyXG4gICAgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KCM3ZDc4NzEgMCUsICM1OTU5NTMgMTAwJSk7XHJcbiAgICB0ZXh0LXNoYWRvdzogMHB4IDFweCAwcHggcmdiYSgyNTUsMjU1LDI1NSwwLjIpO1xyXG4gIH1cclxuXHJcbiAgLmJ1dHRvbi5leGl0IHtcclxuICAgIGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCgjZjM3NDU4IDAlLCAjZGU0YzEyIDEwMCUpO1xyXG4gIH1cclxuXHJcbi8qIFRlcm1pbmFsICovXHJcbiAgcHJlLCAuYmFubmVyLCBmb290ZXIge1xyXG4gICAgbWFyZ2luOiAwO1xyXG4gICAgZm9udC1mYW1pbHk6ICdDb3VyaWVyIFByaW1lJztcclxuICAgIGNvbG9yOiAjREREREREO1xyXG4gIH1cclxuICBwcmUge1xyXG4gICAgYmFja2dyb3VuZDogIzQyMDkyQjtcclxuICAgIHBhZGRpbmc6IDEycHg7XHJcbiAgICBib3JkZXItcmFkaXVzOiA1cHg7XHJcbiAgfVxyXG4gIC5iYW5uZXIsIGZvb3RlciB7XHJcbiAgICBjb2xvcjogI0FFOURBNztcclxuICB9XHJcblxyXG4vKiBQcm9tcHQgKi9cclxuICAucHMxLXBhdGgge1xyXG4gICAgY29sb3I6ICM3RURBMjk7XHJcbiAgfVxyXG5cclxuICAucHMxLWxvY2F0aW9uIHtcclxuICAgIGNvbG9yOiAjNDg3OGMwO1xyXG4gIH1cclxuXHJcbi8qIERpZmYgKi9cclxuICAuZGlmZiB7XHJcbiAgICBjb2xvcjogIzNBOTZERDtcclxuICB9XHJcblxyXG4vKiBFcnJvciAqL1xyXG4gIC5lcnJvciB7XHJcbiAgICBjb2xvcjogI2NiMjQzMTtcclxuICB9XHJcblxyXG4vKiBBbmltYXRpb25zICovXHJcbiAgLnN0ZGluLCBmb290ZXIge1xyXG4gICAgd2lkdGg6IDAlO1xyXG4gICAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcclxuICAgIG92ZXJmbG93OiBoaWRkZW47XHJcbiAgICBhbmltYXRpb24tbmFtZTogc3RkaW4tYW5pbWF0aW9uO1xyXG4gICAgYW5pbWF0aW9uLWZpbGwtbW9kZTogYm90aDtcclxuICB9XHJcblxyXG4gIC5zdGRvdXQge1xyXG4gICAgbWF4LWhlaWdodDogMCU7XHJcbiAgICBvdmVyZmxvdzogaGlkZGVuO1xyXG4gICAgYW5pbWF0aW9uLW5hbWU6IHN0ZG91dC1hbmltYXRpb247XHJcbiAgICBhbmltYXRpb24tZmlsbC1tb2RlOiBib3RoO1xyXG4gIH1cclxuXHJcbiAgQGtleWZyYW1lcyBzdGRpbi1hbmltYXRpb24ge1xyXG4gICAgMCUgeyB3aWR0aDogMCU7IH1cclxuICAgIDEwMCUgeyB3aWR0aDogMTAwJTsgfVxyXG4gIH1cclxuXHJcbiAgQGtleWZyYW1lcyBzdGRvdXQtYW5pbWF0aW9uIHtcclxuICAgIDAlIHsgbWF4LWhlaWdodDogMDsgfVxyXG4gICAgMTAwJSB7IG1heC1oZWlnaHQ6IDM2MHB4OyB9XHJcbiAgfVxyXG5cclxuLyogQ2FsZW5kYXIgKi9cclxuICA6cm9vdCB7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1iZzogI2ViZWRmMDtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LWJvcmRlcjogcmdiYSgyNywzMSwzNSwwLjA2KTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUwxLWJnOiAjOWJlOWE4O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYmc6ICM0MGM0NjM7XHJcbiAgICAtLWNvbG9yLWNhbGVuZGFyLWdyYXBoLWRheS1MMy1iZzogIzMwYTE0ZTtcclxuICAgIC0tY29sb3ItY2FsZW5kYXItZ3JhcGgtZGF5LUw0LWJnOiAjMjE2ZTM5O1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwxLWJnOiAjZmZlZTRhO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwyLWJnOiAjZmZjNTAxO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUwzLWJnOiAjZmU5NjAwO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1oYWxsb3dlZW4tZ3JhcGgtZGF5LUw0LWJnOiAjMDMwMDFjO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDQtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDMtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDItYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gICAgLS1jb2xvci1jYWxlbmRhci1ncmFwaC1kYXktTDEtYm9yZGVyOiByZ2JhKDI3LDMxLDM1LDAuMDYpO1xyXG4gIH0iLCJmb250cyI6IkBmb250LWZhY2Uge1xyXG4gIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgc3JjOiB1cmwoJ2RhdGE6YXBwbGljYXRpb24vZm9udC13b2ZmO2NoYXJzZXQ9dXRmLTg7YmFzZTY0LGQwOUdSZ0FCQUFBQUFEK2tBQklBQUFBQWNiQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFCR1JsUk5BQUEvaUFBQUFCd0FBQUFjaVR2ME1VZEVSVVlBQUQ2MEFBQUFLQUFBQUNvQS93RTFSMUJQVXdBQVAxUUFBQUF5QUFBQVFCYWJLSmhIVTFWQ0FBQSszQUFBQUhnQUFBQ2laNGR5eFU5VEx6SUFBQUlNQUFBQVR3QUFBR0J3MW8vV1kyMWhjQUFBQXlBQUFBQ3VBQUFCVXNSdFd5SmpkblFnQUFBTGFBQUFBRU1BQUFCc0p1RVFoV1p3WjIwQUFBUFFBQUFHOGdBQURoV2VOaFBPWjJGemNBQUFQcXdBQUFBSUFBQUFDQUFBQUJCbmJIbG1BQUFNZ0FBQUwzd0FBRmRRZytIRXJtaGxZV1FBQUFHVUFBQUFOZ0FBQURZWG1ScXNhR2hsWVFBQUFjd0FBQUFnQUFBQUpBc1BBZmxvYlhSNEFBQUNYQUFBQU1FQUFBRFlMM1FkdzJ4dlkyRUFBQXVzQUFBQTBnQUFBTkl2QkJsK2JXRjRjQUFBQWV3QUFBQWdBQUFBSUFIUkFnWnVZVzFsQUFBNy9BQUFBY1FBQUFPVEFWeXVwbkJ2YzNRQUFEM0FBQUFBN0FBQUFVbGtYOFR5Y0hKbGNBQUFDc1FBQUFDaUFBQUF2VnF4M3pzQUFRQUFBQU1FbTFPdXd6UmZEenoxQUI4SUFBQUFBQURabklQaEFBQUFBTm43U1VmLzVQNWxCT2dGaHdBQUFBZ0FBZ0FBQUFBQUFIamFZMkJrWUdCeitPdkN3TUJ5NXYrVC8wOVlYakFBUlZBQUN3Q3BGQWNRQUFFQUFBQm9BSEFBQlFBdkFBSUFBZ0FzQUZvQWpRQUFBS1lCQ2dBQ0FBRjQybU5nWVRuRE9JR0JsWUdCMVpqbERBTUR3MHdJelhTR29ZbEpDOGhuWU9Wa2dBRm1CaVFRR0Jyb3lIQ0FRWUZoQTV2RFh4Y0dCdlljWmdVRkJvYkpZSVZ6V0JZREtRVUdaZ0JuL1F5aUFIamFZem5ETUpVQkNGak9RRERqUzRiL0REWU1teG1NR0NZelBtWFVaTXhtMk0rd2lyRUVpTzh6SEdQWXczQ0hZVGRRWkRLUWRaTGhLY001aGdPTTl4azdHR29aVmpHc1ovZ0gxTVhGRU1CUUJzUWdtQVRFSnhpS3dXdzVCamVHQ0NBTnd2TVlxb0E4cnYvZmdPcHRHSll6ZWpHbU1iejQvNFRSa3FHZFFaV2hIZ2duQVcycFovQUZrdnNZbkJrMi92OERaTGVBNVNZRDNWYks0TUZnQk5UdEJ0Uy9pV0Vqa3pURE80WnBETi8rLy83L20wR0VZUjhUTzhOdUFCRlVQa2tBQUFCNDJtTmdZR0JtZ0dBWkJrWUdFUEFCOGhqQmZCWUdBeUROQVlSTVFEcWFvWTVody8vL1FKWUNReXlJOWYveC8wZi9OMEoxZ1FFakd3T2N5d2pTdzhTQUNvQ1N6Q3lzYk93Y25GemNQTHg4L0FLQ1FzSWlvbUxpRXBKUzBqS3ljdklLaWtyS0txcHE2aHFhV3RvNnVucjZCb1pHeGlhbVp1WVdsbGJXTnJaMkRQWU9qazdPTHE1dTdoNmVYdDQrdm43K0FZRkJ3U0doWWVFUmtWSFJNYkZ4OFFrTUJFRWlBMDBCQUJWTkg1Z0FBSGphclZkcld4dkhGWjdWRFl3QkE1S3dtM1hkVWNhaUxqdVNTZXM0eEZZY3NzdWlPRXBTZ1hHNzZ6VHRMaEx1L1pMMFJxL3AvYUw4bWJPaWZlcDh5MC9MZTJaV0NqamdQbjJlOGtIbm5abDM1bHpuekVKQ1N4SVBvekNXc3ZkRUxPNzJxUExnVVVTM1hMb1JKNC9sNkdGRWhXYjYwYXlZRllPQk9uQWJEUkl4aVVCdGo0VWpnc1J2a2FOSkpvOWJWTkNxb1JvdEttbzVQQzdXNnNJUHFCcklKUEd6UWkzd3MyWXhvRUt3ZnlScFhnRUU2WkJLL2FOeG9WREFNZFE0dk5yZzJmRmkzZkd2U2tEbGo2dE9GV3VLUkQ4NmpNZXJUc0VvTEdrcWVsUVBJdFpIcTBHUUUxdzVsUFJ4bjBwcmo4WTNuSVVnSElSVUNhTUdGWnZ4M2pzUnlPNG9rdFR2WTJvTGJOcGt0Qm5ITXJOc1dIUURVL2xJMGdhdmJ6RHo0MzRrRVkxUkttbXVIeVdZa2J3MngrZzJvOXVKbThSeDdDSmFOQjhNU094RkpIcE1ibURzOXVnYW8ydTk5TW1TR0REalNWa2N4UEV3amNueDRqajNJSlpEK0tQOHVFVmxMV0ZCcVpuQ3A1bWdIOUdNOG1sVytjZ0F0aVF0cXBod0l4SnltTTBjK0pJWDJWM1htcysvVkV6Q0FaWFhHMWdNNUVpT29DdmJLRGNSb2QwbzZidnBYaHlwdUJGTDJub1FZYzNsdU9TbXRHaEcwNFhBRzR1Q1RmTXNoc3BYS0JmbHAxUTRlRXpPQUliUXpIcUxMbWpKMWk3Q3JaSTRrSHdDYlNVeFU1SnRZKzJjSGw5WUZFSG9yemVtaFhOUm55NmtlWHVLNDhHRUFLNG5NaHlwbEpOcWdpMWNUZ2hKRjBaT3JFUnFWYnB0VlN5Y3M1MnVZNWR3UDNYdDVLWkZiUnc2WHBnWHhSQmFYTldJMTFIRWwzUldLSVEwVExkYnRLUkJsWkl1Qlcvd0FRRElFQzN4YUErakpaT3ZaUnkwWklJaUVZTUJOTk55a01oUklta1pZV3ZSaXU3dFIxbHB1QjFmcDRWRGRkU2lxdTd0UnIwSGR0SnRZTDVxNW1zNkV5dkJ3eWhiV1FuSVNYMWE5dmpLb2JUODdCTC9MT0dIbkZYa290anNSeG1IRC83NkkyUVlhcGZXR3dyYkp0aTE2N3dGTjVsbllualNoZjFkeko1TzFqa3B6SVNvS3NRcklIRnY3RGlPeVZaZGkwd1V3djJJVnBRdlExcEUrUzBvbEJ4S3NZYVpCRGI4NThvVlJ5eUxxdkI5bnlOUmd5Rll5MnF6SG4zb3VjOGpicXR3dHU2MTZMTE9ISlpYRUhpV245TlprZVZ6T2l1eGRIVldabmxWWnhXV245ZlpETXRyT3B0bCtRV2RYV0RwYVRWSkJGVVNoRnpKTmpudjhyVnBrVDZ4dURwZGZNOHV0azRzcmswWDM3ZUxVZ3U2NUozbk1QdjZiK3NyTzNyU3Z3YjhrN0RyZWZqSFVzRS9sdGZoSDhzbS9HTzVCdjlZZmhIK3Nid0IvMWgrQ2Y2eFhJZC9MTnRhZGt6bDN0UlFleVdSNkg1T0VwamM0amEydVhnM05OMzA2Q1l1NWd1NEUxMTVUbHBWdXFtNHd6K1Q0YkwzWDU3a09sdXNoRng2OU1KNlZuYnFZWVR1eUY1KzVVUjR6dVBjMHZKRlkvbUxPTTF5d3MvcXhQMDkweGFlRjZ2L0V2eTNmVTl0WnJlY092dDZHL0dBQTJmYmoxdVRicmJvSmQyKzNHblI1bitqb3NJSG9MK01GSW5WcG16TEx2Y0doUGIrYU5SVlhUU1RDQzhnMmkrZXBrM0hxZGNRNFR0b1lxdDBHYlFTK21yVDBMSjU0ZFBGd0RzY3RaV1VuUkhPdkh1YUp0djJQS3JnTnVSc1NRazNsNjNkNkxna3k5STlMcTJWbjR0OWJybHo2TjdLN0ZBN0NWV0NwKzl0d20zUFBrK2xJQmtxS3VOMXhYSXBTRjNnaEZ2ZTAzdFNtSWFIUU8wZ3h3b2FkdmpwbWd1TUZweDNoaEpsbTJzRmx4akpLS1BneXA4NUZTZXlFVTAyb29qZnZLVitxZ3VGMEpuRVFtSzJ2SmJIUW5VUXBsZW1TelJuMW5kVWw1VnlGdTlOUThqTzJFaVQySS9hc29PWG5hM1BKeVhibGFlQ0trMk03cC84aUxGSlBLdmE4MndwTHZsWFQxZ1NUTktWOEpmTzB5NVBVcnlGL3RIbUtPN1E1U0RxdTNoY1pTZHVaeHRPRGZmMnRWT3JlMjcvMUtwLzV0NW43UWcwM2ZHZXBYQmIwMTF2Qk51NHh1RFV1VlFrdEUwYjJCRWFsN2srMTJ6a1UzeXArZFoxTGxDRjY5UEd6YlBuNytoc0RvL09aTXYvV05MZC8xY1ZzMC9jeHpvS3JlcEV2VFRpM000dUd2QWRieEtWMXpHNjZ6VlVIcGZjbTJrSTdpTUVkWHZ0OFZtQ0cxNXQwMjNjOGpmT21lL2hPS2RXcFplQTM5VDBNc1JiSE1VUTRaWTdlSUVuMFhwYmMwSFRXNEJmMVdNaGRnRDZBQTZEWFQxMnpNd2VnSmw1d0p3dXdENXpHRHhrRG9Pdk1ZZkIxL1V4ZW1FQUZBRTVCc1g2MkxGemo0RHMzRHZNY3hoOWcza0d2Y3M4Zzc3SlBJTyt4VHBEZ0lSMU1raFpKNE1EMXNsZ3dKelhBWWJNWVhESUhBYVBtY1BnMjhhdWJhRHZHTHNZZmRmWXhlaDd4aTVHM3pkMk1mcUJzWXZSRDQxZGpINWs3R0wwWThTNE0wM2dUOHlJdGdEZnMvQTF3UGM1Nkdia1kvUlR2TFU1NTJjV011Zm5odVBrbkY5Zzh5dlRVMzlwUm1iSGtZVzg0MWNXTXYzWE9DY24vTVpDSnZ6V1FpYjhEdHg3MC9OK2IwYUcvb0dGVFArRGhVei9JM2JtaEQ5WnlJUS9XOGlFdjRENzZ2Uzh2NXFSb2YvTlFxYi8zVUttL3dNN2M4SS9MV1RDeUVJbWZLakhGODBuTGxYY2NhbFFEUEhmRTlwZzdIczBlMGpGNi8yanlXUGQrZ1Qxb0FQNkFBQjQybVB3M3NGd0lpaGlJeU5qWCtRR3hwMGNEQndNeVFVYkdkaWR0akJvU3pNemFJR1kydzFZRkRpRTJKbTVJRHdUSmcwMlNWWXdqOHRwRDQ4RGh3UExBUVptQm00Z245ZHBENE1ER0lMNE80RWtnOHRHRmNhT3dJZ05EaDBSSUg2S3kwWU5FSDhIQndORWdNRWxVbnFqT2tob0YwY0RBeU9MUTBkeUNFd0NCTFliTVNteGliQXk4Mm50WVB6ZnVvR2xkeU1UZzh0bTFoUTJCaGNYQUgyVkxnY0FBSGphWTJBZ0FJd2drR1VuQXdQem5QL2YvaFVoV0F6emdIQUt3eFNXeFF3TXJBck1jeGdZL3RXdzdQei9paldZZWRQL1YvL1NZSHBaelJnZkEvRkZBTW1FR1lnQUFBQUFpQUNJQUlnQWlBRGlBUEFCa0FKaUF3d0Q2Z1FnQkdRRXFnVW9CWEFGbmdYSUJlNEdMQVoyQnNBSFBBZTRDQklJaEFqcUNVQUp1Z29lQ21BS3BncmtDeW9MYUF2eURKNE5CZzFzRGRnT0pnN0FEMHdQeGhCQ0VJZ1EzQkYyRWNZU1JCTEFFd29UWWhRcUZLd1ZRQldZRmU0V1FoYkNGMFFYcWhnQUdEd1llQmpBR09vWkdCbmVHcHdiQmh2RUhDSWNwaDJFSGd3ZUdCNGtIcmdmQ0IvT0lISWd1aUZtSWhJaWtpTW1JNFFrRWlSbUpOWWxWaVc0SmpvbXdpYjBKM29uMmlnb0tOWXAyQ3J3S3p3cmFDdW9BQUI0MnJWOEIzd2MxYlgzdlZPM2FGZmExUlpKMjdSZHZhNTZXM2ZaNnU2eWJFdHlsOEZOMklCd0V6YkdnS20yQVp0Z0lOUWtOR09EUVhUNENDV1VKQThlNUZGQ1BnSUV5RXZndmNTRUlvMitjKy9NN0s2S2JYN3YvVDcvck5uWm1UdXo5L1QvdWVmTUlCYmRLSDNHTmZFNUtCbWxvaXEwS0RxL1BOK2Z6Z2tjYnVZeHh3Z01Kd3pxUkVaZzRmOHVEY2FJNFRDelZvdFpoTmhGOE1HaWJ0aERiUlpMU2dwQ2xpcExaYVFrSytSeHA2U21wSnBOY0ZkRG1WNnc1eUtibGJVSWZxOHZWSllhS1MvMXNxbGV0anhVRnFsSVpXRmJYbHBpc3p0d1BZWlBxMFZrVTJFcitIMWhQUmI4WElHTGRmbUdYL2VSRDdZc254bkpaQTRGMkhmZlpYeFdjenAvNTUxOHV0bnFZOTU5bHcxWVE5bzc3OVNHK0J4UDhJZHBRWThueUQ4VDlQemc1UWQrMlArdHljQUorQlo4aEJXTlpyMU9Pb2xiZEhxelVXU2xkZElhZ1RPWVVuR0xkRElWTWZqTDBXK1pQM09ua1JFNTBZTEhkU3pESW95Ym00N2IyeGRIN1FnaDNNdGhqQU10UE5ETzlDS0c4VE90anFnVkRnSWZNT3BMUE40Wk5TY25JNVRzVEhiWUxIREhwS0NnSWJ3UVdTUDIrMEpoTmxSZWc4MDJGeWJVaHVvd01JSjUxc0lVTTY2TURBOHVZaXoyUGJpbVp1cFUrT05PcDJXTTFOblQwKzNNLzhsSUcwNTMrVzd4dWVobWRCU05NcSt6YjNLblUveElONXFCVUFxTGRPaHpSUDR4cUhiMEsrNTZiZ2cxb1RhME9McGdWaTJqMVhsdERNc3d6U2tHUGFzMWFoaUV0V2lkS1Zsa3NjQXhEQXZ5VGNJNlhSWWxNWnR0Ylc1R3FMbXR1YTIxQlc0eVo4YTBhRU4xWlZtcE54RDBXLzBCYjhDczhSRHhXb1JjTEZMNXdZNU1IeEd2Tjc1TFA0RGdDblVuTlNad2IzeTNGRmQ0UmU0Q29PM0Y2Tk9FeEUvbWNaNVVaeDdUSlAyZzd0MUJqdjg2K2h6NStMUkRQdGlJZVhYdm1EUVFsWDZNc3IzZWNOaDdtbXlrNTFKTTdqUldoejN4dmRoSlhDRWZrdjRhMzVPMm56NU4rTWVpazZON3VRdytFODFDN2FnVDNSTjE4Q3lqUVJhTU5ZdmJxcTBjajZ1d2xzOEtNWXlXQnkzSkJDM0owMk1OUnBwT0FUUUM4d2ozSVY3TDhKMUpXQXVtdzJxWlBzU3lZcThPaTJLQUJkVXBnVDNFaXAzbnVvcGN3UGJDU0xhak0rcnM2R2hzUktpanM2T3pzYjJ4SFdZMzB4M004anVEV1FhTkM4VGh3amE3YkZleWNvVkRZYXZON3NaV2l4R0xWa1hkNEZoYzhVcklhYnNwRkM3QVpSR1FCcm1hRWF3V214M3VaQzR2aTRUZ0hpWm1uN2U3dzVlZDdmTmwrNHkxMSsxdWJ1OWNkTitGM21EUXUyT0JmTmlhcG5WdTZkd3pjM1pIMTgvWGVJTjNyYzNPOHJmL2MyTmVkdDRDUHRQamV5aHRkcjdmN2ZZLzYzZG5iSFg4eStoMGJWeXllRjh6YzhMbjhmaWVTVjlRU1U1KzQzZW4ycG9XSm1ON2lzdTFkdDZpbmRHZit6elNnUm0xbVZtR0pQM1hJOTN6cHZyeWpNazY2YitJakhoVUFqcCtDK2g0TXZLaVlqUUZkYUFWMFc2d1pSNHovQ0JpTllLR0ZRWVJoNURJb2I0a0xCcXdWaU5xKy9TWTV6RUlBdU9zRnFUUkNMMUlFTEtGMXFsVFMwcDhQb1NtZGt4dG45TllNcVVrV2wzcEsvWVY1V1E1MHMwcDhDUEdrSkdZc2N4TnYwOWhHRmRhWWljYWpDbTdRZUZ4d0FnajNLRFk5VENpQVB2SFgyRmt4cHpHMSs2YU0wZjl6enhqejBoTFR4dSt5VVkvMmZVakpWUERZZlUva3pnMG5IQ0NHNXFUY0diUTRiRFo3Y012MnVBenpjYldXeEtIanJ5WE9IUlA0aW5pTnc0QlR6Y0FUK3RSSS9wNzAvRmlVT3cwUFVhNEVqT29FYlBNTEwrVjVkaEN6SE44czJQeVV4bzQxU2w3eml4UWFnYUN4eURjbWVVWXRnK2NxdGlyQlpYT2F0RmdqdU43QlJDR24yOTF5RDlWY3M3eENJYlRYVlZzam1qUldTNUNzV3NTSk4wSkRocWhtZE9CeURwL3hCK29Eb1IweEh6c2NaY2M4dnVJRkcxMlhGNEJMa3Z4YjRKb1YxMmRyNUFJbkVpMHZDSkV4VXFzaG9pMUFqT2YzbXdsVnRHOG9hSWpKenNIQjdNeWs3S09FYSsxTEZDeVlUN1o2Uzl5TDlyN1VOL1JqalhMVnM0N3N1cWR1b0s1WlJkMlNUOXlRK3VTdzd1Sk1Td3BMR2d0akhRV1NxY1diNERJRnZSYzBuMEorZkQySGxseWM5ZnEyNlpzdmJyejRQeVIzUE9tUmVZWGJjWWhJUG96NW5YbUx4RERrbEM1elA0a0VyaTZHUks0RURES3pKQm9oUmVSQTZnWDlzQ1JSSFV3SmducEFpelI3WGlFcXNITVg0UUsxdTkyQmRnS29mQnU3blNKVkovaGRHYmdGNG1RY0xiMFM3YVhYNDA4eUhNUzdqYUgvdUJqY0s4dy9OSkorTHl3ODFHYkJXdHN1WWo0R0dJaEF1aTltZTZSSHdHSHc1UkZ6T1VWckZHWDR0S2JEQTkrOWVWREJwUGVsYUxUWC9MZWxWZitZWUJmYlRPNzBpM2FmdW5xMFZIcCtuNnRKZDFsdGdtei80SG52dm9xbm45Nk5wbkhlVENQdTVSNWFER2FUWDB4bVVkT2ZCNXVKNTJIeld5MU1JSklCRXdOdGR4c1NtSG9Ib2xDZG1icUg2Njg4cjFMOVBKc0h2cnlxd2VWMmZDMjA5SURyNzRxUGZTUDJZSXlJN3daUWZqRlc5VTVFWCtFMFhQNEtzNEF0bE9HNWtlVGl6RGlDc1ArOUdRV1hEc0RNU0lIQkpKS0pJQXZCNGpGWmJVQWJFQzVSQzVXMk9Nd2gvQWdrY3hsOUN3SEtNSUFkeTFERVhlZ0FBQkVCZ1VRd1hLRm00TEl5MHoxZ3lhS2l1OXB3RUdpa1RJOXZBeXhtTVA1ZkFBanV5a3RxQk44bWRKWEw2WG51RE55MHZmdlQ4L0pjT2VrdnlqOVo2WlAwQVhUVEhhTUFqZy9oeHNxeXBHK0dOQjVQYWxtWjBnbysxMjZLK2kyRnB3K1hXQjFCMTNwdnlzVFFrNXpxc2VyRzhCcHZNNmZKZFArSzNRVjUrTVlrRU4rTkFlTUdrRVE0ekJBSTNBT2VDMnhjb0tPZUtZRFJudVFPK0QzQi95aXhrRWdoTWxMYmNydk5WSGpLek41S1ZBbzlackk5QTk0Y0JXeEdPa1ZvdjNTSzJRZlYzbUNIRFB4V0pDT0pmUEJXNlgzbWIrQlZhUWdkOVFCaWdGZ0RsSGxSekhkRDRVWVRSckZNQ0lMUDB5d1NqMEd2Zi9BTEw1am50N0lMT2NjMWhkeEtEWFptQ3c1czB1NEpQeEpxcFhTeWpDY2o3a0tHWkFuNmt5MHFXNXl0ZzErMzREMEVXcFFNbUVLUFJ3UDh4d1J5R3laSDVpcnlIekpINTN2eDRBLy80Yno0TXIwcUUwMVVPUkhyZlJ1U1VINWJtTWc0ME1ORFkyTjhJZnpYTDRueUUyZmtHbEhMMHZIT0lIdlJ5WlVma3JQTURLUUpSQWxpZHc0cDBXeDBxaU9hdU0rYWlUVUQ1aFFTbGlkdG9oVkJFY0FPdnR2RVhha1IvVGJzeUlzY3dkODh2MXV1MGI3L1kwcEZ2SXBuSmRpa1hIbjB4QS9VbWhNOXFDOGFEYkJrakowQmw4TVV5RkVaYU5Xa2pTa2VGTGNhVFlhVjJWNFRNMFRmcEs2aGZGUmt2bjhoYjYrNXkrOTlQbSt2aGNHMndhbVR4OW9rN2ZjMEZIcHl5ZWVrTDQ2ZWhUYm5uZ0MyNDhlM3ZUMndZTnZiOXhJdHBzSVB6NUVDT3p5YVpoUlVUVGZDTEFLZEFFMkxJTUJKYkFBZURuQ2lKNFl2MEUvdy81QWhOaGNZSXdBVGFxaFZWQTdCTTFsdnlFaVhVNFYwUEM5eVpocE4zcndnTVZpYzZIUksxUUJzMHQrcHN0T3Mvbk1YeVM1TW9aWktxT25BR1IrRFh3cVJPYy81c01jUzBSa0JCRUZFT3l6SE15TXFOVm1tSjhjSTdPSTFKZ2VOZkVJSmd3RDc3RnI4bkdkVVNOOEswUUZnWnd5djUyYUc4RWlnb2k5Q1NqUnEwb1p3SjdmRjRPSjFJMHdUenpjcy9vODZUZytRUUlha0RySDUwckdUeXh0dW1qRHhsNXl5RDc3VjB1NG9YbTNiVmh6L3dicC9sMGtjcjFJcUE2bDRHZVg3MnhjdHFGeUl6bDJLSnhTVmtOOTVPaFg3SDlUZk5FVWJTekdBaThBR1V3ekVnQlFDQnlRdzVKTWhLQTJGcmdDYUpnWGV6VnlLSStyRDJ3aGRBY0NrVWpBbnFjbG9Wc21Td1ZhaW44SEowZzBpSUJZQ05oeThrRy9KVklKOGIyVWVlR0I1ZTJ6dTFiM1BubnBpbGZiM0thTXpCVHoxRnRhZCt6WmUrRnNJdHFLL2dzdlBIOHJCY0FHNDNYSHVhR09HMWN0M0JrTUhWeXo0ZDZsMDZ0dFRvc3J4MUJjdFczTjJ2T0l2SHVXTHVnTlR5TmtiN0JsYUJkVHV6Z0VPZ2d3RFFWUkZpcVBsbVpoSk9CbUVTTmVkcEFhTEFoWkxRRDVHYllIWk9sbmdjWndDRVpEcGhYeEJueGFqVE1YV1UwcStyQ1dsaVFvWmcwdWk4bXdGSHRUMlpsM2tsbmZlUm4xbTNQSjlyRGs4N2wwK0ZOYlNVZzZEeS9VY0VPdEkvdklYUCtrS2luc2VJM016ejN1a1FyOGplelRuNmF5dWd0RjBNem9OQkZnTlNaeVlubUJCYnZoZUpiYkJZTkFnSHdmREJlN2laaDhCSEhSUERpYklXS0tvQkovS0dBUCtRSlVUUEtrV1pETTVLSlNqTjBuUjJuaWowdTk3TTJFaWdMRHFnc3VQcjVzM2ZPN2VsNXM4NlFRQ1UwNTB0UnhjVVBOcGpuVHp5OU44ZVg0R1F1VG1jM1l1THRvVUhpdWNzMWoyN1lOclk5V1dOMjJqRnhEUWZtVWJhMXorcVArZ003dHgvLzB1MlYvOVJyNHF5VHVTY2o2ODFCdHRFb2pVNG1CV2s2bWl3V3pJazRpZ1M0WHVGbFhuaXMzNklmTEhLRkFRS05KbDJrVEljc2d3WGNNZGVaQUJScVhFckRISWJoSzMwcWZPQ05IRm01OFpQV2Fwd1kyUEY3WmNnaFArVTQ2dkhWS3d3WE56ZjMxZFZ0YXVTZERwUjRITnY3cm5lbHpsait3K2Z6N2UxWjFYL2JiQjNIa1RmM0l0Ulc5RFRNMzFsZXVuVDVqWFJXVjEyZEFDdy95Y3FDNWp3RXdaNGhQU1NJQUhuWUJJdmRESUdDN09hREcxeUxia1NPYUxwOUNneFBPZFZMMDZFRHBmbXVZVitoTGlBbmVoQnpTeTM3aEVxU0YyckFqa00vam02V1E3Q3VZTzRrbzBsSisvTDkydXl2TnFHZi9mSkRZeExzUThWajBGdWlXQlBiZ0FBaFVnNlpIcDFnRVFBZkVNWU1JT0lidkUybmtFT1RJd1hHcTZlZmxPWjBJNWRYa1ZVZEtuTG5PbklBUGJwRUJUc0ErM2duSTJIenluSXNaSncvbXJWLzJMSjJ6YlBQNko3ZHVmWEw5NXFWenVucCt1YTYrdDdKeVpXM3R5c3JLM3ZyWm14c2FOcytXdDl6UW9pTmRIWU5aT1RldFdIdlA4dVgzckYxeFUwN1dZRWZYa1VXSDgrZFhsczR2S3BwZldqay9YK0xMZSt2clYxUlVyS2l2N3kwbnV2Yjg2SmNjQ3pRcnVtYkNEQWNFY3lBQ2pnRjZlVDZtYTByNEIzckg2bG9nRUpaMWpXQS9oaE1GWXY0VmViaml6T2tsOHdwUkxPbTU3eHlnY2xpSDNYR1ZrM1ZzTnRVM2JvaHFsdlRHbTNvOFh1Y095em9tNnh2TWxtSVY5bDdBSlE0UzR6a1ZyUVNKajRhc0FGTUhab1RZWTNRWU02eXBGTURRR0srdU9kQzR3NHo5NWxiZ2pQckhiSTdEbXBITHgwQWNtTU1WMHZzUUFNa2MzQ2duR3JiTFVaMkZ1TTZzams4SWd3OXlPMjBXT2dOK3dnek1FN0NmT29rckV6Rmc0a3lrVXhQeDRFNjBuWE54cVNpZDRFRzlobGhVTThGMHFKTXVITUlJM09ITXBHQlRXU3pRWWdXN2g3R3NwcGg5emVTMUpXV1A5REIzWkNmWkFBb1AveXZkWmt0bnRWeHFicHJaYTVHZWxaNjFlTTFwdVRxOE15a3pQVDB6Q2U4a092VXJYTTM1MkxsVUZvQnUxUFhJdFNBRWtNVWl1aXpaVGJqU3BzZ2ozV3FtOEZTWUFFL05ad2Fydm9SOWRxNGFNcVROQ1JBV3FId1krTkNtOHNHY3pNUkFkMmNjZER2REt1Z1c0a3NtV3F3R0FjeFZBZFhELzdKUWJqQjNqUFRJM0dDMXpDQ2xXdHFyby96QVUvRlVtUi9TWHNJSGFmUmI5bVhJZmNPUU1WMGMxV1ZnQmh2QUJUTEtFbTRvNXVjZzRpSitGM0YzMU5nQ0xjVHd1RjV3TVg0T0hHSmczRUFZZzRodTlTVU82NHhhc2lEdnlTckxpaFRtdzArR0FubloxQzVsMzVPTWFWWVdLbS9BOWN3a2NHUGMwdSs3eCtiTjJML0J3TmMxc0FZbTJUU2pmVm4rNnFXN0Z4TW5tbVM0K1dsVGVYbGRIZnh4cDl1dVdiWndlMWYrOVVWRkwxdlNSS2UzdXJHNGFVbXdrempWM1ZhSHB1dkgvM0w1K3VucUFyRVNCcFdNcnVVT2N1Vm9EbHFNdXFLTE0reU1qdEZoVmtmZ0Z1SWhsQS9xc1FaeGpJYnJRMHdTMXJHTXJrK0xJV1ZEQW9zQWVva2kzMGtCR0JKNXNhT3BDYUdteFUyTDVyYkREV2VIUzBMQmdsQWdaTkM0NDB0aW9YQ0NIeXF4SzJFZExNeHFzVkVjUm1PNzRwL0s2V2wxT1lCY1pBNlVVc2RzazUxWHlNL20vMlhYek1GNVU1YlpJOHNiaWpzS0ZoNWNzRERISTZRbXAxcnNYSXVZNVc5YTJQUEl3QlVmN1Z6eTBQWVorOG8wck5QQXA1WGYzSEg3NTl0dng3WUhheGRVQmR6Rml5SlpBYTc4d0hkM2JEMjVjbXJEdEdubHEyZDIvV2IvcWdhOUtLWWJwWDl6cE9jVUhoclk4OXphR3lYcDlzRm4xbGhNVEw1WjU5Q2xPZmYrODc0WGNjMmowdExPQTdNS0M3cXVtbHBRS21NR1NKVzRGeUhPNXFOaVZCa3RRMXJ3TzFwMkxSSkZUYmNPYXpTK0ZvRmpXTEwwQW1BQys0a1RLaXFFMGJrRXk1a0NFYitlTU0xbXgrTlFYTmdyampzaVIxdXdScEgxc3N3dmlwTndieDBGZGJlUjdmNjVrbVBlQVAxK2dtd3JjZE5UTkJQWkZId0tYL0VrUkYvZmNFZzEwYi8vUFphT0hDTGJLMGIrekxqa3RlNTJvR2NtME9NR1ZTNUVkZEZxQVl0eVpCSXhKNElyQVU4QzZJNWdBMEZKYytWTXFUQS9KeXNjOUVLK2hKemVRSzFXTllGWUVGYnBNS2wwc0NvY2g2UWZkdnhlNXZ1NzU4MklydCt5NUlGTFJsNGprNy9rRWtyQzZjOStlOEdGVzdmOUZtdTM3L3RSQWhUYWZrTnY4N2FnNytaTmZVZm14cW1RaEo3RlM1Y1BiMWpmKzVic2d5NEVERFFEWW13Sm1oYU5GbUNBY3pRcUlKWWhFSWZ2RlFGbXlFbFNmQi9TZVdMWTJSeEJyQ1dvT0JUMmg0SkJEWUhja09QSml4SlVkVlhVTUZaMWxZUzFSRjU2NTFKOHhITHJkaTA3Lzc1bGkrODhmK1dqalNiSWtjMmVaUjlzdmZYTDNYditldlB5Z3lXK2JHN0k3WmRPRWRPZHZubGEvenZYWHZ0MmYzV0ZNZXkydTIxVHBwSk05bkZzdnlWYVU2M2lWQ0tqclNDak5PQjhialJMbG9sQVpjS05rWW5mNjBpSFVUWnZvRnlrVUVGT3F5ZVRoSXdRY3VFbWY5Kzc5Ky9IcEd6QytjMmJLZi9mKy8yVEZ4M3Y2VGwrRWFqUmRkSS9UcDJTL25sZG5PMC9mdGIzNXFGRGI2NlhlVTdtMWd4enEwRUhtNDdyd051V0k0QW1ETmVmaFBWYURkYjNnN3ZSNmdVdFdBaUNKRUhUSjg4ZWtjbVRaWGcxOVhaRUs4bUZJaWNNMGl1MWVzM2dUN3kwTTJxRG5ScFVYUUZhRmZTYlVvT1FOWlVaNUJxVnlUSUovU1Z4Sit3MUtlbXdJdXpZRVM0SFlPendIc0tRTld2SWxsMFBCMEM2STE5aXhwT1Y1U0Yva3NUaytyTHhReURQOXhJTnpCT1VpSGlmbEs3cElwL1NpMlRiSmEzN0RFUXE4MndoOEt3Y1hTcnpyQkFzRVVKUFA4aWE0Tisxb0xXY3dITGdrREhXZGV1eFR1ZHJJVm1pMkExK3hpL0s2OTZrVEVuWHZYL1NKUkMyZ0VubEtGSlVBSTRvbGJJcEtjNGltZkRTY2F6d204YjVwQmdIdVNxRkYxS01GVjlRb0NDUjdXVTArMlN2SURtQTlCMmgvU1ZwWUF3bmRveDFTTEl1clZEcWxyVm9UblJXSmNZaVFYWVFzRGdDYURoMWJWL0QwQlVCeURwait3eWpMdS9ENFZwVUV3b0dJajR3WXgzMXRaT2FjVVZaWEJsb1dtMmExS0E1YXRCVGRpM2FkSDlQMTMwYkg5N3hMMm9oRDVKdFptRHV1OXR1L1hydi9xK1BMTCtoV0RIclB4TDZhcGVYeVdaZDllY1lYanBkYkNrc1BvcnRqNS9DYWJmVVZCUlQ0NVoxWVFmb3dqVGlzNUFlY1ZqUHJVM1NhU0NFYUx1TkJrYXI5YldJUEV2V1VzSGs2Y29PWERjTlRhbXJxYTZxTEM4cFZPS0tONUFjTDhwT0VKdjNqSUpVcWZmR1Jkc050RFUyMHREeU10a3VsWXhMNDkva003aWFuc0gvdlZUK0ppZmV3eHRVY3ZFUmFkMVlFVk1tWElNdm9PTEc2RldnbXdPNlBTZzdHdUlBS1BMZFpBbkwxd0tVWW9KYUZVbzl5RVZYUVpUMVlycFU3QzBadXpLbjdyQnZ3MXhHRWJaUVRaeEtaMllaUlJTNjNqUitoakhGdytnQzBMdkxZUzVCc2pwakoydUR6U1JxQUhJZVRKd1pJa2twS1grUW9BNkQvZjVBMkIrZkdGRWhwYjVnVXN5SUFwL1k5TGcrbU1ocmI3elVQeFJOSVZvMS8rRGVDNlg3NmV3ZWxXYzNVdkx3b3gwelV6T3hpOXJLZDAxYkI1ampjZnNndW5JM3pITWVzWTg1bUlPWk1HVDlEQU9PdzF5Zlh0RWFRNUtpTlF6SnlBU3NMQ25CWlIwdFRiTm5UWXNDUXdOWmtjcmlnREd1TWxqR2ErUy9MVmJ6SWpYa0FoeW15QzBabjFPSFlvaUZVbG9uTGRPazdHMzFGRG81YjBxNDFFa0luYnQ2VnJyUEhyS256UzdJYVhXNzZWS1Z0RGdoOUt5UTFlcVVyR1RUbGZXYzgvQ3FyRlZOdWdXdVJ2TDFRTW1pdXZsZVg4RHRja252VEtKazgvQ0RZM2xHNGxNQWxZQ2JoYlFFTVA0Z29Ic2tkRU1PSXNnUk5MN3VCdU44RUR6OHBvQUNBUlRqaVB2RkNkUXpIOEJVL3h0L0xTOTh5QkhqVGtvWms2TXFIWjVOQlhyQlJKOEhYb0I3Q09ZWEpmWmY2N0d6SEtMb2kxU0ZCaldZeUZPdk80TVhpS0w2cW5JaXpBQ3hrS1M0TUZQSFNVb3ZyOTJFOWVOUlo2eEJnemJqd0NmdHdpakpLSS9iK3liYkc0YmNRQ0RYOEtaMVUveG9lWG94K1hnN3pTbjg4U045MGRzVHJLdDA1R1ZDTWxNOS9PWllFYVdZUm01bmVyMkU5cG1LM1pXaDNsTzVCbEtzVURJMkIrZ3VrUkQ0ZDFsRURJTjdpV01BMDNORVBSUFBVbFRnYjVHTnN6TnFvc1d6VW9JRElnRi9RQWtETVJNTm56R3dVVWJnVXRNWVJhNEtoc284STk5ejE4VFI5N1FXc3YyVHphSEI3M01EaWJvNnJITmtWckMzRDc4NmxtcWpjZmc0OHlrVk80TVdBOTFiL3ovVVNWam02NzE3djc3MVZycmRlRjhYQkN4NXl3M2RJbjM1K09QU2wwZEpBQ0xvOHJBY24vcmZ2dmJhZC9wVmpMa1laT0ZGT2Fnc1dnTFFDMkVCclJWSjRSM3cvMFRQbkpNVjhNRm9EL0hPSWExYVhqRGkzRFA3aVZnQ3dGWTh1M0xscy92KytnMTExSDlJc0JqL1g5ODljUERRVmU5eWR5MS9ZTXVXWHk2VDNodkx4NUdiZG0yNWdJQ2V4ZEkzbElkVmFEWWFpcWFXWUNUYUFCSVdZc2krbW5XWXdVMU54d09nU21GaVNTd21XUzVCRWV4cWtxUUp2VnE2NWc3UVNDMjFPWnFPaDJCNEVMQW13aUprd0dlK1RBTTZtSU40bHI5ODRtREU4Z3piTjJad1oyZlVYbDJOVVBYczZzYXBVWmh3WlhFdzMrOFA2YW1EVVFRYUZ1WGlycEpmMkJKeVkrcCs0MVhlczRyZW1YWnBSMXRtVmU2TWNGWkxybGFYN0VreTJhclhsbWJVQkRXUkdWbm5ieE0xWG4rRzl0RmJIb2F4bSs3dDZycDNrN3psaG02US9ubmloSFQ2Qm1aL3BrYWJuT0VSMGl3dVcwWktia0FqTW5wZE1WdmdTemZxMzZqRy90K2V3RWszSEY3LzZwVlh2dHJYUjdicll6a0tpVTIxYURwcWlOYUNrOUtBSDlQQUdRM1RwNlZBVkVkckJEekxxQjExTkR1ZVByV2hEcTZxSm5xVUhhblh4eXM2dER2SmxoaU9RbW84T3F1U1pjbzZKcHhjZHZqU3lxQW56K0ZNVnNKUFkrMjhzQzNUSGN4d3o2KzVnanBxYVdOQzN2bkRWNjlqNHhVNy9wMjdhLzZSMWYyM3VXekYyUjAxZFU0YWRCcWE4eHFuemc3azVFcjd4bW5rRjYvMDlNbSsvRGF3NjJ6YWQ5Y1JiWjJGc2VERkRFL2lNeFo2Z1kxVTQ4Qnh4ZlpKVllFRjc1WGRna2lKbk81U3gwNTc3a3FLOG5OREFZL0xIOVRTVlRPbHE0c0dZOUtkSWdmcitQS0xWYW1nUnhKclh6SzcxQVl2QmRXeWZ3QlVHeklXUGJScDQwQk8yTCs4YmVIcTRsVmJWangzK2FyN0crU09ydHprN0pON0I2OXNxQTB0YVoyN3FiQzljK1VqV3hiZlhTMWozTS85N295dTdqVUxzeXN0Wm51eXlXN0pQclJ6M2JIRnMyZTJFbytQOC96dW5LMDdOblkxdEdXWXJDa3BUbXRnKzZxMVJ6cW1WOWZKK1N4R2w0Q3V6QVZkeVVhUmFMR0FsUTRlc2w2aUZwTGlQcDBHNVd3VTlwdG8ycUpVa21MZEFwTWczVGdidkZ3WnpWS2swLzlKSGMxQnN2MVA2YlFjcWRrbE5EM1pUeWRkbGdnTXBkZnBzUUUxUnF0eEtwLzJOOURsSGJZYmhFZ0xKcVNmTEFZSzgxRXVvTUlJL01WS1hpb3NMSnNBbCtSMXNiR3hwdjZEVjEvOW9GNE9LQlFXN1Rsd1lNL214QUF6c3ZIM2I3MzFlK2FnT3QyUlBVY3Z2L3dvczB2QjFUcVlLMW1mQ3BPNXVrbU52NWxYWmd4cE9aMnhPdGt3Q3Zyb1hCT2dqZ0lVOExpNWF1UFE3aDZZUzR0MDFGQ2FsMXVhSk4zYVRPZDJJZGxlZzB0dzJTcjZ2VlVKaGlsK3Q4ZkhmcVBPZGZocWRxczh6OUZ2WVo3djB2cGk3K081QVFPTEJSTDgwK1hnejhKOE9STGZJZjlxZ2NRdTJNS293ZDhOa1luVVR3ZkhqVklHeUxFL2drb0NSQXhqWXovdGI2SU54cVRMYVJ5RkRxeDBKTWNJSFNJdzV5bytPMnV1WmVncDY3eHdOcmVQWWg1TThlckJWVThicXpQOXdsUHJkb3dKL3lrQjF4Um14c2hUVTl6K0JMby9acG9MTFphUkIxbXZqUHd3S29HNTMwTHp2bWkwcmpvN1RlU0lxSFJhRVlqU2RDZnBHWGtwVVlaOC9OakVyNm9pQW9Lai93MXgwS2NkRCs3WThRZTBlQUxSWTVLK0tkTHJlRWwxSE9Wc0dKVituRWUvMHE3Y2VyeE1lblZHbkFXZEgvMnhsbjRyVW1CNnErU0o1WDhicEJnZ3gzL0d4MlBnL0NWY0c4dTdhb0VIMXdNUFNsQkZOQUlzWUFrTFJDQ2E1RndnMTBuU3dSSlVwSktlSU5tSjBlQXNsQktFTzEyNit4UHFFdTZsN2NiU3ZUTmx0YVY5ZWo4TVQwa2thK1QzMHEweFVsWXhoVEZTMXVLamNSeC9IOURpVjNQSVNSbzAxQnd5M3FDaDVKRFdNcjlWelNGRlBDSFRpRlZiWlkvR2pyaDBJMzJNUmVuSVlId3VJM05JMGlsRjF6K1JHYWNiaDl1eGdlWWJENU9aMnF6c0E5OVRoMWFuOUJ2TmtVNnlhL2lseUU1eWI1SVJrZjV2VHU3djUrTDkvVERXam15QnNnZ3BBWE14L3BwaWJDV3BPRHViNkFkTjJ6QlZHbWtJejNxRzlGaDdnb0kzU0Z1dWY3aUk4Z2l2Z2QvZFEzODNLeG9rdjhjQXRGb2JiODJLdFZEWmtSV1NNS1h5YkpvMDFWOGQvOWxaMHBEODgveFNUL0Q3aitYZjVLOGtXMWsyWCtCdjJVOGhMcnRRMWlQQ3F1bFJseEVTQ0VqeWdXekU3Q05Wc3d0aG5BczV3K2tjaE5wSEJNQXdrQWJRT3BVZzUwMUsxNkxTWjhIc2NldHdSSERhelBaVWwvQzN2d211Vkx2WjVoUndST2QyY2tQbTFKRkhkSHFUUXhRTlNmaFBVbWFTUVJRZEpramoybExOTUovUlQ2VWQzQmVqSERLZ1REb2Y2M2dXQkFPTU1nOXViRjN1STcwKzZjZWNKTmh5N3c1bjVPUmtrRC9LMnlyT3lPYnkrNUVKcGRON0dwSGEzcFZtVVcrR2xMcGpNRlp4WTNQVGJHbEdzM1NWemUzMXBacnhVbTVqYXJvalhmZUJJY01WemphTXl1dlArMG44WTArZ0FsU05QbTA2N2dJbm5lekVHcmFpSE5CZENzeWFiWGFNT1NMQ0VhVUxPQnZ4SE9rWEdVUXNvR0xFYXZvUTZkOGxpREMzUlNSMDl6SXlGSFRJZHk0OTl3VkFycC91cWswWmptangyYTVDc1lzQThLdlhFRmhlV0loUVlYVmhWVmtwMEpidkR3UURrWWhlWGZwUGhKMnhuZ0pnR2kzcUNiRnVNS1g3MTBhV0ZBa1FEejA5MVUvVU1UcGxtWEh1YytldC90bmlUMDdlZnNPR2dhWTdaNXVNWHBzK09QK0YzdWYzcmU1NjVZN3B0N2F4SjM1eGo5VGZSdHpJbEliRzFobVhkZDEyYyttQzNxNmNvTFlvTGNXZm1sY29jVzBMWjNmY3M4Rm1sMlVSQkZtMDhKbmdPc3JRSjZkU0lEVVIxYXpaajlSY0xkQkNPcUJwYXBQYkl0RDBVZzJnY2pOZy9wbUh5czVXdVFxcEY1RUc3VndZanpoZ2ROOVB1Q1NhUGRsb0ZCc01VVjBkMndtaXNJVkNDSVhLUXBHQ1BPSVZ3ZnBENE9EbEZ0RXhIVU9LUk1ZbTdlTmJiUEEwMTZWUDczaHA4K2FYZHF5NHQ4SGx1NTJ1UGRGVi9HZHcrb0cydGdPZG5ZUFRwZzEyOHBtQUFJdnYyZmJCNGNNZmJGczh0MTMyN0Z3SzlmdFMrNUYxNjQ2MEx6aXljdVdSQmNRdWR3UHZYV0FIWjYwdjVTYlVsM0wvMS9XbGNjRDlYM1E1T3JxN3MrZkl3bzVEUFVzZm5HVTF1OUtUTTl2Zjc3L3VnNHN2K2VDYXpoc2p2bXoyaExvUVhiYzhzdkNXbnQ2akM2dktVN0xUN1g1NzdmUmRIMTUxMVllN3B0VFdFalRPVUpvT3hmVEptY3lnTStvVGVSS0ZKUklmYTdTVDZWUGkwRzVxZVVLaXVTYnFFOHR6YTMvQ0pZbytqUnVOWW9OQm4rS1dQVUdmZktGZ3hLL3FVNnlOUDFTSHg5U3N6NmhQN0djdTJra0hldFJ3N3dwWnNaNitsSzVZZkMrNXFDWjFVcTBpK3ZUakF6SkNhSis3V05hcmUvQUJXWjlrVFpLMWl2RCtJUEIrR3VoVEprQnh5Sm5WMVVuRXcwa2UwYjVBcnBlc3dPUzIwSjRGUkovTjhrSlU4NGE5b1lBZkx2U0UvVDVJaWpKSXptd25rZUtNS21URW9wZVFndDdjcUFIa2tDZmVkZVBTUjZlYmpINmJOcS9sMzliZi9PN21TLzV3WVB2UDA1bVYxcHYzc0NlMi9YYS96M25qMGNLd3RzeHF5cktGaTdhK2Y5TjFIdzdjc0hQVEJRTktEeXUzaEEraVVuVFJZNERSdEdxYmNiYjZRSVlHTXlKcDcyUWh3R050cnc1cnRRRVFLZEVUSkQvMkVRMnJZK0VrM0ZLTCsrSVhKWTZrajJ6QUw1VW9EWkYrbTU3QVhyVUhQZ3orMklYamtPUU1LM3ZVZ082OXJJZzFCdlNHM1J0L2c1ZFF1SEt2L0VtYVcxMitsK25pNXN0RDkvSEJVbk9SUHJtS0wvNlBqVlI0TDZtd2o2SDRkZnM5UTdJLzNpMnQ0UTZCREF0UkE5WkY5VUVHQ0VpankvS3lFZVVpVUZtZTVRWjFHdEpvM0tzVkdOb3NKWXJxc3lsS2IyRSt0WXNBcmFBbVhxSUdNZm42Ym5TMnE0bFZSZFNya1loNFZ1VDd6bnlYaEdzaGdJNi9MTGFHUmJWdjRqWEV6T3hGUlFnVk5SVFZWNWJUVnVPQVBSQW9reU9vWFZsT1ZYTGRTVnB6NjlTbmFDWnBYTHNoN3JaWFA3Ky81NlVGWVkwNXJOZTNQdEIyMWRVN1hwQXRzQzNCOE5nVE1lODkvTlpGOXkveGVvemhsTFFLenBtNXQvKzFXemY5N3VxcmY3ZnBjTnMxWFYzWHRNMjVwcWZubWpsRWg4RjljUHZCOTlXZ0RVU0hPVldIQTBpajBYYkxHcXUySCthT1gzOTNSSDFFYlRWSVM3SEc1SU5remExQlZmSkNkQ1FRMUNzMVY2VlRkRUxpRXBHZlBqcmoralR1ZFUyNWYyWFg1WTF6NDRuWjBybnRDdzR0WGhvL01KZnVuNlRSemRpN3R1M3dTc2taUzJIK3ZYUGRpZ2ZXUzUrb0IrUm9oMFpIcVUzUDV1ZWwrTkJhaEZJWXRJYUR5Y1B4WjZVMTdINTZmRFY5MG5RTmVwSGk2bWtLL3hyUXRxaTJMaS9aeUdGUjVXRVExRlBvQnE4c0J3Uk5OL0EwMktMWGNReHBVK3NtejcvUXFyK2Z0Q05wQkw3dkxLUGsyblVEcXErdGpoQUhBSWw5aEZRN0FtUFRYZEY2NWtWOXEybmlra1lwdHo3R3NjWWZUODJPTjlOczJrdTI3NE5YMlRrcm5oaldTTy9qOXVwWVp6L091ZU9xc1R6MEJJZS93TzJ4L0hCRWt2TWU5QWp3cVFINDVFQ3paT2JZd1pOejNlUlpuMEFMRXd0NEJEVlo0U0FwNWJOckU0L0xqd001VURxaFhYNGN5SHJHS2loenB3dlRCSGI0Ry9uWkdPbHIrcmt1TVRqRnhFN3lrV0dZMytmZ3c5clJLZXBEVGpWT1pjQk5ORHZvamdhcldONmpJUTlMYUh0cFFTcllZa2dTZVk1aFVMZEFsblRsTlhUaWdYTG9NRjB2YVVMSWJaR3Y2VWFUWHhFTms0VmdkU3kxdThsSGdyTkpnOG0ybzdhbTJUT25OOVFTZ3dxUy8wWlZFU2dzSEdjL2t4MmJURDFjOG9QbzluTEZLTG5YZ0dNMytsejVKWVh0aGZRUnBPdVZMeEdxSlo5U0s2TW1DS055TDU0NWZZMjU4NXFhWlJYMWlub3c3VE5tTFByWlN1bTVTYjlDRkxsYTNsdTV2SHRwNTJNMUE0dEhQcEYxaGZpa0cwQVdOZWh1eXMzSEtza2FRck9EZklveFNUaEpoN1NtVjZkbGlMMk02emhUeEJBaVkrVEFTeEluR0M5YjEvalI0TzdpNDFETUNNY042MVJkV1hWRTlXWFVsZjFQZkpqQ2I3YmtIRjZNQXZhVFB0ZlVSOWF3Sjg3dXhGUitYcnptZkRrdVh3YllxaEg0T0tIR2xudXVHdHZabjlobHZ2NXc1ODRQcjd5U2Juc1B0YmNmNnBXMzdJa2RIeDA0OE5FT2VYdDR3ZEVWSzQ0dWtMYzBiNE9jdndYbWs0MnEwR09uUWxwRzVGU2NEWWtPUXg1VjFaS1VJUmdyU21YSDE3N0NzZWhlU01jbVJITUZKWjN4c21qZW1FQitqdUVrcE9ma0lKUlRsVk5aVWdTVHpTTFM5c20xS3BVeDRYTUpkbnh0S2wwQnpBL0V5LzFyRXZEMHlvU0VESUNuakptbGJlTjlLK0RwdzJNek1obC83ZUR1aS9IVlErQlhJbDhuZ1Z6WjhlcENtRTNrNjlteDFyakx4dkgxSE1Nbjh0VkhBdG1rVUdrOGMzOFNTRm9UWiswRGF1cDdCbnowWTJ4WkdoOVFNdC9EWXpNVDRvZklNMHR6Z2E5RjZNS29EbFJFeUNPTFpRcG52U2loWnFQVXM0SmppallPQUw2SmRSMzZIRmR1Q3gzZmpjYVA3b3lDSGNKUEZjcSt4YWFWbjhpT3czc2pqZ1A4U1pXT0tXVS9uNTZsdFFhVERjV1ZTMDV0d3gwVTFOTzErV083eWZZTm42dm9pbHVhMkJOWmFTRnpXcFhHc2ZOMzIxNGM3ejUrcy9peVJwbitrK0EvTW9EK1psTExhNXlrbHBlYlVNdkxQVXN0cnhrMXpaeGVXdncvcWVYRlg5Snd0bUxlYitpTEdYTHYzdFc3SVR2THUyaEc3MFZsN1oxZEQxOXkvdDExc2RjekJINXg5ZFlkZWRuK3JwbkxkNVhSMXpUMC9yeGFYaWdnYjJXWU8yMUdmV2FXUVo4azZsTlRYUnVYTE5rL3A3WXUvbHFHbnNYelovcnlqUHBrVVdlenlpOW5xSTdray9VRGpMWVJQOHNOb1h5NjdnMWtZNVlaRk9pemJTeDl0azFwMEV0WUJjbEhlUUYvbUR3RXJGYno0ZzhCMnlZMDJKYkZCRTBXbnZFL2ZQaG5WTmRYdDYyWWRuaUcwZVJMTTNoYm41LzNxMk92azhPdksyMTR0QzlJT3R5L3ZqeGZWNUNSbW1rcGJuamtPQjZnV3ArbjFpRWJZZTRYczdkQ1pubnRZOGswek1ycW5VRldzamhTNGVPNFlBcy9icjJEdUl2QXhCSHlNZ1EvWnMzQ04yWll3bUtGL0VTMHNneVpRcFBiWWhuT3hIZ3l5U3JGR0R5cmRNckhqckcvaWExUlFMeFVFNFJmK2x3MHJGNUx2bnpHM3VvSmpoUVJKcmlEQTJ2T2g1Q0tQNVVWZitRdk5LQmlkNncrUmQ2dkFidzVVeDB4K0wrdEkrNkVDVFZJenhncmlvdktrcVhuNitQdFg0UFloQzJMNUw1Q2xwWmVSdXprVlNITWw3R2E1MWJaWU5VNklzeXpIRlZISy9KRFJscEluTFJHR0NzaXluMncvZ0RNT1RTeFFLaXU5azlXSXFTclJPTktoR20vMW9WRHVjVkpSMytXVkpvYkNtbGZNTk9aaDhoMisvWDNpU0ZQZy9IZXc2dnBRYk5LVHNEbDhlRVRVcXZQNHdva2tQVWsvcDAxSTB2S1ptYkdhbVF6WWY2WEEzMW5xUk1HLzVkMVF2MDU2NFQyaW5GMXd2ZndsRkpxaGI4ZzI1NXZ2bTZMdDRhVjRCblMrN1BpWmNMbWQvNjlRcTZueWRSTHIwZ1B4aUlRSTBteC9RVzRRdDMvL1BPWUhrcXJxUjRXa0Y2Qm9JVTJpUW1LV0ZXN0l0MWhvSTM1VkxRRktNOUhBV3BpQ1I0YkdmcThYRVU5VTNFT25heVgxazdaOGJOTi9sQlp6NWJ1R2RMQmhrVEZ6TUNHemtURkhINXkzNUZaSEE0V1RtSDU4cjBIbUxkaW9ueUxLWW5KOEFSTU5nTm9DS0liNUg1dnYxd2c3STgvNTAzTGc4RXh6M25MejI4RzRrUEhsQktENTM0bWZPSzRUdm1oOEVuS2poTWZDUi83a09jL1hNa2p0K0hQbExLampaUWRWMHBWU3RueERjSU1sMmxrK1FNMFpCQU91Sk9adTI0azMvNUQ0Y0VqMGtuMmoveFNTQ0RXUlhYbGtPUWE2TFBmY2o3c2lEM3lUUlpBbWRWMEJaM01ucnpJSStvbHI1UkFISS82NHNOQTVPVEJNdUpGTWRNUnkwMktDM096TTkwWmFRRXg5b1FiWUFjUHRnbWlsVVRYWkN5WGFteEtUVFhTZ09Wbnd1VTNrc0YrSWFhNzdBc2c1ZlVEeFJ6TGI5cTlhd3ZXNEwzVWhiNzJNYU5uTHIrZTdCNjREUFBNUjYvelMwbWhzWHI3cXNhTGowVjB3ZXMyMnZRRGh2VGRXOG5SUngvMW03YzdrN1pzSVY5MmJiWG81cmdOUTJUaEVETU82Ump6Q04rUERLamdwNzJmSWY0aUNHdENpd3R6blU4TzhueS8yLy85ZzRUandqdzF2djFkT3NrNUtNOVhSM1Y1Y0Q4cmhnQWQ0emtNWWNsTHArUUhKNUg2UnA0Y1R1VTVyZDdFaHdGZTYwVHltODVZd3ZOa21lZmxrVUIySUZ1VVZ5WEdjUmoyUFRqRzdFUU9rMklaTUw5QU5UNzgzVWNNank4N1FIUHR5NEhKSDlNbmdxN2RDNnpmc212M0pwN2xpZ2ZXazBQODBxRWhnM3VPenJKMUYySHJsaTFKenUxbS82T1BraTliZDZjYkJ2UzJqZGNGZFpGakZ6ZXUybDR0VjRFeHVnay95SlV6SDRQdU45UDY2QlFEc0RjVGxJbGdPcDQ4N3pjSUpzU0FUZzZTUnl0UUoyRUFxU2dTQmhDU0VYMTlTUkFGZklHd2ozWjlLM1ZpK2pUQkdNZ3lwbU9QRkFqeGg2dWoxWTNoQlROVGJEWnJwbGg0Uld2MXFxbVZjMElKQjVpUGM3SjhtZk5UVFdsT283NjVLeWZMNjQxOUlYbk90OHlWYkVqcEdhMmdGT1J4cEFMRkF1QWlmWWVJNlZUeVdnWjFUSkxXMHNtZUk3VmRjbWxUMDZYTnpYUWJuaGFPL2VlR1lvZGh1ei94RkxDRUcvMXgxTWY5SG5UWmhRcFJLK3BBbStqOFZubUF3KzJZMDA3RmdvNXR0bW9aWmc1NUM4dytZRGEvRDNGYW5aYlREWkluRHBFV283Vkl5NG5hVHNDZ3JFNkRCVkVuOUNHdFZseUJSSzA0dDYydHFLaXRvNjJqcUxXb1pVNmozeDlLUzgveis0ckowZytsaXppdHNnZ2d4SGlicE54RlFUYUJNUy9vSW9JeUt5OVNVSjk3b1JwWW9ieUwwRlRxVDJVWms4VXFUY3ZKK2RVMXhpUjdzc0grbzlhUWJMblRhbUdhamNQclJhM2RhalN5TjVIUGpSYUxwU3ZEN1haSUwxdlNCUTJ1Uy9aWVhmbGRiL0FmTVMrbGwwWHdHM05FcHpYWm90L05tMDBqdjA1MzFGdFNOU08vNVp3V3MxbkxGSFBPRVdlYTA1bCtGTzVpT2VyTlRFN1Y0NEZVczhNaVhZMTEwcmVnaU1EYkxPNTFoYmZMMENqbGJMSUhKRDhkY3lJamMxVkdyVFZ4NW1yZ25GN2s5T1JSS3AxT3Z6bUJ5VWprdEdJZjBnbUNiaEhTNllRZUpPaUVkZ1hXMXA3aEZxSmV0K3ZjOTRoT1RSU3ZxQkU1elNEUzZFV05mdGRQdmdrcDNSVVZGUzByV3RwSkV0YnNjbG5TaHYreHBDR2swVXNxZ3NvN1RvU3hMem1oamlwWkRvQS9XZW9yTXJJbGYxWUd0aFhsVHEwUHpIU0JBbVNZaW5mWGJkbzlkZVlyMkpEaG5sejRtOGNKZi9nV3EzVm5mbTJtL2N1czZkbkZWYWJraFRhcjFYWkptdDRiMkxvaXVyN3FuaWxXSzlnWHNsRDd1Z0NjYlFzNkgyMUMzMUV0eUNqQUFnOE9nSnNDU1ZjS0JNNU5XR3RjRFl3V3dNT25nalJiMVJlcmFMRDZaaFd0VVdmVTZnWkpod1l2aUh3OG9JSURNVEtvejRTTjJpUmpaekxXR2JBK1NhY25CNHhKSzFDU01XbXVJem8vOXFZV0RZQU5EUUViNUxhN0pyMnQ1aWZldGpNYWFBWGN0bkZENi9tdDU2M3NYYjYwYzlHOGpsa3o2K3RJYkFrRVNpTUJlNDRaa0Z6TWdkSG5TNFV6dk9obDh2ZThFRUdqQ2UvcU15ZGtXWlA0QXJZMEZTL2RWTHU4b3U2S3krcDJGS2VLUm9lb3plbkpiNXJiTmljdllEWjdaemJPbVRLdGtzcSs2T0lhVmtjVkpLNG94dnd1eXlUZVlmUVBQSDlCU1ZmMXF0TFVlZlVydHpnZE9wc2hOY3phMGl0S0t2SWphYTZpc3VLU3RESXIvRnVhb1hXNVJ2N3NOSTlSRytrWWNRK1RlQTFwR2RiSmNaL1dhd0J2WmhMTXJNY01mUlJmMFFDMThCQ01MWVBtMDNmcVpDSzNQMkFQcXNXRnlSZ2NiNzVhN3pyMnEzblB0M29OYVQ2VGNjYmhhU3ZhSkJrV1N3UUpEbTg2L2toRHNTVXpOYU5BbDErK3ZwK055cmthSTNKdHpLLzVlUUJsd2xTRGxmZG5kU2E4a3k0QjZNamhkY3pUOHNleXNpb3E0SStmNXdyc0Niam9ScWxGendaNkhTaE1GN05WQ2hOTEtPZXVuOFNlNTNsZ1hQMWtoSDdNanlmUDhSVWp1T3YvQTJBK2hmeDQybzJTVVd2Yk1CU0ZqOXkwWXc4TmcyMHZmWmtlMDBHdHBGMmhOS3dRQW4xWm9jMW9DM3RNTTJHN0pKRWp5UStGL3FuMVI0eXh0LzJnd1k1VXJVdkRPbVpqNjd2WDl4eGRTd0x3QWw4aGNIOTl4dmZFQXB2aVErSU16MFNWZUExdnhKZkVMYndXUHhPdll6TlRpVGZ3S2lzU3Q3R1YzVkVsV3M4WmZZc09nUVcyaEVxY29TMCtKVjdEa1Zna2J1R3QrSkY0blQ0dkUyK2drNzFQM01hNzdCWkRHTlM0Z1VXRkFpVThKSGJSUlEvN3BITm1OTWRRMWNRYXpiZkVXZVJaL0JiWTRKbzhpZW9CS3oxMWhubkh1Qk5kUFdkeE9JVGlYVkFiS2hwY0lhZkswRWxod2Rnd3J6bk9sNkl4bFVHclZycjQwOE0yWFRBMDlZMnRpdExMM1c1dlg1NlhXZzVOWXl0dDVabXRacHB2YzYwblhnNGFYeHJyWktmMHZuYUhTaFdWTDV1cmZHSm1hdEVZcjV0NUhNWjE3VlN5aUE3YllaWW5Gd0tQWmdNK01sZXdkc29mc0F4MTBVekhoRDAyRzViM0FIMk1jTUZuUUhycTEzWldmZmJ5YnUrZ1A3b1lEZnJMdmUwOCtQOXJxMWE4SHEvUGc4TmxWRHFxRERkQ0xuV01TMjFkWmVZeWRvSC83L3J2cmY0K0YvZW53dkVrQklPYU9jY3BRd05UanVFY0ZmeCtpbU9jVU1SZDQ2YTVpYTFxNzNKWFRYTmpDM1Y2ZklKZjMyS3pLSGphWllyWFRzSmdBRWJQWDBZUm5BekZMVzVSc2NWWlYxd291QVVucUtVeFlDOElOUVZqdk5Wbjg3V01wb2t4MFhOenZweDhTRGg4ZnZEMkxjRmZUS2RLdUhEandZdU1qd2I4Qkdpa2lXWmFhS1dOSUNIQ1JHaW5neWlkZE5GTkQ3MzAwYzhBTVFZWllwZ1JSaGxqbkFuaVRETEZOQWxtVUZCSk1zc2M4eXl3eUJJYXk2eXd5aHJyYkxESkZ0dnNrR0tYUGRKazJPZUFRNDQ0NW9SVHpzaVM0NXdMTHJuaW1odnlGTGpsam50MGloaThDMG00aEZ0NGhGZklJYXRhMG1zVm8yYnFaZXZaVHBSdDR5SDQyK292bHBNaWRkTXUvVHZLajVYWEoxUFRmSTVWUmZrWjZoY05SelZRQUFFQUFmLy9BQTk0Mm1OZ1pHQmc0QUZpSlNCbVltQUd3a1FHUm9Za2hoUWdMNVVoSGNobUFjc3dBQUFuMUFJMWVOcGpZR1JnWU9CaUNHRklZbUIyY2ZNSllSQkpMMHJOWmxESVNTekpZOUJoWUFIS012ei96d0JTaGN3V1kyQjJkZ3hSWUJEejlmY0Jra0grdmtBU0xzdVlWcFNZek1BQllvRXhDMWd2STFDRUVXZ21FOUErQlNESnhzREhrTXpBekNERUlBcXlIVWlMZzlXbXdObE1EQ0lNWWdDMXRoTVplTnBqWUdSZ1lPQmlzR0d3WTJCMmNmTUpZUkJKTDByTlpwRExTU3pKWTlCZ1lBSEtNdnovRHlTd3NZQUFBRnNhQzJzQUFBQUFBQUVBQUFBQTFhUW5DQUFBQUFEWm5JUGhBQUFBQU5uN1NVYz0nKSBmb3JtYXQoJ3dvZmYnKTtcclxuICBmb250LXdlaWdodDogbm9ybWFsO1xyXG4gIGZvbnQtc3R5bGU6IG5vcm1hbDtcclxuICBmb250LWRpc3BsYXk6IHN3YXA7XHJcbn1cclxuXHJcbkBmb250LWZhY2Uge1xyXG4gIGZvbnQtZmFtaWx5OiAnQ291cmllciBQcmltZSc7XHJcbiAgc3JjOiB1cmwoJ2RhdGE6YXBwbGljYXRpb24vZm9udC13b2ZmO2NoYXJzZXQ9dXRmLTg7YmFzZTY0LGQwOUdSZ0FCQUFBQUFFQ29BQklBQUFBQWRQUUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFCR1JsUk5BQUJBakFBQUFCd0FBQUFjaVR2MEhrZEVSVVlBQUQrNEFBQUFLQUFBQUNvQS93RTFSMUJQVXdBQVFGZ0FBQUF5QUFBQVFCYWJLSmhIVTFWQ0FBQS80QUFBQUhnQUFBQ2laNGR5eFU5VEx6SUFBQUlNQUFBQVR3QUFBR0J5QXBLMlkyMWhjQUFBQXhnQUFBQ3VBQUFCVXNSdFd5SmpkblFnQUFBTFlBQUFBRDRBQUFCc0o3RVJWbVp3WjIwQUFBUElBQUFHOGdBQURoV2VOaFBPWjJGemNBQUFQN0FBQUFBSUFBQUFDQUFBQUJCbmJIbG1BQUFNZEFBQU1Ja0FBRnE0aUs1eE9HaGxZV1FBQUFHVUFBQUFOZ0FBQURZWG1ocFFhR2hsWVFBQUFjd0FBQUFnQUFBQUpBc1BBZTlvYlhSNEFBQUNYQUFBQUxvQUFBRFlLdWNaUG14dlkyRUFBQXVnQUFBQTBnQUFBTkpZZWtKT2JXRjRjQUFBQWV3QUFBQWdBQUFBSUFISEFoRnVZVzFsQUFBOUFBQUFBY0lBQUFOdit4OXFnbkJ2YzNRQUFEN0VBQUFBN0FBQUFVbGtmY1R5Y0hKbGNBQUFDcndBQUFDaUFBQUF2VnF4M3pzQUFRQUFBQU1FbXdpYmlRaGZEenoxQUI4SUFBQUFBQURabklQaEFBQUFBTm43U1RULzJ2My9CUElGcEFBQkFBZ0FBZ0FBQUFBQUFIamFZMkJrWUdCeitPdkN3TUJ5NXYrdC83ZFlQakVBUlZBQUN3Q29HZ2NHQUFFQUFBQm9BRzRBQlFBeEFBSUFBZ0FzQUZvQWpRQUFBSndCRlFBQ0FBRjQybU5nWVRuRHRJZUJsWUdCMVpqbERBTUR3MHdJelhTR29ZbEpDOGhuNE9Ca2dBRm1CaVFRR0Jyb3lMQ0FRWUZoQTV2RFh4Y0dCdlljWmdVRkJvYkpZSVZ6V0JZREtRVUdaZ0IwbHd5eUFIamFKWTZoaXdKeEVJVy9BWlBaSmdnS2drVUZteUJjRS93elZvTkJPSk5nRXhHTDhXQnQ1eG9VWVMyYUJGRmsyd1dEV2N3SEJ5YkQxcDlQYng3dkc5N0FESk00NDZOS25QOXRQMnlwc0pBN2RqS3pJa2RDOCtTSWdERjdadXpvczJIT2dUVlRpNnluSFBMRmhheUxxZE9tOWxaRFYwSmFZbzJrK0tIK3NrK1Rpb3ZkblF3RkpwYXpFcEc3V29wUDBnendHTEVTeTJKQWxXLzNFTHZrTlJ2b04wKzNDdHF1djdaWjJoKy9ETG01dXhRVEtLK2VOOGs5TVFBQWVOcGpZR0JnWm9CZ0dRWkdCaER3QWZJWXdYd1dCZ01nelFHRVRFQTZtcUdPWWNQLy8wQ1dBa01zaVBYLzhmOUgvemRDZFlFQkl4c0RuTXNJMHNQRWdBcUFrc3dzckd6c0hKeGMzRHk4ZlB3Q2drTENJcUppNGhLU1V0SXlzbkx5Q29wS3lpcXFhdW9hbWxyYU9ycDYrZ2FHUnNZbXBtYm1GcFpXMWphMmRnejJEbzVPemk2dWJ1NGVubDdlUHI1Ky9nR0JRY0Vob1dIaEVaRlIwVEd4Y2ZFSkRBUkJJZ05OQVFBVlRSK1lBQUI0MnExWGExc2J4eFdlMVEyTUFRT1NzSnQxM1ZIR29pNDdra25yT01SV0hMTExvamhLVW9GeHUrczA3UzRTN3YyUzlFYXY2ZjJpL0ptem9uM3FmTXRQeTN0bVZnbzQ0RDU5bnZKQjU1MlpkK1pjNTh4Q1Frc1NENk13bHJMM1JDenU5cWp5NEZGRXQxeTZFU2VQNWVoaFJJVm0rdEdzbUJXRGdUcHdHdzBTTVlsQWJZK0ZJNExFYjVHalNTYVBXMVRRcXFFYUxTcHFPVHd1MXVyQ0Q2Z2F5Q1R4czBJdDhMTm1NYUJDc0g4a2FWNEJCT21RU3YyamNhRlF3REhVT0x6YTRObnhZdDN4cjBwQTVZK3JUaFZyaWtRL09vekhxMDdCS0N4cEtucFVEeUxXUjZ0QmtCTmNPWlQwY1o5S2E0L0dONXlGSUJ5RVZBbWpCaFdiOGQ0N0VjanVLSkxVNzJOcUMyemFaTFFaeHpLemJGaDBBMVA1U05JR3IyOHc4K04rSkJHTlVTcHByaDhsbUpHOE5zZm9OcVBiaVp2RWNld2lXalFmREVqc1JTUjZURzVnN1Bib0dxTnJ2ZlRKa2hndzQwbFpITVR4TUkzSjhlSTQ5eUNXUS9pai9MaEZaUzFoUWFtWndxZVpvQi9SalBKcFZ2bklBTFlrTGFxWWNDTVNjcGpOSFBpU0Y5bGQxNXJQdjFSTXdnR1YxeHRZRE9SSWpxQXIyeWczRWFIZEtPbTc2VjRjcWJnUlM5cDZFR0hONWJqa3ByUm9SdE9Gd0J1TGdrM3pMSWJLVnlnWDVhZFVPSGhNemdDRzBNeDZpeTVveWRZdXdxMlNPSkI4QW0wbE1WT1NiV1B0bkI1ZldCUkI2SzgzcG9WelVaOHVwSGw3aXVQQmhBQ3VKekljcVpTVGFvSXRYRTRJU1JkR1RxeEVhbFc2YlZVc25MT2RybU9YY0Q5MTdlU21SVzBjT2w2WUY4VVFXbHpWaU5kUnhKZDBWaWlFTkV5M1c3U2tRWldTTGdWdjhBRUF5QkF0OFdnUG95V1RyMlVjdEdTQ0loR0RBVFRUY3BESVVTSnBHV0ZyMFlydTdVZFphYmdkWDZlRlEzWFVvcXJ1N1VhOUIzYlNiV0MrYXVack9oTXJ3Y01vVzFrSnlFbDlXdmI0eXFHMC9Pd1MveXpoaDV4VjVLTFk3RWNaaHcvKytpTmtHR3FYMWhzSzJ5Yll0ZXU4QlRlWloySjQwb1g5WGN5ZVR0WTVLY3lFcUNyRUt5QnhiK3c0anNsV1hZdE1GTUw5aUZhVUwwTmFSUGt0S0pRY1NyR0dtUVEyL09mS0ZVY3NpNnJ3Zlo4alVZTWhXTXRxc3g1OTZMblBJMjZyY0xidXRlaXl6aHlXVnhCNGxwL1RXWkhsY3pvcnNYUjFWbVo1VldjVmxwL1gyUXpMYXpxYlpma0ZuVjFnNldrMVNRUlZFb1JjeVRZNTcvSzFhWkUrc2JnNlhYelBMclpPTEs1TkY5KzNpMUlMdXVTZDV6RDcrbS9yS3p0NjByOEcvSk93NjNuNHgxTEJQNWJYNFIvTEp2eGp1UWIvV0g0Ui9yRzhBZjlZZmduK3NWeUhmeXpiV25aTTVkN1VVSHNsa2VoK1RoS1kzT0kydHJsNE56VGQ5T2dtTHVZTHVCTmRlVTVhVmJxcHVNTS9rK0d5OTErZTVEcGJySVJjZXZUQ2VsWjI2bUdFN3NoZWZ1VkVlTTdqM05MeVJXUDVpempOY3NMUDZzVDlQZE1Xbmhlci94TDh0MzFQYldhM25EcjdlaHZ4Z0FObjI0OWJrMjYyNkNYZHZ0eHAwZVovbzZMQ0I2Qy9qQlNKMWFac3l5NzNCb1QyL21qVVZWMDBrd2d2SU5vdm5xWk54Nm5YRU9FN2FHS3JkQm0wRXZwcTA5Q3llZUhUeGNBN0hMV1ZsSjBSenJ4N21pYmI5anlxNERia2JFa0pONWV0M2VpNEpNdlNQUzZ0bForTGZXNjVjK2pleXV4UU93bFZncWZ2YmNKdHp6NVBwU0FaS2lyamRjVnlLVWhkNElSYjN0TjdVcGlHaDBEdElNY0tHbmI0NlpvTGpCYWNkNFlTWlp0ckJaY1l5U2lqNE1xZk9SVW5zaEZOTnFLSTM3eWxmcW9MaGRDWnhFSml0cnlXeDBKMUVLWlhwa3MwWjlaM1ZKZVZjaGJ2VFVQSXp0aElrOWlQMnJLRGw1MnR6eWNsMjVXbmdpcE5qTzZmL0lpeFNUeXIydk5zS1M3NVYwOVlFa3pTbGZDWHp0TXVUMUs4aGY3UjVpanUwT1VnNnJ0NFhHVW5ibWNiVGczMzlyVlRxM3R1LzlTcWYrYmVaKzBJTk4zeG5xVndXOU5kYndUYnVNYmcxTGxVSkxSTkc5Z1JHcGU1UHRkczVGTjhxZm5XZFM1UWhldlR4czJ6NSsvb2JBNlB6bVRMLzFqUzNmOVhGYk5QM01jNkNxM3FSTDAwNHR6T0xocndIVzhTbGRjeHV1czFWQjZYM0p0cENPNGpCSFY3N2ZGWmdodGViZE50M1BJM3pwbnY0VGluVnFXWGdOL1U5RExFV3h6RkVPR1dPM2lCSjlGNlczTkIwMXVBWDlWaklYWUErZ0FPZzEwOWRzek1Ib0NaZWNDY0xzQStjeGc4WkE2RHJ6R0h3ZGYxTVhwaEFCUUJPUWJGK3RpeGM0K0E3Tnc3ekhNWWZZTjVCcjNMUElPK3lUeUR2c1U2UTRDRWRUSklXU2VEQTliSllNQ2Mxd0dHekdGd3lCd0dqNW5ENE52R3JtMmc3eGk3R0gzWDJNWG9lOFl1UnQ4M2RqSDZnYkdMMFErTlhZeCtaT3hpOUdQRXVETk40RS9NaUxZQTM3UHdOY0QzT2VobTVHUDBVN3kxT2VkbkZqTG41NGJqNUp4ZllQTXIwMU4vYVVabXg1R0Z2T05YRmpMOTF6Z25KL3pHUWliODFrSW0vQTdjZTlQemZtOUdodjZCaFV6L2c0Vk0veU4yNW9RL1djaUVQMXZJaEwrQSsrcjB2TCtha2FIL3pVS20vOTFDcHY4RE8zUENQeTFrd3NoQ0pueW94eGZOSnk1VjNIR3BVQXp4M3hQYVlPeDdOSHRJeGV2OW84bGozZm9FOWFBRCtnQUFlTnBqOE43QmNDSW9ZaU1qWTEva0JzYWRIQXdjRE1rRkd4blluYll3YUVzek0yaUJtTnNOV0JRNGhOaVp1U0E4RXlZTk5rbFdNSS9MYVErUEE0Y0R5d0VHWmdadUlKL1hhUStEQXhpQytEdUJKSVBMUmhYR2pzQ0lEUTRkRVNCK2lzdEdEUkIvQndjRFJJREJKVko2b3pwSWFCZEhBd01qaTBOSGNnaE1BZ1MyR3pFcHNZbXdNdk5wN1dEODM3cUJwWGNqRTRQTFp0WVVOZ1lYRndCOWxTNEhBQUI0Mm1OZ0lBQ01JSkJsSndNRDh4d0dobjgxQ0JZakR5TVB3Mk9HeHl5TEdSaFlGV0N5LzEreEJqTnYrdi9xWHhwTUw2c1o0Mk1ndmdnQTFsRVZMZ0FBQUFBQWlBQ0lBSWdBaUFEY0FPb0JrQUpFQXVvRG5nUGFCREFFaGdVSUJWd0ZqQVc4QmVJR0pnWnFCcndIUEFleUNCWUlnQWpvQ1VRSnNnb1lDbG9Lb2dyaUN6QUxjQXY0REp3TkVnMlVEZm9PWWc4c0Q4Z1FSQkRZRVNnUmdoSXlFcVFUTmhQQ0ZBWVVmQlZFRmVvV2VoYldGendYbkJnY0dMUVpLaG1hR2RZYUVocGFHb29hdUJ1RUhEd2NwaDFXSGJRZVBCN2VIM1FmZ0IrTUlDQWdlQ0VjSWE0aDlpS1VJeklqM0NSaUpNQWxRQ1dnSmg0bXNpY2dKNVFvSmloY0tPNHBaQ21zS29JcmtpeWNMT2d0RkMxY0FBQjQycTE4Q1h3YjFiWDN2Yk5vdDJ4dGxoZkpzbVpHa21WWjhpN0Z1eEpudFMxbnQrUEVpZVBzRGxrZ0lhd2htSWFrSlFtVVFLRXBCR2hKZ0s5QUE0U0drQkFlYTF2YVF2ZW1mWlFDNzlIU1g3cTk5eWp3Q3NTVDc5dzdNMXBzaC9DKzcwR3NHYzNjR2QyejNIUCtaNWxCTExwTC9pUFh6VmVpZk9SQVRhZy91U2dlRllzNUhZZDdlTXd4T29iVGpacjBqSTZGZjdzTUdDT0d3OHg2STJZUll2dGh3NkloMkVOem5jNkNBb1NjVGM0cERYVVZRVjlaZ2FQQVliZkJYZk1helRwM0JCVzZXS2RPOUF2QlJrZER2TjdQT3Z4c1BOallrSEN3OEJtdnJ5dDBsK0oyREZ1WFU4ODY0Rk1uQ2lFejFvbGN6TXQ2aGZNL0ZzaUdiWXd5WStYTW5SSjc5aXdqdU96Ri9JTVA4c1YybDhDY1BjdEtycUR4d1FlTlFiN1NGL2kwTStEekJmam5BNzVQL2Z5MW4zNzVZMXNlcDhQMzRFT3MzbW8zbStTbmNjcGt0bHYxckx4QlhxZmo4bXdPbkpLZmRpQUd2M2JoWTVialBrSVdWSUo2dXA5MHoxdVNkQ09FOEJDSE1aWlNQSkRNRENPR0VabmUwcVFMRGdMNUdJMWtIeDlJMnZQeUVNb3J5U3QyMnVGR0prbG5JQ3pRczRRb05oaHZ3VXloRnhNU2cyMFlxR2YrMDhrMDhTdFc4RTJNMC8yK2Y4NmNCUXZnai91b3FHUnNhM016YzdDazZQeGlyM0JXOE5JUG1NMkZDK2dwNWdIT3ozMVVJQ0tUL0FGQ0JTd3lZU3NpL3pHbzdzS2Z1WHU0VTJnaDZrZExrLzF6cHpOR1U2Q0VZUm1teDVhdlo3R09ZeGdXeEdqQkpsTkZ5bXBnRURJT0ZlU1pXYU14UUNrTXM3MkxGaUcwcUg5UmY5OWl1TTJDVlBmc1dkT1NiUzMrWUVCMGlVRi8wRzd3UlZBWmRqbXRPSUwxOVhYcFhTc0dxaG9iT3JDWXRTdkVjR05ETzI3QmlheGRWZHo1dUQ1ckYwYm91ZTBsZVhrbFJZZmJiaXlpTzZlU1hLUXNPZ2NuZnEvdHJGRk9QTkI2azdKenBrMDUwZmkydHJOS1h0NzYremIyY1h0TmRYV043Wnl5K2JqQVZsNmlZMytsYlcza3FQMmNzdm1yY3ZCSDJsYU9uenNIbW4zMHdtNHV4cGVqR1NpRkZxRnJrKzZVazJjNWpCYjJUSEZ4UEY2VXFBaHlETStDcXBTRHFwVHBRQjh3ai9BSTRtR2hzRHd6Z2xoV1AyekFlcjNFZ3NaSXNJZFkvY0RFY1dRSU93em4yUGtEU1ZoTDhJdlRQWUVLRWY2TUJpK29qeGNYdXBXMW91aE9LQmh5RmJvVnh1dGRxamJCc1l4ZTFibmhpaGdPQlFuSEUrUmFSdWR5a29Pb3NZRmN6bnc5V0Z0VjI1R01SMm9ibmNrVjE2WG1MZTE3ZUVjd2tRZzIxRFluay9IcTJyYkNsdlZUUnlMN2xqMndOcGk0cFZaeVNUaGM2UW56NVI3eEJYdXBpYWprTHdXdmE3cjNEbXU1LzZyaFpWL3A1YjRyZWp6aTY3WXlBem41anIvTTArMzlscW1zcU9kbzMraE01b2pva1hzcnZPVU9NMy9iMkc5bitGMFczVGVBVmo2dHMvbElSTldvQTNXalRjbVJRc3p4NWRoZ1pIcGdaZktZNFVjUmE5QVpXTjBvNGhEU2MyakVndlY1MkdqUUcwZk1tT2Z4c0FsV2FVVUtHUXk2WWFUVGhYVzl5V1JOalNRaGxPeE9kczJjWHROUjB6NGxMbFZMc2NvS1Q0bTlBSDdPR3JTUzFhbndVVlBQZW82WUpHS01NT0VtNFdBQ2M4Qzh3dnE2ZUdORFVCdy8zb296NS9CdHU3cTZ0SC9NdHgxV3NiaXE4UHlkYnB0VkxJcTYyYzFqcytyckpRbittT3lCa25xUU85V1ZkWFNqdXlUcWNSU2UveGVYdTZTbTFPWm1wN1VwdzZSNnVTQjc0SFBhWVZqL2x3RXZyd2RlZHFJZWRERHBzbUNFZTlwY1lLQzZnd3pITm1DZTQxVFRWZ0ZheUlCUkg0V3JXSTVoUnhERyttRWpxR0pGeW9BNWpoL1dBVnRGSGpTMzdsSkRoeENNcExzYTc4RVFJdFExRytZeFRZeUx3V1lwWkNLYUREcWJ0bjVCVVNCYzllRjRnaGlGdEIzUjZkMFpveUpVRXlrUVRzY1RWSmVwSGdPN0V5SG0zNDhWdXBxVDdiSFpzNmJNbk5Kd290U3BMM0s5cFZpRlphVmx5MUxLN21NVjVWTnZlbUhrL3I2bFN4Y1BQcjdqRmYrMFJHL0hLOXlwbFJhdjYzdUMxeU91azJhMzFDeVBQeisxelZsWVVGVlpXV1ZMSlZmWXlFNkJ2L082L252WEROM1plczNPMVllWG5CL3JERGROYi9zeGNBTy93RHpBT3NCWFdGSGJDU013R2F0Y3RWQ0h3UkNIZ1lCemRvWjRDZHhQRHFCaDJFT3d3azB3eG9vc0VrdVVUODlTV3hraXpyQUZzdzc5SEw0eUZxdms1K0RLVDdtUDZ1Unl2eWo2OGJ1Y0lVanVqTEg4Q1BzQXZ4NzUwRFRsQjgxd3VESUZaMEs0dDFTeFJHYWsvQmlxaEVQRW5zRFhBWEwxTVB3K25qOHdjTUxsTEdmSWoydWFybU5jVGp2ZEk1TUp4VERUMkdDUEoxaWIxVjNybE95dnZmNzZhM2JKV2V1Mld2Zi82ZmJiLzdTZlh4L3d4Y09sbGh2azU4K2VsWisvd1ZJYWp2c0NocmwveDcxdnZJRjcvejZYempVS2MvMXg3bHd4aHJraUZFS1p1U3J6d3BXSXpwVndhd0JsbURWd3d1dXBvSE10dEx1Y2pFNmZYcE54ZTJNRFEvZUlDM0V6aStqTXJCTm16QmY4WFQ3K3hodnk4Yi9QTmFpenhwMW56K0pPYmRaa0J1aDV2SnZMaDNYVGdoWWw4NmN3RE9JYXcxNGJtQlhFZ0dSZE1GTUhFU1hlQzlDSXEwaUIzMGNSTW1NWDdIR1lRM2lVaVBobWVwWUQ3UWNRQVBkcXJnNVdoM1NHRWdLQ3dNVWw0aXJEZGZtWVdtOUtUYlhpT1FrcDhRNGNJcnBPU2ZKUjZ3MkcrNEVPcnZycGNrRklXQTNOMVQrNzMrVk9CRVBsamRhRkM2Mk41YUZnd3UyNi8yZlZ6UVpyUWhES242N21PcHE0VTIzVnR2elhOem1ySXFYTzZCVGVjWXNqNm82SFBTSGhwWmVFa0NjY2QwZmhFRDhsNml5TlZEazN2WjV2cTI0alBIZ1U3ZU1FamdIcFJKT1ZzUGdSd3crQXUyTXhaaEJlVDZ3QmdUazhNNTlLTUJpVXBLQ2tONVJTQTJyenEwdFc5TnMwNDJqemF5YlNiNk1yOTY0YUc4NVRWcVg4RDhYMXloOHEzN0VGL0RUSGtETWZLaDViL29kNkprOFppUzN3bmVyVnNQd21XNEJYSVJzcVM1YWE2T0tqZXRPZjBadFFrREVVVWE1VDVFWGhKakV5akd6WC84M1pGNHpnTlZ5cDZ4OTRsVDAvUDMvc1R6V2VZaVBIbERsY1ZCY2V4V2M1Z1RrSjkvY2xQZGtMZUlpY0pib042RGJPWnJtT0RLSHNaM1RTWXpwbDhzeW56RW1GSElVSU92K1hBR2VhOFRhVWg0cVRoWnBsQU4vWEM1OTV5QktnZDg1RmljLzM5dmIzd3gvZTVoVms0bHhsQ2dZeGVrQSt4RVg1cThHWmRUOWpBcldsaHFpVUdDSnk0NnpGSnFuSEVONmpIa3VhMGwrdkdsQ3NFbkdKeXE5cjdvODR2M2c5KzR0bDNOZzZlN0p6R2NmY1kwL3lWMWNKWnVNbnh5SmtvMXNRQWJld0Ivek9MT3JEUzFGVk1reVFKQjdtRkk4TTB5SUVobEV2Q1JRS1NndEtDcDMwcDNTWmRRMC9SVzFPampkbFBubnp5aXZmdlBOTytybGg4K1lONUk4N2RaOTg3cnZmbGM4ZFBvemQzLzB1ZHQvMzN2ZGVmUEhWVjE5ODhYdkFqOU1JY1ZYY0dSUkFOY21vSGVBVjZBWjhzQXdHL01CV3BIaU9FTDB5emU4QWtzSmlNRTdXcURST21DM1lsclkyOFVTQXJGMlhyWjdqRlFGTGlvQS8vcm5kNmhEdFRvY1RQK3p4ZXFXL3ZxRjREc1dSTUE5ZWJaSkNWVjZYeC96M2d2THk4L09wek82SE9ZS3ZSN1ZvMHdrSmN5d1JXUUdJUjBLd0R3QnpsR3J6NVRCZnhRZFhFQ2t5SzdYSUk1QTFES3pQcnNuSERTUkpTRkNMYXFTcVJ0R3RMVk9uVG8vOVdValNyN3BXQ01BSXc0VTBtS1FtaVBuZHFhRmxxK1gvd0NXeDltUnptWGorVXlEYVpNWGZXZGd4cjZlL2p4eU1ERHpieDUxYWRuVEwya2VINUU4R1JZOVgrRUR3QVE4cUt2THdmZk5XTmN4WVZIbUFIUDFiMkYxYml5ajlKMEZYQ29IK1p0U2RuQjNGT29EQmdDcDZFT3p3T2c3SVlrbUlRbkFlQzl3Qm1Nd3JLRHBIbGVDekdUVkpVa09EVkJoV1VETG9MQ1ZSc2FYRTJJS1JWVlFKZ0FTUklxQ00rQ1Iwc2tXL3UzWGhjdmtQM3o4WXRBbVZCc3ZVZlZNM2J1cGJ0SjZnMlo2Qi9rVUx1bnNKcmJWekgxdkluWHJpb2NlNmdsOGVldTZGbENOYUdsM0UrNFM1WGJQblJOdmJZOU5tVHAvcG5rdUlmUzdxS0pkb1BIWU55TG9MYUkyaUdoUlAxdGRncE1NOWVveDR4YWdhc0U1WGtZSXdnR0ZYZ2h4RkZ1aXFqc0hvS244dzdnK0tSb09IRUdiTEFDSlhmZDBFUFcxVWRva1U2M0c5ZzYycGZselJ6c2R2VTdaalAxRzJqOG9MWU1lQno1Yk9xcGZ2KzEwQmR5cFdOZmF1b3JFUFpTdnVRN0NaV3NSMEN1TFlYa0F5R0QxSlpYWUU4UG5NWktjZUFEa204bUo1SFF2cmlvT3dhQmNNNGtFTFI0QnMvUkFSbDVCQ0hFY0Q0ekJEeEZXTm9vSWt1Z09DcElrTDlFOGZWK2pKdUhVU3V0UnJZaUtIaWVVR3czb0doQ0hQdEs1Y3VmT0pwWi85ZnVpNVhrVlc5K3dldkh6WndoV3JLaXVTall5ZjhRck1TdTVJckwwOStrNWc3WW1yZnZqVDZrcFhoSWdwdFhMeC9FR3BvRXhrZ21LWkVpdC9FMmlLYzZjQm4wUlJNdGtHQ0pjMWtWQUR2QWxReUNtMHNMQzBpT0hJb3FXOEhLSHlhSGxWUlJBdUxRc0dDZzJHWXFCSHdVK01udmh1TFVRSVVuZHVsd0tJMkRWTkcwWDJMMTZlQ1QvN1gzdWM4YjM5VzQrdDJ2NzY2SzZYcDRhanorRXQyQ0J2WDFvWDdXL3UyekM4bUR2ZE1NWG02V2VOUGJkdmEyMGFlblRMNVUrdFhyZXk3ZGphWCtMYXgweGpTeXBteDJLOXNZSHVWRDlaVjJlQW5pa2dvekswNElRVmdBdXhLeWF3SzBXd0N3QitHemdIZGdqV0dpdWtsRFZVbWl4V1RxSFJDZWNHS0pRdFF4N1JYY0VUK2loZXdTbytKTXJtVjZUV2FDTlpIYzVXa21lVWgweTFnS2lqVFRwOGpYd0hXVEkrZ1RuUEhRSE5xbldmbDl4dXZTbGFac2xuTDN1UkxCTGNSd1hCb3NkZzNuNVlJNlhnbHVyUjlPUlVwdzVRQmpIY0JoQUR3NC9vcVRmUktkNkU0elFUVUZIaDhTQlVVVjlSRjZ2eWhEeEJvUnh1VVZKbDFCeXpUcDhkcWNVVGs4UnJURlpjeDd6NzdLcSsxTkJsVzErNytlYlh0bTVjbWVwYjlleDFzeGFSZk15aVdYMkRnMzNranp1MTlON2xnemVJNG0yWGJmbFdYOSszdG15NlZSUjJEUzYvZCttYnFZNk9ucDZPanBRY1d0TFYxZGZYMWJVRWRPenVDK2ZBSDUwQ1JsWVJIWE5naGpNVGp2ZUFkV013eHdCdFBKL1dNUlVLQUcwK0gwSytLbDhrQU9FbThnWUtRNnFPQVVVRnNNNlV0ZExPSkNiR29jU1N4N0RJL0pJb2xIeFF2cTZFNk5venY5bVluOWExeGFCYXpWVEp1Rk5VbmVUVDh1RjhyT3BhOTIwN05GMTdoNmlXb21Rd1c0cGIySWNCbzFBZnoybklKVURzTWp0TWZENFlNQ3Y0SFd1cHRjVGxvR0NHK25nMUo2SDRIQ2IzVzc0S2JiUS9aa0VtM3pWMk5DZjNCWFBZQWRoUG9uUHdvY3BrcUVqeDhDejRlR1p0WmtJWTdJM1BDeWlEeklDZk1BT3F5cm00VUp2RjR6bjRNSHN1L3prUktzS2F1d2FsdUdadUtuQUVzS2lSNEttZThmRldXVG5Gb2xxc1pjVHBPQXVyenBmOWZwNVRjcFZJWXllWk9WS0pTM0xtT2M5L1dPeHlGYk1XYnFwVTJlQVRIUEpiOGxzT3dkZFFLWm53SFhrVjRUQzQxenRBdng1Ri84VUo3R0ZBcENJS0o0TWdBOEtLMWVtMFpRRDEyZ0YxMmtXN3Y3U0k0bGJkcExqVmZta2tXelR1TzNzNEc5bks4ZkU0RjkwQnZGbWs4YVlnZzlPejRydXlrSWJUZFZucEZpTk9oM1dZNndBK25QL1FxWENJbVROMlV1VVFhMkVPVVQ3SVcwd0tqN0NFSlpWSDhoYmd6YzlBWDkrSEdGMUNkZWk2cEFWMEJWdkFaNEd5cXNGNk1HMzl3QjhqZmhjeGduUXBTaW15TExsaE1EWWlSMUozNHdiQ0dFUTBieVI3MkVEU0dRaUE4dFVGYXFzcTRVZEZLVktockZvYThGRjNVSTJESFpOZ3JYaTlQUWZ2czhWdmZQMndqcWxLSktvWUMrTmZQM3ZtM0pTQ1FjS25IMnFiUGoyVmdqL3Vvek9QN0g4ZzBsZnNkaGYvdkVydnRNNXFuejZ6akVLd2Z3azdsNXlQZW9WalJIZVBxV3NIK1MrczU0NXdjZFNGK3RHQzVOd2lGMk5rSUh4aW1SNFQxaU9PMFhNamlERmpJOHNZUnd3WXdqNEV6QUw0cGRQeEF3RENTR3FIMTgzdjdrYW91Nys3YjhFOHVOR2NhREFZQzRoQkMvSG9HYWVuTEMwcVFCV0d3WExMdGs2QzVnNHpJYkZlTTJWMnFaN0pzbVVpVy9zZnUrZnVYekpqbVMxMXphSjFTKzVZdUN6ZzU0c2NycEl5YnJhaHZEallLaTU5ZFB1ZW4rOVlmSFQ3VjY0ejZLeE9vOTVpYWZ6V2dpUC9jZU1SN0h1cWVtYTFWQ2JNaUU3ajRnYyt1Zi9HVThNOUhiZnYycmIrcDN1Mnp6RHE5SzQ4K2JWeWx4Um8zOTV6MWZGVlgvMzR6aXVmSEs1Z1MvMmxOcHVkZDN2M2ZQalFpN2psR1RrMTkvcjI2dnFCRzJMckVIUGhZOEIwWjhIUEppRENuNUpzUkVhd1AwWjJQZExyRFVNbWJEQUlLUjNIc0dRRkFrekNJakZHelUwd3VwRmdPbHN3THBvTlpjU1c0MG1nWE1pdm4rU29JMjNrL1hxMm5tWCtyYzZNaFg0MWtsNmliUHVpOHRlaVhlcXhUY3AyMGRnamFoRDk1cExyUDdtR08rSVR6bCttSUR3RjdSMDhtUDJOTlNyYk4rVEYrREZFZmZOTW9IVTcwT3BERllCZ2Q1emdzWjRqdUtJV2xrODUrREE5NXZUcmVZSmZBZk1SOUtCVEEyVVNYNVVtcThBYThUeUJIam9BdnR2SUJUcTRBTFNKWGFtTVJ6cWROaHdXRUVJMXNVaTRncmh5SC9MNmcwMUdiUUhwRmJ5WWljMHlMR0UxakE4d21XN1pvUi9Pbi9QSHQzODY5b0pDL1dXWHFUYkxlUFMycFVzV0w3L3R4WmVIVnIvSUhYbnMwSUlkWXZ1NzMzNUNZUUpyVkxaeUtEbXRzMjNNdkw5ckZyVmo2d0dmckFjZkhrT2R5V1FsQm9oSVBRNHNIQUtiK0dFOXdCVWwrTXJzTXd3MUMyR09JRjhBOU1HZ0tBVUNCaFhPTzlXY3Bwb0NoZmtydUZmTkNDbVJjQjFOK1hOVnNiWloxZlhPeld2MzMvNk5BLzNmWEZGZ3JmWlpZMmQvZmZUVFcvYis3ZTRuRmpjbnVWT0FqRWNGTDFDNDVwclh6cHorY1hXTllXR3dyTDV3NDkzWS9keHA3TDU3VjRkbUExcEJucnRCbmg2SWZKY3FZaXhTeEtlajR1Qnl4Q2VseGNjaERzUkh4S2FNSXpBc0xUYUk2Z09pendzM0xRRVYxMU9SS1ZIOTU4dUx4ZWYzN2ozL2hCeFd4RE04ckNycmIzWnV1UGYrKysvZHdCM1pKMzkwNW96ODBmNWNBWjF2ZU9uMDZSZXBiQWc5QVBoUkhIMm1nTjJZa3F1R3ViSWN4MjhqWXVJWkZnSXRqSTJ3T28xR0FXdzd4K2xXZ3VLSk9wSVpzY0JWMVZsWHNUdzMrZ1V1STZ5clNTZkd2K2gxeVZaa0FKaGcyRGJoU2owSEt5TTlYMUFzNDBybGVwUzVmR0NBNXRXQjJnWi9zRkcwU1g1SHdFektjYXBPZ2Zmd3UyZzlUUWVyUVEzMDZhbEpCY0hGeWtqK1hMNzhReExwZm9qdmFlbWNWZ05oL21DdVBOamJ1U05sb3Z3TGtpdy9ORVppSy9tZEg1RXY4amNGWDY1a2NtUlNqeDVTdUJ2U3VLdVVEOWJyZ1R1R0lhTmlLdFAxQTE3ajZ2akt4TVhIZzdUMXdHcjl0dkZYQVBzTUt5ZGVBT3dqVTZ4SHRjUVVFKzZacUNuT2NNL21yMU1NeldSeGRqYnJwaW1zdXc3WEVON0pQL3RYRlI0ZFU3WTNxZ1ZNOW1nVzcrU2ZFdWI5ZDNhZ25XRWNSblBBemh3Rk85T091cEt6bW9Fc0YyQU1FaWtBcW1NNHJlcGlZR2dtQktMczlEN0RhR1VYT055TzJvTEJZRndBYzVOTlhJNjVTVFJtS0VsbkZteXFEODQxUDFiRi9HellTTXpQMXRVdmFmNUUyZm9jdHVWdlg2MllvaWNYcWFiby8xQlQxTGVDbUtLeVI3SWRqRHhXSkJscmFqU3pkRlVDekJJR2RJYTRlMEJmRmhMN2lzeGdhY3pjZW92SndKTGF0RFdQb1l1SVowa2VHcXdVelc0Qm5RdlIvTzQ1czJmTm5ON2VvdnBWZnpBL3V6UnRtMHlDZnR2bnl6WEREWCsydEpXeWRGT1Q2bDczS2R0T2VXZG43aEZ0Qkw1S0hZRnY3dFNPMERnWW1IQStSd0Z3UlA3MVpBcWhNdXdUckZjVmhPVG5FU2NBbjBJRTZYT0FwUGtoa3ZZVFVzQVpZQTNTT0JOQ0FabzlTaWY5RkhycUprRDhiSnY4SnpyTHYyS1VDL014K3F2cU8zOHgrZnpUQ296UmFsckhQUUxoYXp4WlgweHlyajFrUFlJUEdjMmVMUUpKcmdKZERoTmdCSU5EWWlBb2pwdXNtc1FqcVFVeWJSdU4wYlBxQ2FwQVR2LzI1MysrdDRBcTZJemhCUXRrTmMzRnZLL05kZXl1RjErNnMwREEwNmxLeXVlRi9tVk1mOXBVcWJyM09zeDVKWnFmN0YwTXZxOEtJblNTQVFLb2dzRXFjd3o4MjJWV2xUSFBvaW9qUXdKZUhWWXpkbkQxaWlWOWl4YjB6QUcraStGNGt5MW96ZFpFWEViS1BXNFN2V2ZWT1Vtd0U0cVJnbzhvNUdQWEY5VkxuS1dXWDZMa1J1UUhwd3dLN21DUlpDMnM4WmtVSHV4dld5eTVpKzNCZ3BLa1VDWFdiMWYxdENJWEVlR3ZLZHRxUEwxUlBiSkg0NTM4R0p1bzhjK3E3eW9LVkNoSHVqc2pUY0dlNGxCVXFIdnljM1QyUlp4TTY0VG1DeUpvdFFZYUdVUnlVNk1RU0NIZEVFUjlPZ1YxYUFuUVVoS1dLVVBBRXJDWTI1WTlFbVVHRGlUekVhbkNoUW5UYlVHS3JiSldyNlk2RjNOK3pDZVUzamZ4RU5XZmpOdTc0dzVWaTlhbHRRampLWW9DMVUxMGVCaVpnTWFYZ2NZVXNWK3pBMTZXSTFrQWp1Z1FIalZnb2pobTAwV3NXQXAxejVnR0JFZ1NXYkdXYksxeFRLSVJaaVdNREpueDUwY0pXbE9Wbi9zeXBTVnViYzAxVklPNnIrZkZLaU14NnlIZDh0d3pMZmx4VlJNOHJsTGR5V2QwcFM3c25YenRNL1BrRGFMWEsrSzd4cDZlVEIrc050bUYvMkt6a25VR3R1RVk4S2dERFQ5VFgwQUtWV29NWGdxTGlZZ1hmSm1pQ1F5RGg0bEJDNVBpdFcvaVdYYUlpRCtsR0JERm4zZWdOZ200RjRkQWxMcThIRE1TREdIeFVrWWZRckZzYTYvd3JLbXVOUmExeWUzYzF0eWdxbE96NklhS0F2d0FwMm9OdmpyTm96Ni92OWpEbkJ2NzNtUThLUjJiajhjMDNXRlFCL0RsMXYvdHVobHIrdlNXV3o0OWVwUis3ci85OXYza2p6dDFsM3p1dWVma2MzY1Q5L3NjZHQvMTNtdG56dnp3aDJmT3ZLYkdCVmVBZkFJUXJLelRWcW9Pa2JodHZaNGlLTU1FVjBOV0tzZnI5ZHcyYlNTRXdQektpUU1wYUkyUmZIa0FpUlI1R1ltMVYyRHFKUXhmSmxpNCtXOS9lLzl1RFdiZG8yenZ2Rk5kcStMZFYxOTk3YlZYZ3hCKytzb3JQM3RxTXM2UEhSOWN1WElaNGJuOGI1VG5UV2dHZXFYN1NRZlFhcXJEU0s4ay8wdVRadklGOTVnQVVuWVBLT2NscEFjSzlZajJiUEVETENncEtmdXZKZUcrYnRoSXFqZ0dBbCs5TURhZ2phVVpGRnBHSUU1ay9HQ0lqVmxhd1JzbDQxbHk3ODhaRHNqVjNkeU1VUE9NNXVuSmRwajZGS25DSVlsQk00MG9WVlVJNldrMkpTZXZvdGZLRUdvMUpVVGI4aTZ1Tk1YT2piMjl2aGsrVDB0SmI3Y2xyekNTN3hDYk5qZEozZlZURjhhdTJxb3pPQ3J6QzIxbnZuRU14dTQ3ZUhBZitlTk8zU2FmLzg1MzVNOXVZelo2alRyZVdLR1RmRUZmWlVtbGFEWlp6TldzNUFtSlpiYlgybkRSSzkvQjNHM3ZQZlB3d3lkUFB2endNNW1ZOUZuUVBkS3p0UDBFckhHRGxtRVFrQUhPRzVnUndnVTl4Rk9rcXNTekRNbXRja3B1cFJUQ0JaM2VhTlJ0MDhZaW8xRy9jcktoTkwvUTB6VnpPdnpTVktLRzRYaWJXYXNjRm42dWg3NEltcHhNVFpmLyt6L2o1UzdSWFpUbnJDaDJxSkhVM0ZWaHA4Y3BGZnA2R3BOcVZDVTNqMHRPNUQ5NjE3cFZxOWJkeFIwNS9kU2ZXbDNoMHBab2pjdnZWMVE1MlMyMnhUckxJOEVMYURMZGx2R2M3dTQ1b0VCM2dUM3BBTjN1UXFsazEweU1kVDdNOEFUUFlOMndRYytRYWlQd1BMTlBxbG9zV05Wd0NwSDJEcnBMSFZNWG1qTjltaFNRcXFXQU1TdHJvV2dTaVNMY0NzZVVsRjhvcXhha2FpQmhoOEs4a01xa09xV0prZjFWUEFMeGw3bjZhOE56RmtwQzFXVWJibTcrNXZMVFgzbmtTcVVkVVF5YjQzZXZXVElZRHBXbnV2c3VyKzNwVy9YVXRubGZxYXNGdXJ5Qy9IZkJXMURRTmIrcnhSdXcydXhPVVJyKzdaYWpnMnVESk5XSmV3V3Z2WEQ5aHRuSmlvU2p3RmxnTHl1cDJMTng0ME9ERFRVQmtnSEJhQlhvMmtiUXRTaHFTTmJxc0JvMmtqeWRWclRNK0JnSzdhSW9JcExZd2hGUXE1WTJsZEtMT0JWYmRsR3NweXpSbElpYytLMXF0UHFVN1c5UGtLTStnZDFMWThPbC9qS1lPWUNNSE5kNlFmNVBldnhoVWlURGFvOGt5VG1TM2h5YVhtU0hRSWcwRjBPNkg5T0FPb0VhUlpFQ0NtTW1LVXQ4b2RhVk0ybm9wd0RzQ1JGUDlaYlhEeHg0ZlV0MWJsU1QyckppeFpiVStMaG03QWY3WGwyNzl0VjlURk0yR2h6NzNmWXJydGpPQkRMNWdRc2ZBeTFuYVMwWmFKRm96WVJYS2RMckZJbzBZa2pOR05DZG1JdnVWQkNFSjZHa05Cc2VQMEZuT0YyK3k5cmMxdGFVSnorb3pmbTRzaDM0elI5bmFUZzQ3YjBYUzk0eWtYMHNoNFo3bWJWWjgvOHJ6UDlkbVA5VTFKeE14R00yRnV0SU5SeVIydjRvZ1hpZ1l3U3hjSnlRWXJCR3lsVFVRVUNlRkpSeVFRcHJaUlJFcDhnbnhFNUtsYko4Y3FnN1JXYytaUzFiV0JlYjFtTDU1b09XMXM1WXJZc2RybE5wVWdIZGpzWTc5QlhWZFZXNk8rUHJKOFNpaTRzOWxqSVIvMFlPaTJVV1QvRTR1cC9Gajd1TEhDNDV4Y3pPeXUrQVFsSXN0NUJVTkdmWGx4azVJa0tUVVErRUc0WXNaa1pKZ1N0UWw4OE4yR2ZOaUlOQTZiKzhiTEJybkRRWlBsa3UzRGlaMk4ySkxNYU1LSXlSUDhaaVd5NTBhL2pPWTBIMXlLaXliY2VpL0VsckxzTWlkeHdzVW85c1NnZERlK1Vyc3Rmbmh4L21CUEgzNEszWmpQdjV6N05qekFyZzExSGdWenRLSkJ1QVhTeGhseDRZUkdKaTBKTkpRdmgyMUtxeEtVZFpKa2RMbDF3SU4xQnFxdVJIWDFVdDBTNWwrNnI4ZUN5WDlzN1RaeG9uTE95UDVHeGkwUVhHbEJQdnZZV2xkTHkzRDJpZFFuTVVhNVI4cktoMEsyM0w5RFJwYVlCTDlUUk5IS2YwTklWUVFDeHNGQXZUR1lOMFMxTldzRGRKZTRKNzdHVzhsU1R0SU5UN0JkRG9aTnJsNCtRN1dPSUNTbXViNy94L3YwMFRtd2RvbkRldGxEWFNSQ2RlcWZTTVlDeklUN1AzODRQSVRYSXdKRW9sRDFOd3lqTXhYT2FaR0JqclJvVlNZd05wbmVEVTBvVTZGelhCYVBPelh5S1pRNFk2THBsbUVaL0huWnVxcDAyTGVRVmRSUENTdmMrS2xkK053ZTgrU24rM0loa2d2OGRnbGxtZmFYdE10eWE2a2Nzdk5mSksyY1NtL2k3NVdadTJ3OTVLK2djWjhvTzRVMzZlYm1WKzBDdDg4bXZCRzVzMnJacjdFL2xVZFBjbC9Ddk9ESGpDaThKUDZkWk1UNWE1cmFTQ2ludUFic1RzSWMyUlY4RkFML0lFdzV5aEtQS1VEazBucFMxYXN0RmxERnNvM2FERTNGNXR4TzE4UEN4NHZHSDljOC9wdzE2UEVJN3p1TjBZaTNDbjdJNngrMDBHdDJneTVGdnhYdms2YTc3QkpMb05KbWFWd3c2Mjk4MnhDOXdIOHJ2SWhzcnBmRnpqV2FCMGZ0SnBUTWgzY1c5YmRUcHIzbWVWZVhUTG5aWGZ0ZFhVMUZUYmJOV3dJYkU4ZHJKamJBTi9GTzVmVE85UFlsZWxSYkxJbWI2eFVxWUpCYlIrSlo1dEtDeVhMR1o1cEtpaUtXWXJ3TXU0L2NEVmV0MGJsdkpRdk50OFFjRzVXOEJ2M01zZVIzV3d2UCtndEQvbis3Q0JiVzBCM09vQUNsZ0lQbktPNk5tZUFTVk1Ea05vUVBxc1JrbVBrZ0d4aGhGU0ZxRFJRU1NsSnp3WVpsUkFyTnk1L3RJWEFMa2kzZFVhbTBxVHRaOTNGVXBmQkhHZWRnMEpUT3JyRWFwdnIyOXJTZ0J0dFNLZ3huaWpXUU9OaGJtQU90Mk9ReFBNSkNPZGFlbk9kUGZIRTQwUWtTUmVGY3A5aWpXNnZIMm9lTzZUeTY4NDJ2Lzk0M3Z1WHJTeDVlQXNtNlU0VkpBZkczaHR5WU56Wm5YTytITEx6YnZZNC8veWxQeE9SVlF4VFBXSnRzN1VWNGNQM0ZQbTdVeDZpL2hBVlpXbjNsWmVQdlpHWFUxMWJhSW1XYXJJcFJUa2NobGZqaXBSTS9xQndtNFRDd0djRGNNYUE1R29YMGd1WHBVR0dEVTFJcFpTNURFSUdxZEhVam9hdmFzdVg1VkQ5T0pERlh1dlhvWFVqRWNFaGlJT3hEQnk2ZEhBKzhKSUJBWTBSNXJxYTJIK0ZmNWdZekJnVW9KclcyNGpHZzIySnd0ZDdGb3RYcTNONDBQZStyMjl1MS9kc09IVjNVT0hHN3pDdXlycTA4cHpucmMzdExkdlNMWVAxdFlPdHZQbFlFeVdOYldOdnZXVnI3dzFPakJ2a2VCVmk4bDcxYkQ3aWRZZDgrYnRhTzI0c3JmM3lnNnlSbThrZlhkMEhYUW1rN0dMMUZNaldmWFV5TGg2S2loWk1DUUdneFBxcWRtZEJabVNhbGFQbEZMVVlEOVJpaHJoK1Uyek43VzBiSnFkK2xhUFBUOHEyQ1BMMzFoLzZQMGJkdjNyM2djN201UHNjVERKTDlERVgrWHNTTWVPVkdwSFIxMlZhVzZrTEZyVTBMenpyUU1IZm4vOWpqaUpLeGcwRERROW91clFkNU1tSHl4ZEcxWWVIcGhNWWNqVFhpeVI2OFNGRy8yY29VTjA5ZWx5bHF5aU1DelByYi8wNklrS0l3WURjVkZUbUt6SGJvSnRPSnR0aGU0c2hVSGpGSWI5MEt2Mkl2eFo4RFljSGxKVXAzZHZ2WnFjd2IxeUJkV1ZKTlVib2pHZi9WVlJEcSt3YU42QW9qcHRUZGl0YVl5aUs0cmVLR3QwTi9CM0x1aU1IOXgvUjdJMW5TSG00U1NQYUI4dE4wd1NWUkdhSWlaY0NMTzlnb0NRRUJLQ2tnZ1hsb2NkQWdSeEpXcHpvT2kvU1A4SmtLalQrd2xkbHJPYnZjTFlMc2NOSys4OVliRVVsdWVaM0NWcmZyYm0wRnZici9uM3I1K000R2R0Vy92WTQ3dlAzUzE0NWkxT2NCVTFnWklTcjlFZjNQbTdXdys4dGZPOWUrWW8vZDZQQUNaYXd3ZFFFN3BjRVhGWUsxY2FNS1BIV3NIU09FenF2ZEs0Q21kSUd3c240VjVHUEpLNUtLZTBTUXZESkM5RUUyeUNXRVFMdzhwakpzcnpKYUxneFJuME1XazZRMm1TcG12a25rUEZ4U2FMV0dTeDNUaDBFMDVRZlBKRFhLd0NTRFZIZlBJa09YN3k1REUrMEdUMGUwcWtxaUFmZXJpVjFvaW41eURrTTZSRGVzN3BsOGxha2RkeGo0QXNhMUVIdWtONUNpR0llYjIyVmlJSWxKbG51VkdUZ1p3YU51b1kybU9vMS9QRDlEa3pyUlUzU3RRL25qTmFjMVhLcFVQb29oZUMxNnFyQTB2U1VkYytKVTdhNUFOaWtSaFV2WlpiYVJVZmwwWk85NlFSLzVTelBNWjFYbTRsUnZQUENvUDYvL0xudnRlWDErVGxCNHJ6ekM5Y2VlMG1NSzAzdmJweDQ2czNOVzdac2p3NTB0WTJBblptWHZkTXpXeU8xYjM2Rzc4M1AxNFVxNjdrV3RhdVg1ZG92ZmJYWC83eXI2OTk3OGJ0MjI5TWJPN3QzWndBUFFCNHhqMEU5bVk2Mm55Q0pjOGZxVStoU3NoZ1VCb1BwSFNyYkdSODNhRTBLUkJ0TWlBajllK1REMUlVYWpxaTFRbWFVTkE2RGRUQ3ltU1JDSEhvVnV6Rm41OHN3NDk3cjNsMDJTMWRxZHpLUTNXOG8zbERSM1h1d1l6WG9aNm01T1M4TzFmTHd6bXF0YVozM3ZDRGcwZHk4bUo3dFFEc3dnVzYvdWJ3Q3dzRXRCNmhBZ2F0c3lyUFVUOGdyMlB2cGNmWDBxZW8xNkZuNlhwdGd2RUhnYmRUMFJWSlkwZk1iT0pJZ0sveFYxMXlVc3BBYzVLZ1hZR1V5VWhZaDRaZ29TcU5Nd0lZSms0UFR2emlneFQrVGtWSnFZRVdMNlJHd2wrcFVEWEFJVlovcVpJZ2lDSWdxcUJlN2ZuUU8rcTVIUjd5MUdPZDUvdytyVU5zMVhoV2dpSGc2aWp3djU5OFZuenlqN1kzS3R1QWV4VjR4Y2k4eVJnSmRqRDJxMkE4RVF3bTRzRWZ5azhUUHQwSGZPb0FQdm5STElVNWJyQzYzQkI1Qms1S01Xa1BSRkNOQ3c2Q2orZlk5ZG5IbGNmay9NaEhLbmpxWTNLWHFGTXpQL0pxTnVpOCtxd250cDFUZDQ0cXJtVnlSY0FYUG9ENUhnQzcwNEVPMHdkdW5tbE5NRVN5Z1BCYU1hOUxBUGFnQ0k4OGl3T1lYakVuQmoycjB3VlNITU1vb3RYOE9lbUgxRTZTNEgyU29Va2ZHVFdFdENGcXcwWWtQV0pBSzErMWd4TnVETUQvbVk0TitzU0tUV25adU5qWHpCUDFwTEdaMmlieS9MS3cwU3ZzRkx6RnBkV0ozQjIxT2VFWWhKWTM5bnd0RXJ0dUZudjg3bStNblNFUktHTnVyTHZqZ1B6NGhQM2JOUVc0L1lvcmY3eG12Ym8rbmdBK1RrY2pKNmFSZUYwMTNCN1NwMjhZTmhrWmd5RXd2Z2V5TkJra3B4VW5SeUlRR0RxRUpobW8yWjNPdUdaNHpHcWk2UC9aNGlqOEFaODI3MzltY3o0VXZEZC9INnp6RjdFNERLUHg2ZUQ3NE9PMkFsNVpEanpLUjc3Y3VsNWtRbDNQVjFCV1ZKaXA2NDEvdXB6SndWcU0vSWZyci8vRG9VUDBjL2JHcHFhTnM1VlA5amdCcEcvdFZEN2ZVeENVaHJrWkZKQjNjcGZCZkdwUUV0MmNORVV4eDVzd1N2dGN5VVRTbFR6eHRUeFBYYVl5eFV4ZUtrVGNSalVkbHVWa1ZXTjRzU3ZBeTVLSHZtcVR0UjBRRzlhZ2FpSlR0V2lWaVV4c2w1YmRSRWF3SFJyS1ZGdGNaWVBxY1hPdzZJYXNVSVU5cmlGTitad2lyUEUyRHNEb2U3blJDc1gyd0x0SE1yd2p5Q0tRaFZla3lYRktPRk5KQ0xFcTd6NGZvT1JlTVlGM0l1a1F1QWhDbVl5RG42TkVPUWlsUDVkL2o2U0R2OElzME00ZXp3cnR6bCtuYkpWUDdOYWl2L2ZHNDNhSTljQldFTDJMbzJkb0wrQ0pldkxzVzA4cDJXSk1ySzJGbGt5Sk9hVTFxVUNLNUpUU1g3S3JNYXJ0cmNxMFRtWXV5aFM0eGwyVEFkc1pZMHdiNlVpMUo1SXpka0I1K1VZY05TcW14MDBMS0puSDRsVkw0NytFVjZiYXluN1lYV1czUjR1dEJWTmFVM3ZuWXpXTk1iWklyVnZ2VUYyV1hmQjJ2N0tHUFQ2bHZNRWZqY1lNdmxXUGJ4eWEzSzc4NjhIN0ZKNGVCZHNTby9hM0p6a25DWVNYamF2eFJiSnFmSkhQcWZHQmtZMkpBYWxhREdpdkdhRjlWMnFGVHlud2FjczA5K1VpUkpsSWZZOVcrSUxab2ZXUDZBdEZXZzZ0YWVuc0NxMVlmbjFpM3RMbFQrL2FmN1gyVHBHNnc4dS9HYTBxWHJiMllNdStGUSt0Ly9xTzJnNzJ1UElta1k3R1NySFNiakthQ3d2OVZ3MFA3ZStlbFg2UFNFZnp3dUl5RTU5bjhmbDdqdlovYWNZY2svcjhNNG03RjlQZTdIaXlIbHdSU1l1TzZ1anpsU3g5dmxKdGtNenR4cGJFQ2xHUUpLMUFsbTc2dERuVnZJRWFFcXFWUGpVc0l0bGJ4bG52eE50cE1IVHJUYkhyRnhUbXVhUUN1OHYxazY4Zk8va1NPZnhTMnl6dUZGbE83OU1nNk04UGh3TkdzU0xxS2ZTYU43eDhHb3NrRE1JbFN0OGp6UDFyN0dFMEJhMCtZY3Z5b3lVa3g4T1I2aDdIa1pmeVpPY0lrdExFazBxY3oyZkgrVlNScDZDNEZBRGNIaGUxMG1WdWdLK2JVQStrK1RwaUp0cXlxZ2ZzWDd5cTAzeVgrTU1NYnNjZ0h1byt0V2F5SUhzWWNPTGxHVWNJbmhNL29HZ3pZSGRydHRja2RSSFM3d3IwWDZ3T0dQamZxZ1Blb05ZQmY1Yy9mZWJNYWZueTc2ZmxkcjkxUHZWMFFqMHl5aDVXNDdCQnNheE1aSTdtVkRwbTRWUGo2NEF3L3c1U0IyeW9LcUIxSGFUakVLZER1WFhBUUZZZGtEUXJTY1FMaXVQcmdEaVRMZy8rVDh1QTRUc01qYTNOVS9JTzNHYWQwdEphYi9pcW9CS2tQaDJ5dUh1ZnVTb2NpWmh2NloydFpXVXlwSktTSjE0dDN5ZVdlYVZ4Sk8vRUN6M2VvaEw1WVh4emRrMkxQQmV5RjJqL25CcGc0R0kxd0ptMEJpZ1dqcThCNnI5d0RkQVJ1bFFOY0xIU3kvWmZtSzNQTGZoWmQrKzBxVWZ1VjdaeCtlT0czUHAyM3VpMWhlcVJWUnFUUHBNL3lUYkxlL2ZtQUVMRHA5bE0yNzA3WFErcmtOZFNIVStRZm9NcU4yMTgwNm1xb2E1aFJEcmV5T3RTdFBJOU1FZHlqU3ZmWXl1ajE5RVhFYlF6aVMrbzhFbjVwcGszSHJsSkNwUVd6MTA5djBuK1NYZXUycmNlT3hZZnIvYm4vM25yblcwY250SlZYOFh3ZFp1M01EdHl0T0ZtdkRQVDkwaHJmVUJiaE5UNnJCZXY5UVcrWUswdk1MSFdGMEZoMFIyZjdQMEZPYTJkY2EzY0Y4UFVRZEY2bjlVKzloR2UwVEN6T3BhdlZ2eXNkc1lzLzVRZThRbHNDWHNZYUNtVkhHUG5kb29lUzBteC9FOWE5WU1qakh1YmNrUXNnMGsrSkQvTnZzOFBRcXkrS1dsdGdVQTJINllmQmdlanZmcXJOUDJxQXBLVVpOYlN6RFdoaUw3VXhrOWVwWUk0SG8xa2hvSEl5Vk9ReEY1alpuNDZGWkJvckk1S2dyYzBvRmRmd21HbENXMGZBM1M3Q1BuNVdLY2dPZTJaZWRMTXBUd3JyNlZxNFZzMURpcSsyR01wTFZwMVdZamo4YWJycjkrS2pUaTJjV2xScWNVamZ2WUJtNGV2dmx5dHJXekhKdmFEOC94Z3BEMFdLNGdzNngwdUdibEZOQW43MWpsTnV5MUZuZk5DK2JGWWU5VlRwNzIrcnhvS0ZpKzN4YXFxb3JiQnhRWEd6V1dlRThkb2ZmS2NmQi96SGsvZWFSSlhlSkw3L2hIdFJVZ0RFMTZFbEhuaGlTdXJkWWI1VG56YXRDVDg4ZHU4d2lmZkpwMHd1bjYvVW9ORjc4dFBjeUdReHpRMGtyU0MyK05xNEo1dURFcVZsZ2NNWThrYjFwUUhnNUgyTnF0S1RwTUhyYkJraGdFSUhFREthL3hZSWcvU1dUd05UVzF0RG9TRFlYMzZCVDVLY1VxRFJQRE5od3MxT2JTcitGcGhmcUl4aHFsa1l1bDZGK1AvZ0RYaDdSclRyOFo1N0FlZmlVUkVTemZHUURaYnI5ODlvdU54ZE1NZ0ZSRS9lT3lFcDJ5enNXRHhvQzFhVlJXekxWOWNZUGlxejN2NnFTb1FVMzVvWG1lUlpiZkp1VzZmWUFyY2ZlV3d5ZDQ1TjFnQWNvcFFIdDJFRDNEZHpCZ3cvM0pTeDN4R3NJSmpKUUREb3ZDSFpkQ0FqaWV2UEFERVJCakJRSFRLSUdZK0FjekFIMkRyS0t4VGh1VUFPQ3VqNFNncERTcURFUm1yMWVPRG9oUVM2YXVBMVBMdnhQcUwyamVtMTE3T1FkNVU4ZDZLYVkxZFVxaXQzRjdvRDFmbnRleGZHaDlPeG1lTDJVZVlNVkh3ZU1zRlJ5QWNzTG42bDBpQ3g1UDVwc1JuYnpHTjdFcTFoelpCcTdaVkhLa3FLYVJCVU1ZTXFERTNnK1pQMGtxYlhTeWU3S1Z1ekk2djlmZHIvMkpUcDhiSUgzZXFQK3ZvTDVXRHNhbXcwQUVYQkxuMytPMFErZGVpZWVEeW5xTnpjcGd4dy9yQlN5Nm9aSGpUZEt3M2MrcXJlcVlBZjlrOXhCTHNRYnpKYk9MTm96cU81TWtnUXQrQVRMekJOR0MxNUxGbUk5WWJ6UG9SWkRJWlZpR0R5YkNBUEUybVhLcURTM1ZZbDc2ZXZwenlVcGNQSkQzejU5ZlZ6Vjg0ZjJIZHZMcTVQVjFUazJLd3FGZ0VXZGFTSjJrb1g3UUdBdlZ0T0ZSNDJydHc0RU5TWHhRVVV0OFVWT2UycTIyOTJoTlY5T3FFK29aUFc3MlkwRE4rcDFzT0Z6bWM3dnV1ek1zcmMrZVZnbnV6dTMySDNFNW1zZk44djhWUTZpMXlzdDhtMjhzaER1bjJWZFpVeW04N0JKMEJ4NjBSTVJydC9qdC9ML01Ud1I4TSt2SGxyZnJhVXBjbjczcDlpWHZzbjBMQVdPaXdqUDAzSDVWZ3l4ajU2Rml0RUFqNHIzSTVuTTZycG9yNUlJYnI3UGJpUXZuV0gvd0FzU0NyRVBlT0txc2g3S0tTeXRja05STWtaU0JHcFJpa2xCekhhaVBtRFJZRGJ4bk53eGF6MlhKNUZzdVJnVGNaUnBCWnJ6ZjNJN05adnhMcHpmcDVhbjF2NWdTUkdZd0czamlLakJhRDBiTHJDOTh0T2V2U056Sll6THN1ZVNjSWU0dnE2dXFHNmxZc1c3cG9RZmVjY0VMVkFldi9odzZvYnhjaUF5ZDl0VkNkOGxCOHZXSVl2N2crREZUWVhiSyt5bzF0TlpHR1dIdU5MeHlwS0ludm1YcnR6WE43SHZxK0wzd3hyV2dacHhYbmp6dWR0N25zaTZMMlg0a0pYMFhNMVVVVTVLRGI2aW03YnUzVWpZbHJRaTRIV2NzZjA3VzhEVFdoYnJRUmJVYnZVdzBwaXBJWEtZS1dkT1FEb05zOG16SGtyY1ltSTYvYTE1bnBMZ3BEbmpIUFlCd0Z6NEhJdTQyb1F3SzdOS0luUXNuRGFLUUE1eG5NZVFOV2JMUmdrOWxvSWdmeXpLdVFPYzhNeXp1VnZwR2VJVlcveVcrb2h4dWlMM0MvZ2FUWTA0UFFwc3Q2TnZhTXJCd2FYTnEvZVA3Y0dkTmJXMmpaVUd5b2o0WnRFRjRwTmp6ek1xV3N5cGNhOW1mZXBwUWxXVld3U0RYNkdZV3dxMnB5RWF2QTFpZndYZnZYTmJaODQwRGJuaHF2MFZScVpYWFY2NnQyeHFwU1RwZkwyYmFoS1Q2bHVheHlRVW5qbnVtc2llcENSaWRpMGU3Q1NVekVPM2Z6L0xhdHExYlhPdWMxalZ4VzdNenoyNG84Wll5amFMWVlFSUpCb1VjSXVtcGRqb3JSRW91N1pPeVBWQzB5NmlGL2k5aUhTY3lHdk9JSDlKMXI2OWg3QWZjS0tKYU1wTjlXcFpVK0F1a0ViNVMrcFVwQTVZSlVGTkRLRzVOeE5PdkJObmFYOStTeHZsUExvblo3c05qcVduQjk3Q1paZmRNdDAwekM2L043VHI5Y0d5dU1laW9yUTRaQStHSG1YUzNXd09lNFdzQmdDd0ZTaGFpV2VpWmlyaXpBcFlnNTV5MXpqelkxenB6WjFEQ1RYK2dWanBMVXkxSFJvOWF2NXdDOWZoUktTbGwwWnBkeS9zZDFuRjlOVXNmNXRicHp1NUpIbUN3Tmh2NHZFZjV0Q2dBQUFIamFqWkxCVGhzeEVJWi9Md0hSQTZpdGVrSTlXS2dIT0xCT29FZ1JPWVZJdVJRSklnRnFqN0MxZGhjbDhXSjdEN3hFSDZJdjBodXEraDU5aHg3NzIzRkxxRXJWWGEzOWVUei96S3pIQUo3akhnS0w1eU8rSlJiWUVPOFNaK2lJSXZFS1hvdlBpVHQ0S2I0blhzVkc5aXJ4R2w1azQ4U2IyTW8rVVNVNno3ajZHaU1FRnRnU0tuR0dkZkVoOFFyNm9rcmN3UnZ4SmZFcS9YOGtYc04ydHAxNEUyK3o5eGpCb01FZExHcVVxT0Foc1k4dWVqZ2tuZE9pT1Fldk52cG9qaEpua1dkeEw3REJEYm1JNmlFOVBYV0dkc2YxVG96cW1jWGhDSXB2U1czd2FIR05uQ3JEU0FxM1hCdmFOZWY1MHVxS3lxQlZmMVR4VU1NdW8yQmttanRibDVXWCs5M2VvVHl2dEJ5WjF0YmF5ak5ienpSSGM2TUxMNGV0cjR4MWNxZnl2bkZIU3BXMXI5cnJ2REF6ZGRzYXI5dDVuSzZheHFrVUlrYllEVm1lUEFnOHlnWWMwM1BLYTRGak0rVjR3QnJEcWZZeHdBUVgvSWFrcC81bzcwRitrSGQ3L2NIa1lqSWNMQmV6dHdqN3I4YjhEdkg0SEJiQ3l5aHdkRFk4YmJsVUh5NjFkYldaeTVnWi8xUGpYd3I3MWZORnh4MjdISFFOYlk2WlF0NHA1M0JIU3U2Zllvd1RpdGdSTnNRVnRtNjh5MTA5elkwdDFlbjRCRDhCK3JHb2VRQUFlTnBsaXRkT3dtQUFSczlmUmhHY0RNVXRibEd4eFZsWFhDaTRCU2VvcFRGZ0x3ZzFCV084MVVmMVBZeW1pVEhSYzNPK25IeElPSHgrOFBZdHdWOU1wMHE0Y09QQmk0eVBCdndFYUtTSlpscG9wWTBnSWNKRWFLZURLSjEwMFUwUHZmVFJ6d0F4QmhsaW1CRkdHV09jQ2VKTU1zVTBDV1pRVUVreXl4enpMTERJRWhyTHJMREtHdXRzc01rVzIreVFZcGM5MG1UWTU0QkRqamptaEZQT3lKTGpuQXN1dWVLYUcvSVV1T1dPZTNTS0dMd0xTYmlFVzNpRVY4Z2hxMXJTYXhXalp1cGw2OWxPbEczaklmamI2aStXa3lKMTB5NzlPOHFQbGRjblU5TjhqbFZGK1JucUZ6TEhOVzRBQVFBQi8vOEFEM2phWTJCa1lHRGdBV0lsSUdaaVlBYkNSQVpHaGlTR0ZDQXZsU0VkeUdZQnl6QUFBQ2ZVQWpWNDJtTmdaR0JnNEdJSVlVaGlZSFp4OHdsaEVFa3ZTczFtVU1oSkxNbGowR0ZnQWNveS9QL1BBRktGekJaallIWjJERkZnRVBQMTl3R1NRZjYrUUJJdXk1aFdsSmpNd0FGaWdURUxXQzhqVUlRUmFDWVQwRDRGSU1uR3dNZVF6TURNSU1RZ0NySWRTSXVEMWFiQTJVd01JZ3hpQUxXMkV4bDQybU5nWkdCZzRHS3dZYkJqWUhaeDh3bGhFRWt2U3MxbWtNdEpMTWxqMEdCZ0Fjb3kvUDhQSkxDeGdBQUFXeG9MYXdBQUFBQUFBUUFBQUFEVnBDY0lBQUFBQU5tY2crRUFBQUFBMmZ0Sk5BPT0nKSBmb3JtYXQoJ3dvZmYnKTtcclxuICBmb250LXdlaWdodDogYm9sZDtcclxuICBmb250LXN0eWxlOiBub3JtYWw7XHJcbiAgZm9udC1kaXNwbGF5OiBzd2FwO1xyXG59XHJcbiJ9fQ==`, "base64").toString("utf8")) - } - - //Conf - logger(`metrics/setup > setup > success`) - return conf - - } -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\ejs\lib\ejs.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_ejs_lib_ejs = __webpack_require__(58509); -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_ejs_lib_ejs_default = /*#__PURE__*/__webpack_require__.n(E_Users_lecoq_Documents_GitHub_gitstats_node_modules_ejs_lib_ejs); - -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\svgo\lib\svgo.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_svgo_lib_svgo = __webpack_require__(20485); -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_svgo_lib_svgo_default = /*#__PURE__*/__webpack_require__.n(E_Users_lecoq_Documents_GitHub_gitstats_node_modules_svgo_lib_svgo); - -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\image-to-base64\image-to-base64.min.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_image_to_base64_image_to_base64_min = __webpack_require__(67192); -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_image_to_base64_image_to_base64_min_default = /*#__PURE__*/__webpack_require__.n(E_Users_lecoq_Documents_GitHub_gitstats_node_modules_image_to_base64_image_to_base64_min); - -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\axios\index.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_axios_index = __webpack_require__(2390); -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_axios_index_default = /*#__PURE__*/__webpack_require__.n(E_Users_lecoq_Documents_GitHub_gitstats_node_modules_axios_index); - -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\followup\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_followup_index({computed, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.followup)) - return null - //Define getters - const followup = { - issues:{ - get count() { return this.open + this.closed }, - get open() { return computed.repositories.issues_open }, - get closed() { return computed.repositories.issues_closed }, - }, - pr:{ - get count() { return this.open + this.merged }, - get open() { return computed.repositories.pr_open }, - get merged() { return computed.repositories.pr_merged } - } - } - //Results - return followup - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\habits\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_habits_index({login, rest, q}, {enabled = false, from:defaults = 100} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.habits)) - return null - //Parameters override - let {"habits.from":from = defaults.from ?? 100} = q - //Events - from = Math.max(1, Math.min(100, Number(from))) - //Initialization - const habits = {commits:{hour:NaN, hours:{}}, indents:{style:"", spaces:0, tabs:0}} - //Get user recent commits from events - const events = await rest.activity.listEventsForAuthenticatedUser({username:login, per_page:from}) - const commits = events.data - .filter(({type}) => type === "PushEvent") - .filter(({actor}) => actor.login === login) - //Commit hour - { - //Compute commit hours - const hours = commits.map(({created_at}) => (new Date(created_at)).getHours()) - for (const hour of hours) - habits.commits.hours[hour] = (habits.commits.hours[hour] ?? 0) + 1 - //Compute hour with most commits - habits.commits.hour = hours.length ? `${Object.entries(habits.commits.hours).sort(([an, a], [bn, b]) => b - a).map(([hour, occurence]) => hour)[0]}`.padStart(2, "0") : NaN - } - //Indent style - { - //Retrieve edited files - const edited = await Promise.allSettled(commits - .flatMap(({payload}) => payload.commits).map(commit => commit.url) - .map(async commit => (await rest.request(commit)).data.files) - ) - //Attemp to guess whether tabs or spaces are used from patch - edited - .filter(({status}) => status === "fulfilled") - .map(({value}) => value) - .flatMap(files => files.flatMap(file => (file.patch ?? "").match(/(?<=^[+])((?:\t)|(?: )) /gm) ?? [])) - .forEach(indent => habits.indents[/^\t/.test(indent) ? "tabs" : "spaces"]++) - //Compute indent style - habits.indents.style = habits.indents.spaces > habits.indents.tabs ? "spaces" : habits.indents.tabs > habits.indents.spaces ? "tabs" : "" - } - //Results - return habits - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\isocalendar\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_isocalendar_index({login, graphql, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.isocalendar)) - return null - //Compute start day (need to start on monday to ensure last row is complete) - const from = new Date(Date.now()-180*24*60*60*1000) - const day = from.getDay()||7 - if (day !== 1) - from.setHours(-24*(day-1)) - //Retrieve contribution calendar from graphql api - const {user:{calendar:{contributionCalendar:calendar}}} = await graphql(` + } + `);let o=0,i=0,s=0;for(const e of a.nodes)e.isFork||(o+=e.stargazerCount,i+=e.forks.totalCount,s+=e.comments.totalCount);return{totalCount:a.totalCount,stargazers:o,forks:i,comments:s}}catch(e){throw console.debug(e),{error:{message:`An error occured`}}}},habits:async function({login:e,rest:t,q:r},{enabled:n=!1,from:a=100}={}){try{if(!n||!r.habits)return null;let{"habits.from":o=a.from??100}=r;o=_Mathmax(1,_Mathmin(100,+o));const i={commits:{hour:NaN,hours:{}},indents:{style:"",spaces:0,tabs:0}},s=await t.activity.listEventsForAuthenticatedUser({username:e,per_page:o}),l=s.data.filter(({type:e})=>"PushEvent"===e).filter(({actor:t})=>t.login===e);{const e=l.map(({created_at:e})=>new Date(e).getHours());for(const t of e)i.commits.hours[t]=(i.commits.hours[t]??0)+1;i.commits.hour=e.length?`${Object.entries(i.commits.hours).sort(([e,t],[r,n])=>n-t).map(([e,t])=>e)[0]}`.padStart(2,"0"):NaN}{const e=await Promise.allSettled(l.flatMap(({payload:e})=>e.commits).map(e=>e.url).map(async e=>(await t.request(e)).data.files));e.filter(({status:e})=>"fulfilled"===e).map(({value:e})=>e).flatMap(e=>e.flatMap(e=>(e.patch??"").match(/(?<=^[+])((?:\t)|(?: )) /gm)??[])).forEach(e=>i.indents[/^\t/.test(e)?"tabs":"spaces"]++),i.indents.style=i.indents.spaces>i.indents.tabs?"spaces":i.indents.tabs>i.indents.spaces?"tabs":""}return i}catch(e){throw console.debug(e),{error:{message:`An error occured`}}}},isocalendar:async function({login:e,graphql:t,q:r},{enabled:n=!1}={}){try{if(!n||!r.isocalendar)return null;const a=new Date(Date.now()-15552000000),o=a.getDay()||7;1!==o&&a.setHours(-24*(o-1));const{user:{calendar:{contributionCalendar:s}}}=await t(` query Calendar { - user(login: "${login}") { - calendar:contributionsCollection(from: "${from.toISOString()}", to: "${(new Date()).toISOString()}") { + user(login: "${e}") { + calendar:contributionsCollection(from: "${a.toISOString()}", to: "${new Date().toISOString()}") { contributionCalendar { weeks { contributionDays { @@ -245,72207 +32,39 @@ var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_axios_index_default = / } } } - ` - ) - //Compute the highest contributions in a day, streaks and average commits per day - let max = 0, streak = {max:0, current:0}, values = [], average = 0 - for (const week of calendar.weeks) { - for (const day of week.contributionDays) { - values.push(day.contributionCount) - max = Math.max(max, day.contributionCount) - streak.current = day.contributionCount ? streak.current+1 : 0 - streak.max = Math.max(streak.max, streak.current) - } - } - average = (values.reduce((a, b) => a + b, 0)/values.length).toFixed(2).replace(/[.]0+$/, "") - //Compute SVG - const size = 6 - let i = 0, j = 0 - let svg = ` + `);let l=0,d={max:0,current:0},p=[],c=0;for(const e of s.weeks)for(const t of e.contributionDays)p.push(t.contributionCount),l=_Mathmax(l,t.contributionCount),d.current=t.contributionCount?d.current+1:0,d.max=_Mathmax(d.max,d.current);c=(p.reduce((e,t)=>e+t,0)/p.length).toFixed(2).replace(/[.]0+$/,"");const u=6;let m=0,i=0,g=` - ${[1, 2].map(k => ` - + ${[1,2].map(e=>` + - ${[..."RGB"].map(channel => ``).join("")} + ${[..."RGB"].map(t=>``).join("")} - ` - ).join("")} - ` - //Iterate through weeks - for (const week of calendar.weeks) { - svg += `` - j = 0 - //Iterate through days - for (const day of week.contributionDays) { - const ratio = day.contributionCount/max - svg += ` - - - - - ` - j++ - } - svg += `` - i++ - } - svg += `` - //Results - return {streak, max, average, svg} - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\languages\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_languages_index({data, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.languages)) - return null - //Iterate through user's repositories and retrieve languages data - const languages = {colors:{}, total:0, stats:{}} - for (const repository of data.user.repositories.nodes) { - for (const {size, node:{color, name}} of Object.values(repository.languages.edges)) { - languages.stats[name] = (languages.stats[name] ?? 0) + size - languages.colors[name] = color ?? "#ededed" - languages.total += size - } - } - //Compute languages stats - Object.keys(languages.stats).map(name => languages.stats[name] /= languages.total) - languages.favorites = Object.entries(languages.stats).sort(([an, a], [bn, b]) => b - a).slice(0, 8).map(([name, value]) => ({name, value, color:languages.colors[name], x:0})) - for (let i = 1; i < languages.favorites.length; i++) - languages.favorites[i].x = languages.favorites[i-1].x + languages.favorites[i-1].value - //Results - return languages - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\lines\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_lines_index({login, data, imports, rest, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.lines)) - return null - //Repositories - const repositories = data.user.repositories.nodes.map(({name}) => name) ?? [] - //Get contributors stats from repositories - const lines = {added:0, deleted:0} - const response = await Promise.all(repositories.map(async repo => await rest.repos.getContributorsStats({owner:login, repo}))) - //Compute changed lines - response.map(({data:repository}) => { - //Check if data are available - if (!Array.isArray(repository)) - return - //Extract author - const [contributor] = repository.filter(({author}) => author.login === login) - //Compute editions - if (contributor) - contributor.weeks.forEach(({a, d}) => (lines.added += a, lines.deleted += d)) - }) - //Format values - lines.added = imports.format(lines.added) - lines.deleted = imports.format(lines.deleted) - //Results - return lines - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } - - -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\music\index.mjs -//Supported providers - const providers = { - apple:{ - name:"Apple Music", - embed:/^https:..embed.music.apple.com.\w+.playlist/, - }, - spotify:{ - name:"Spotify", - embed:/^https:..open.spotify.com.embed.playlist/, - }, - } - -//Supported modes - const modes = { - playlist:"Suggested tracks", - recent:"Recently played", - } - -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_music_index({login, imports, q}, {enabled = false, token = ""} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.music)) - return null - - //Initialization - const raw = { - get provider() { return providers[provider]?.name ?? "" }, - get mode() { return modes[mode] ?? "Unconfigured music plugin"}, - } - let tracks = null - - //Parameters override - let {"music.provider":provider = "", "music.mode":mode = "", "music.playlist":playlist = null, "music.limit":limit = 4} = q - //Auto-guess parameters - if ((playlist)&&(!mode)) - mode = "playlist" - if ((playlist)&&(!provider)) - for (const [name, {embed}] of Object.entries(providers)) - if (embed.test(playlist)) - provider = name - if (!mode) - mode = "recent" - //Provider - if (!(provider in providers)) - throw {error:{message:provider ? `Unsupported provider "${provider}"` : `Missing provider`}, ...raw} - //Mode - if (!(mode in modes)) - throw {error:{message:`Unsupported mode "${mode}"`}, ...raw} - //Playlist mode - if (mode === "playlist") { - if (!playlist) - throw {error:{message:`Missing playlist url`}, ...raw} - if (!providers[provider].embed.test(playlist)) - throw {error:{message:`Unsupported playlist url format`}, ...raw} - } - //Limit - limit = Math.max(1, Math.min(100, Number(limit))) - - //Handle mode - switch (mode) { - //Playlist mode - case "playlist":{ - //Start puppeteer and navigate to playlist - console.debug(`metrics/compute/${login}/plugins > music > starting browser`) - const browser = await imports.puppeteer.launch({headless:true, executablePath:process.env.PUPPETEER_BROWSER_PATH, args:["--no-sandbox", "--disable-extensions", "--disable-setuid-sandbox", "--disable-dev-shm-usage"]}) - console.debug(`metrics/compute/${login}/plugins > music > loaded ${await browser.version()}`) - const page = await browser.newPage() - console.debug(`metrics/compute/${login}/plugins > music > loading page`) - await page.goto(playlist) - const frame = page.mainFrame() - //Handle provider - switch (provider) { - //Apple music - case "apple":{ - //Parse tracklist - await frame.waitForSelector(".tracklist.playlist") - tracks = [...await frame.evaluate(() => [...document.querySelectorAll(".tracklist li")].map(li => ({ - name:li.querySelector(".tracklist__track__name").innerText, - artist:li.querySelector(".tracklist__track__sub").innerText, - artwork:li.querySelector(".tracklist__track__artwork img").src - })))] - break - } - //Spotify - case "spotify":{ - //Parse tracklist - await frame.waitForSelector("table") - tracks = [...await frame.evaluate(() => [...document.querySelectorAll("table tr")].map(tr => ({ - name:tr.querySelector("td:nth-child(2) div:nth-child(1)").innerText, - artist:tr.querySelector("td:nth-child(2) div:nth-child(2)").innerText, - //Spotify doesn't provide artworks so we fallback on playlist artwork instead - artwork:window.getComputedStyle(document.querySelector("button[title=Play]").parentNode, null).backgroundImage.match(/^url\("(https:...+)"\)$/)[1] - })))] - break - } - //Unsupported - default: - throw {error:{message:`Unsupported mode "${mode}" for provider "${provider}"`}, ...raw} - } - //Close browser - console.debug(`metrics/compute/${login}/plugins > music > closing browser`) - await browser.close() - //Format tracks - if (Array.isArray(tracks)) { - //Tracks - console.debug(`metrics/compute/${login}/plugins > music > found ${tracks.length} tracks`) - console.debug(JSON.stringify(tracks)) - //Shuffle tracks - tracks = imports.shuffle(tracks) - } - break - } - //Recently played - case "recent":{ - //Initialisation - const timestamp = Date.now()-24*60*60*1000 - //Handle provider - switch (provider) { - //Spotify - case "spotify":{ - //Prepare credentials - const [client_id, client_secret, refresh_token] = token.split(",").map(part => part.trim()) - if ((!client_id)||(!client_secret)||(!refresh_token)) - throw {error:`Spotify token must contain client id/secret and refresh token`} - //API call and parse tracklist - try { - //Request access token - console.debug(`metrics/compute/${login}/plugins > music > requesting access token with refresh token for spotify`) - const {data:{access_token:access}} = await imports.axios.post("https://accounts.spotify.com/api/token", - `${new imports.url.URLSearchParams({grant_type:"refresh_token", refresh_token, client_id, client_secret})}`, - {headers:{"Content-Type":"application/x-www-form-urlencoded"}}, - ) - console.log(access) - console.debug(`metrics/compute/${login}/plugins > music > got new access token`) - //Retriev tracks - tracks = (await imports.axios(`https://api.spotify.com/v1/me/player/recently-played?limit=${limit}&after=${timestamp}`, {headers:{ - "Accept":"application/json", - "Content-Type":"application/json", - "Authorization":`Bearer ${access}`} - })).data.items.map(({track}) => ({ - name:track.name, - artist:track.artists[0].name, - artwork:track.album.images[0].url, - })) - } - //Handle errors - catch (error) { - if ((error.response?.status)) - throw {error:{message:`API returned ${error.response.status}`}, ...raw} - throw error - } - break - } - //Unsupported - default: - throw {error:{message:`Unsupported mode "${mode}" for provider "${provider}"`}, ...raw} - } - break - } - //Unsupported - default: - throw {error:{message:`Unsupported mode "${mode}"`}, ...raw} - } - //Format tracks - if (Array.isArray(tracks)) { - //Limit tracklist - if (limit > 0) { - console.debug(`metrics/compute/${login}/plugins > music > keeping only ${limit} tracks`) - tracks = tracks.slice(0, limit) - } - //Convert artworks to base64 - console.debug(`metrics/compute/${login}/plugins > music > loading artworks`) - for (const track of tracks) { - console.debug(`metrics/compute/${login}/plugins > music > processing ${track.name}`) - track.artwork = await imports.imgb64(track.artwork) - } - //Save results - console.debug(`metrics/compute/${login}/plugins > music > success`) - return {...raw, tracks} - } - //Unhandled error - throw {error:{message:`An error occured (could not retrieve tracks)`}} - } - //Handle errors - catch (error) { - if (error.error?.message) - throw error - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\pagespeed\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_pagespeed_index({imports, data, q}, {enabled = false, token = null} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.pagespeed)||(!data.user.websiteUrl)) - return null - //Format url if needed - let url = data.user.websiteUrl - if (!/^https?:[/][/]/.test(url)) - url = `https://${url}` - //Load scores from API - const scores = new Map() - await Promise.all(["performance", "accessibility", "best-practices", "seo"].map(async category => { - const {score, title} = (await imports.axios.get(`https://www.googleapis.com/pagespeedonline/v5/runPagespeed?category=${category}&url=${url}&key=${token}`)).data.lighthouseResult.categories[category] - scores.set(category, {score, title}) - })) - //Results - return {url, scores:[scores.get("performance"), scores.get("accessibility"), scores.get("best-practices"), scores.get("seo")]} - } - //Handle errors - catch (error) { - if (error.response?.status) - throw {error:{message:`PageSpeed token error (code ${error.response.status})`}, url} - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\posts\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_posts_index({imports, data, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.posts)) - return null - - //Parameters override - const login = data.user.login - let {"posts.source":source = "", "posts.limit":limit = 4} = q - //Limit - limit = Math.max(1, Math.min(30, Number(limit))) - - //Retrieve posts - let posts = null - switch (source) { - //Dev.to - case "dev.to":{ - posts = (await imports.axios.get(`https://dev.to/api/articles?username=${login}&state=fresh`)).data.map(({title, readable_publish_date:date}) => ({title, date})) - break - } - //Unsupported - default: - throw {error:{message:`Unsupported source "${source}"`}} - } - //Format posts - if (Array.isArray(posts)) { - //Limit tracklist - if (limit > 0) { - console.debug(`metrics/compute/${login}/plugins > music > keeping only ${limit} posts`) - posts = posts.slice(0, limit) - } - //Results - return {source, posts} - } - //Unhandled error - throw {error:{message:`An error occured (could not retrieve posts)`}} - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\selfskip\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_selfskip_index({login, rest, computed, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.selfskip)) - return null - //Search for auto-generated commits - let commits = 0 - for (let page = 0;;page++) { - const {data} = await rest.repos.listCommits({owner:login, repo:login, author:login, per_page:100, page}) - commits += data.filter(({commit}) => /\[Skip GitHub Action\]/.test(commit.message)).length - if (!data.length) - break - } - //Results - computed.commits -= commits - return {commits} - } - //Handle errors - catch (error) { - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\traffic\index.mjs -//Setup - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_traffic_index({login, imports, data, rest, q}, {enabled = false} = {}) { - //Plugin execution - try { - //Check if plugin is enabled and requirements are met - if ((!enabled)||(!q.traffic)) - return null - //Repositories - const repositories = data.user.repositories.nodes.map(({name}) => name) ?? [] - //Get views stats from repositories - const views = {count:0, uniques:0} - const response = await Promise.all(repositories.map(async repo => await rest.repos.getViews({owner:login, repo}))) - //Compute views - response.filter(({data}) => data).map(({data:{count, uniques}}) => (views.count += count, views.uniques += uniques)) - //Format values - views.count = imports.format(views.count) - views.uniques = imports.format(views.uniques) - //Results - return {views} - } - //Handle errors - catch (error) { - if (error.status === 403) - throw {error:{message:`Insufficient token rights`}} - console.debug(error) - throw {error:{message:`An error occured`}} - } - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\plugins\index.mjs -//Imports - - - - - - - - - - - -//Exports - /* harmony default export */ const E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_index = ({ - followup: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_followup_index, - habits: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_habits_index, - isocalendar: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_isocalendar_index, - languages: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_languages_index, - lines: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_lines_index, - music: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_music_index, - pagespeed: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_pagespeed_index, - posts: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_posts_index, - selfskip: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_selfskip_index, - traffic: E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_traffic_index, - }); -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\templates\common.mjs -/** Template common processor */ - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_templates_common({login, q}, {conf, data, rest, graphql, plugins}, {s, pending, imports}) { - - //Init - const computed = data.computed = {commits:0, sponsorships:0, licenses:{favorite:"", used:{}}, token:{}, repositories:{watchers:0, stargazers:0, issues_open:0, issues_closed:0, pr_open:0, pr_merged:0, forks:0}, plugins:{}} - const avatar = imports.imgb64(data.user.avatarUrl) - - //Plugins - for (const name of Object.keys(imports.plugins)) { - pending.push((async () => { - try { - computed.plugins[name] = await imports.plugins[name]({login, q, imports, data, computed, rest, graphql}, plugins[name]) - } - catch (error) { - computed.plugins[name] = error - } - finally { - return {name, result:computed.plugins[name]} - } - })()) - } - - //Iterate through user's repositories - for (const repository of data.user.repositories.nodes) { - //Simple properties with totalCount - for (const property of ["watchers", "stargazers", "issues_open", "issues_closed", "pr_open", "pr_merged"]) - computed.repositories[property] += repository[property].totalCount - //Forks - computed.repositories.forks += repository.forkCount - //License - if (repository.licenseInfo) - computed.licenses.used[repository.licenseInfo.spdxId] = (computed.licenses.used[repository.licenseInfo.spdxId] || 0) + 1 - } - - //Total disk usage - computed.diskUsage = `${imports.bytes(data.user.repositories.totalDiskUsage*1000)}` - - //Compute licenses stats - computed.licenses.favorite = Object.entries(computed.licenses.used).sort(([an, a], [bn, b]) => b - a).slice(0, 1).map(([name, value]) => name) || "" - - //Compute total commits and sponsorships - computed.commits += data.user.contributionsCollection.totalCommitContributions + data.user.contributionsCollection.restrictedContributionsCount - computed.sponsorships = data.user.sponsorshipsAsSponsor.totalCount + data.user.sponsorshipsAsMaintainer.totalCount - - //Compute registration date - const diff = (Date.now()-(new Date(data.user.createdAt)).getTime())/(365*24*60*60*1000) - const years = Math.floor(diff) - const months = Math.ceil((diff-years)*12) - computed.registration = years ? `${years} year${s(years)} ago` : `${months} month${s(months)} ago` - - //Compute calendar - computed.calendar = data.user.calendar.contributionCalendar.weeks.flatMap(({contributionDays}) => contributionDays).slice(0, 14).reverse() - - //Avatar (base64) - computed.avatar = await avatar || "iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mNk+M9QDwADhgGAWjR9awAAAABJRU5ErkJggg==" - - //Token scopes - computed.token.scopes = (await rest.request("HEAD /")).headers["x-oauth-scopes"].split(", ") - - //Meta - data.meta = {version:conf.package.version, author:conf.package.author} - - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\templates\classic\template.mjs -//Imports - - -/** Template processor */ - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_templates_classic_template({login, q}, {conf, data, rest, graphql, plugins}, {s, pending, imports}) { - //Common - await E_Users_lecoq_Documents_GitHub_gitstats_src_templates_common(...arguments) - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\templates\terminal\template.mjs -//Imports - - -/** Template processor */ - /* harmony default export */ async function E_Users_lecoq_Documents_GitHub_gitstats_src_templates_terminal_template({login, q}, {conf, data, rest, graphql, plugins}, {s, pending, imports}) { - //Common - await E_Users_lecoq_Documents_GitHub_gitstats_src_templates_common(...arguments) - //Disable optimization to keep white-spaces - q.raw = true - } -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\templates\index.mjs -//Imports - - - -//Exports - /* harmony default export */ const E_Users_lecoq_Documents_GitHub_gitstats_src_templates_index = ({ - classic: E_Users_lecoq_Documents_GitHub_gitstats_src_templates_classic_template, - terminal: E_Users_lecoq_Documents_GitHub_gitstats_src_templates_terminal_template, - }); -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\puppeteer\cjs-entry.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_puppeteer_cjs_entry = __webpack_require__(34651); -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_puppeteer_cjs_entry_default = /*#__PURE__*/__webpack_require__.n(E_Users_lecoq_Documents_GitHub_gitstats_node_modules_puppeteer_cjs_entry); - -// EXTERNAL MODULE: external "url" -var external_url_ = __webpack_require__(78835); -var external_url_default = /*#__PURE__*/__webpack_require__.n(external_url_); - -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\src\metrics.mjs -//Imports - - - - - - - - - -//Setup - async function metrics({login, q}, {graphql, rest, plugins, conf, die = false}) { - //Compute rendering - try { - - //Init - console.debug(`metrics/compute/${login} > start`) - console.debug(JSON.stringify(q)) - const template = q.template || conf.settings.templates.default - const repositories = Math.max(0, Number(q.repositories)) || conf.settings.repositories || 100 - const pending = [] - const s = (value, end = "") => value > 1 ? {y:"ies", "":"s"}[end] : end - if ((!(template in E_Users_lecoq_Documents_GitHub_gitstats_src_templates_index))||(!(template in conf.templates))||((conf.settings.templates.enabled.length)&&(!conf.settings.templates.enabled.includes(template)))) - throw new Error("unsupported template") - const {query, image, style, fonts} = conf.templates[template] - const data = {base:{}} - - //Base parts - if (("base" in q)&&(!q.base)) - conf.settings.plugins.base.parts.map(part => q[`base.${part}`] = false) - for (const part of conf.settings.plugins.base.parts) - data.base[part] = (`base.${part}` in q) ? !!q[`base.${part}`] : true - - //Placeholder - if (login === "placeholder") - placeholder({data, conf, q}) - //Compute - else { - //Query data from GitHub API - console.debug(`metrics/compute/${login} > graphql query`) - Object.assign(data, await graphql(query - .replace(/[$]login/, `"${login}"`) - .replace(/[$]repositories/, `${repositories}`) - .replace(/[$]calendar.to/, `"${(new Date()).toISOString()}"`) - .replace(/[$]calendar.from/, `"${(new Date(Date.now()-14*24*60*60*1000)).toISOString()}"`) - )) - - //Compute metrics - console.debug(`metrics/compute/${login} > compute`) - const computer = E_Users_lecoq_Documents_GitHub_gitstats_src_templates_index[template].default || E_Users_lecoq_Documents_GitHub_gitstats_src_templates_index[template] - await computer({login, q}, {conf, data, rest, graphql, plugins}, {s, pending, imports:{plugins:E_Users_lecoq_Documents_GitHub_gitstats_src_plugins_index, url: (external_url_default()), imgb64: (E_Users_lecoq_Documents_GitHub_gitstats_node_modules_image_to_base64_image_to_base64_min_default()), axios: (E_Users_lecoq_Documents_GitHub_gitstats_node_modules_axios_index_default()), puppeteer: (E_Users_lecoq_Documents_GitHub_gitstats_node_modules_puppeteer_cjs_entry_default()), format, bytes, shuffle}}) - const promised = await Promise.all(pending) - - //Check plugins errors - if (conf.settings.debug) - for (const {name, result = null} of promised) - console.debug(`plugin ${name} ${result ? result.error ? "failed" : "success" : "ignored"} : ${JSON.stringify(result).replace(/^(.{888}).+/, "$1...")}`) - if (die) { - const errors = promised.filter(({result = null}) => !!result?.error).length - if (errors) - throw new Error(`${errors} error${s(errors)} found...`) - } - } - - //Template rendering - console.debug(`metrics/compute/${login} > render`) - let rendered = await E_Users_lecoq_Documents_GitHub_gitstats_node_modules_ejs_lib_ejs_default().render(image, {...data, s, style, fonts}, {async:true}) - - //Optimize rendering - if ((conf.optimize)&&(!q.raw)) { - console.debug(`metrics/compute/${login} > optimize`) - const svgo = new (E_Users_lecoq_Documents_GitHub_gitstats_node_modules_svgo_lib_svgo_default())({full:true, plugins:[{cleanupAttrs:true}, {inlineStyles:false}]}) - const {data:optimized} = await svgo.optimize(rendered) - rendered = optimized - } - - //Result - console.debug(`metrics/compute/${login} > success`) - return rendered - } - //Internal error - catch (error) { - //User not found - if (((Array.isArray(error.errors))&&(error.errors[0].type === "NOT_FOUND"))) - throw new Error("user not found") - //Generic error - throw error - } - } - -/** Formatter */ - function format(n) { - for (const {u, v} of [{u:"b", v:10**9}, {u:"m", v:10**6}, {u:"k", v:10**3}]) - if (n/v >= 1) - return `${(n/v).toFixed(2).substr(0, 4).replace(/[.]0*$/, "")}${u}` - return n - } - -/** Bytes formatter */ - function bytes(n) { - for (const {u, v} of [{u:"E", v:10**18}, {u:"P", v:10**15}, {u:"T", v:10**12}, {u:"G", v:10**9}, {u:"M", v:10**6}, {u:"k", v:10**3}]) - if (n/v >= 1) - return `${(n/v).toFixed(2).substr(0, 4).replace(/[.]0*$/, "")} ${u}B` - return `${n} byte${n > 1 ? "s" : ""}` - } - -/** Array shuffler */ - function shuffle(array) { - for (let i = array.length-1; i > 0; i--) { - const j = Math.floor(Math.random()*(i+1)) - ;[array[i], array[j]] = [array[j], array[i]] - } - return array - } - -/** Placeholder generator */ - function placeholder({data, conf, q}) { - //Proxifier - const proxify = (target) => typeof target === "object" ? new Proxy(target, { - get(target, property) { - //Primitive conversion - if (property === Symbol.toPrimitive) - return () => "##" - //Iterables - if (property === Symbol.iterator) - return Reflect.get(target, property) - //Plugins should not be proxified by default as they can be toggled by user - if (/^plugins$/.test(property)) - return Reflect.get(target, property) - //Consider no errors on plugins - if (/^error/.test(property)) - return undefined - //Proxify recursively - return proxify(property in target ? Reflect.get(target, property) : {}) - } - }) : target - //Enabled plugins - const enabled = Object.entries(conf.settings.plugins).filter(([key, plugin]) => plugin.enabled).map(([key]) => key).filter(key => (key in q)&&(q[key])) - //Placeholder data - Object.assign(data, { - s(_, letter) { return letter === "y" ? "ies" : "s" }, - meta:{version:conf.package.version, author:conf.package.author, placeholder:true}, - user:proxify({name:`############`, websiteUrl:`########################`}), - computed:proxify({ - avatar:"iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mOcOnfpfwAGfgLYttYINwAAAABJRU5ErkJggg==", - registration:"## years ago", - calendar:new Array(14).fill({color:"#ebedf0"}), - licenses:{favorite:`########`}, - plugins:Object.fromEntries(enabled.map(key => - [key, proxify({ - posts:{source:"########", posts:new Array("posts.limit" in q ? Math.max(Number(q["posts.limit"])||0, 0) : 2).fill({title:"###### ###### ####### ######", date:"####"})}, - music:{provider:"########", tracks:new Array("music.limit" in q ? Math.max(Number(q["music.limit"])||0, 0) : 4).fill({name:"##########", artist:"######", artwork:"iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR42mOcOnfpfwAGfgLYttYINwAAAABJRU5ErkJggg=="})}, - pagespeed:{scores:["Performance", "Accessibility", "Best Practices", "SEO"].map(title => ({title, score:NaN}))}, - followup:{issues:{count:0}, pr:{count:0}}, - habits:{indents:{style:`########`}}, - languages:{favorites:new Array(7).fill(null).map((_, x) => ({x, name:`######`, color:"#ebedf0", value:1/(x+1)}))}, - }[key]??{})] - )), - token:{scopes:[]}, - }), - }) - } -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\@octokit\graphql\dist-node\index.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_octokit_graphql_dist_node_index = __webpack_require__(3584); - -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\@actions\core\lib\core.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_actions_core_lib_core = __webpack_require__(32882); - -// EXTERNAL MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\node_modules\@actions\github\lib\github.js -var E_Users_lecoq_Documents_GitHub_gitstats_node_modules_actions_github_lib_github = __webpack_require__(29483); - -// CONCATENATED MODULE: E:\Users\lecoq\Documents\GitHub\gitstats\action\index.mjs -//Imports - - - - - ((async function () { - //Hack because ES modules are not correctly transpiled with ncc - const [core, github, octokit, setup, metrics] = [E_Users_lecoq_Documents_GitHub_gitstats_node_modules_actions_core_lib_core, E_Users_lecoq_Documents_GitHub_gitstats_node_modules_actions_github_lib_github, E_Users_lecoq_Documents_GitHub_gitstats_node_modules_octokit_graphql_dist_node_index, E_Users_lecoq_Documents_GitHub_gitstats_src_setup_namespaceObject, E_Users_lecoq_Documents_GitHub_gitstats_src_metrics_namespaceObject].map(m => (m && m.default) ? m.default : m) - //Yaml boolean converter - const bool = (value, defaulted = false) => typeof value === "string" ? /^(?:[Tt]rue|[Oo]n|[Yy]es)$/.test(value) : defaulted - //Runner - try { - //Initialization - console.log(`GitHub metrics as SVG image`) - console.log(`========================================================`) - console.log(`Version | 2.3.0`) - process.on("unhandledRejection", error => { throw error }) - - //Skip process if needed - if ((github.context.eventName === "push")&&(github.context.payload)&&(github.context.payload.head_commit)) { - if (/\[Skip GitHub Action\]/.test(github.context.payload.head_commit.message)) { - console.log(`Skipped because [Skip GitHub Action] is in commit message`) - process.exit(0) - } - } - - //Load configuration - const conf = await setup({log:false}) - console.log(`Configuration | loaded`) - - //Load svg template, style, fonts and query - const template = core.getInput("template") || "classic" - console.log(`Template to use | ${template}`) - - //Token for data gathering - const token = core.getInput("token") - console.log(`Github token | ${token ? "provided" : "missing"}`) - if (!token) - throw new Error("You must provide a valid GitHub token to gather your metrics") - const graphql = octokit.graphql.defaults({headers:{authorization: `token ${token}`}}) - console.log(`Github GraphQL API | ok`) - const rest = github.getOctokit(token) - console.log(`Github REST API | ok`) - - //SVG output - const filename = core.getInput("filename") || "github-metrics.svg" - console.log(`SVG output file | ${filename}`) - - //SVG optimization - const optimize = bool(core.getInput("optimize"), true) - conf.optimize = optimize - console.log(`SVG optimization | ${optimize}`) - - //GitHub user - const user = core.getInput("user") || (await rest.users.getAuthenticated()).data.login - console.log(`GitHub user | ${user}`) - - //Debug mode - const debug = bool(core.getInput("debug")) - if (!debug) - console.debug = () => null - console.log(`Debug mode | ${debug}`) - - //Base elements - const base = {} - let parts = (core.getInput("base")||"").split(",").map(part => part.trim()) - for (const part of conf.settings.plugins.base.parts) - base[`base.${part}`] = parts.includes(part) - console.log(`Base parts | ${parts.join(", ") || "(none)"}`) - - //Additional plugins - const plugins = { - lines:{enabled:bool(core.getInput("plugin_lines"))}, - traffic:{enabled:bool(core.getInput("plugin_traffic"))}, - pagespeed:{enabled:bool(core.getInput("plugin_pagespeed"))}, - habits:{enabled:bool(core.getInput("plugin_habits")), from:Number(core.getInput("plugin_habits_from")) || 100}, - selfskip:{enabled:bool(core.getInput("plugin_selfskip"))}, - languages:{enabled:bool(core.getInput("plugin_languages"))}, - followup:{enabled:bool(core.getInput("plugin_followup"))}, - music:{enabled:bool(core.getInput("plugin_music"))}, - posts:{enabled:bool(core.getInput("plugin_posts"))}, - isocalendar:{enabled:bool(core.getInput("plugin_isocalendar"))}, - } - let q = Object.fromEntries(Object.entries(plugins).filter(([key, plugin]) => plugin.enabled).map(([key]) => [key, true])) - console.log(`Plugins enabled | ${Object.entries(plugins).filter(([key, plugin]) => plugin.enabled).map(([key]) => key).join(", ")}`) - //Additional plugins options - //Pagespeed - if (plugins.pagespeed.enabled) { - plugins.pagespeed.token = core.getInput("plugin_pagespeed_token") - console.log(`Pagespeed token | ${plugins.pagespeed.token ? "provided" : "missing"}`) - } - //Music - if (plugins.music.enabled) { - for (const option of ["provider", "mode", "playlist", "limit"]) - q[`music.${option}`] = core.getInput(`plugin_music_${option}`) || null - console.log(`Music provider | ${q["music.provider"]}`) - console.log(`Music plugin mode | ${q["music.mode"]}`) - console.log(`Music playlist | ${q["music.playlist"]}`) - console.log(`Music tracks limit | ${q["music.limit"]}`) - plugins.music.token = core.getInput("plugin_music_token") || "" - console.log(`Music token | ${plugins.music.token ? "provided" : "missing"}`) - } - //Posts - if (plugins.posts.enabled) { - for (const option of ["source", "limit"]) - q[`posts.${option}`] = core.getInput(`plugin_posts_${option}`) || null - console.log(`Posts provider | ${q["posts.provider"]}`) - console.log(`Posts limit | ${q["posts.limit"]}`) - } - - //Repositories to use - const repositories = Number(core.getInput("repositories")) || 100 - console.log(`Repositories to use | ${repositories}`) - - //Die on plugins errors - const die = bool(core.getInput("plugins_errors_fatal")) - console.log(`Plugin errors | ${die ? "die" : "ignore"}`) - - //Built query - q = {...q, ...base, repositories, template} - - //Render metrics - const rendered = await metrics({login:user, q}, {graphql, rest, plugins, conf, die}) - console.log(`Render | complete`) - - //Verify svg - const verify = bool(core.getInput("verify")) - console.log(`Verify SVG | ${verify}`) - if (verify) { - const [libxmljs] = [await __webpack_require__.e(/* import() */ 344).then(__webpack_require__.t.bind(__webpack_require__, 53344, 3))].map(m => (m && m.default) ? m.default : m) - const parsed = libxmljs.parseXml(rendered) - if (parsed.errors.length) - throw new Error(`Malformed SVG : \n${parsed.errors.join("\n")}`) - console.log(`SVG valid | yes`) - } - - //Commit to repository - const dryrun = bool(core.getInput("dryrun")) - if (dryrun) - console.log(`Dry-run | complete`) - else { - //Repository - console.log(`Repository | ${github.context.repo.owner}/${github.context.repo.repo}`) - //Committer token - const token = core.getInput("committer_token") || core.getInput("token") - console.log(`Committer token | ${token ? "provided" : "missing"}`) - if (!token) - throw new Error("You must provide a valid GitHub token to commit your metrics") - const rest = github.getOctokit(token) - console.log(`Committer REST API | ok`) - console.log(`Committer | ${(await rest.users.getAuthenticated()).data.login}`) - //Retrieve previous render SHA to be able to update file content through API - let sha = null - try { - const {data} = await rest.repos.getContent({...github.context.repo, path:filename}) - sha = data.sha - } catch (error) { console.debug(error) } - console.log(`Previous render sha | ${sha || "none"}`) - //Update file content through API - await rest.repos.createOrUpdateFileContents({ - ...github.context.repo, path:filename, message:`Update ${filename} - [Skip GitHub Action]`, - content:Buffer.from(rendered).toString("base64"), - ...(sha ? {sha} : {}) - }) - console.log(`Commit to repo | ok`) - } - - //Success - console.log(`Success !`) - process.exit(0) - - //Errors - } catch (error) { - console.error(error) - core.setFailed(error.message) - process.exit(1) - } -})()).catch(error => process.exit(1)) - -/***/ }), - -/***/ 12541: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; - result["default"] = mod; - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -const os = __importStar(__webpack_require__(12087)); -const utils_1 = __webpack_require__(74332); -/** - * Commands - * - * Command Format: - * ::name key=value,key=value::message - * - * Examples: - * ::warning::This is the message - * ::set-env name=MY_VAR::some value - */ -function issueCommand(command, properties, message) { - const cmd = new Command(command, properties, message); - process.stdout.write(cmd.toString() + os.EOL); -} -exports.issueCommand = issueCommand; -function issue(name, message = '') { - issueCommand(name, {}, message); -} -exports.issue = issue; -const CMD_STRING = '::'; -class Command { - constructor(command, properties, message) { - if (!command) { - command = 'missing.command'; - } - this.command = command; - this.properties = properties; - this.message = message; - } - toString() { - let cmdStr = CMD_STRING + this.command; - if (this.properties && Object.keys(this.properties).length > 0) { - cmdStr += ' '; - let first = true; - for (const key in this.properties) { - if (this.properties.hasOwnProperty(key)) { - const val = this.properties[key]; - if (val) { - if (first) { - first = false; - } - else { - cmdStr += ','; - } - cmdStr += `${key}=${escapeProperty(val)}`; - } - } - } - } - cmdStr += `${CMD_STRING}${escapeData(this.message)}`; - return cmdStr; - } -} -function escapeData(s) { - return utils_1.toCommandValue(s) - .replace(/%/g, '%25') - .replace(/\r/g, '%0D') - .replace(/\n/g, '%0A'); -} -function escapeProperty(s) { - return utils_1.toCommandValue(s) - .replace(/%/g, '%25') - .replace(/\r/g, '%0D') - .replace(/\n/g, '%0A') - .replace(/:/g, '%3A') - .replace(/,/g, '%2C'); -} -//# sourceMappingURL=command.js.map - -/***/ }), - -/***/ 32882: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { - function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } - return new (P || (P = Promise))(function (resolve, reject) { - function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } - function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } - function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } - step((generator = generator.apply(thisArg, _arguments || [])).next()); - }); -}; -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; - result["default"] = mod; - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -const command_1 = __webpack_require__(12541); -const file_command_1 = __webpack_require__(29582); -const utils_1 = __webpack_require__(74332); -const os = __importStar(__webpack_require__(12087)); -const path = __importStar(__webpack_require__(85622)); -/** - * The code to exit an action - */ -var ExitCode; -(function (ExitCode) { - /** - * A code indicating that the action was successful - */ - ExitCode[ExitCode["Success"] = 0] = "Success"; - /** - * A code indicating that the action was a failure - */ - ExitCode[ExitCode["Failure"] = 1] = "Failure"; -})(ExitCode = exports.ExitCode || (exports.ExitCode = {})); -//----------------------------------------------------------------------- -// Variables -//----------------------------------------------------------------------- -/** - * Sets env variable for this action and future actions in the job - * @param name the name of the variable to set - * @param val the value of the variable. Non-string values will be converted to a string via JSON.stringify - */ -// eslint-disable-next-line @typescript-eslint/no-explicit-any -function exportVariable(name, val) { - const convertedVal = utils_1.toCommandValue(val); - process.env[name] = convertedVal; - const filePath = process.env['GITHUB_ENV'] || ''; - if (filePath) { - const delimiter = '_GitHubActionsFileCommandDelimeter_'; - const commandValue = `${name}<<${delimiter}${os.EOL}${convertedVal}${os.EOL}${delimiter}`; - file_command_1.issueCommand('ENV', commandValue); - } - else { - command_1.issueCommand('set-env', { name }, convertedVal); - } -} -exports.exportVariable = exportVariable; -/** - * Registers a secret which will get masked from logs - * @param secret value of the secret - */ -function setSecret(secret) { - command_1.issueCommand('add-mask', {}, secret); -} -exports.setSecret = setSecret; -/** - * Prepends inputPath to the PATH (for this action and future actions) - * @param inputPath - */ -function addPath(inputPath) { - const filePath = process.env['GITHUB_PATH'] || ''; - if (filePath) { - file_command_1.issueCommand('PATH', inputPath); - } - else { - command_1.issueCommand('add-path', {}, inputPath); - } - process.env['PATH'] = `${inputPath}${path.delimiter}${process.env['PATH']}`; -} -exports.addPath = addPath; -/** - * Gets the value of an input. The value is also trimmed. - * - * @param name name of the input to get - * @param options optional. See InputOptions. - * @returns string - */ -function getInput(name, options) { - const val = process.env[`INPUT_${name.replace(/ /g, '_').toUpperCase()}`] || ''; - if (options && options.required && !val) { - throw new Error(`Input required and not supplied: ${name}`); - } - return val.trim(); -} -exports.getInput = getInput; -/** - * Sets the value of an output. - * - * @param name name of the output to set - * @param value value to store. Non-string values will be converted to a string via JSON.stringify - */ -// eslint-disable-next-line @typescript-eslint/no-explicit-any -function setOutput(name, value) { - command_1.issueCommand('set-output', { name }, value); -} -exports.setOutput = setOutput; -/** - * Enables or disables the echoing of commands into stdout for the rest of the step. - * Echoing is disabled by default if ACTIONS_STEP_DEBUG is not set. - * - */ -function setCommandEcho(enabled) { - command_1.issue('echo', enabled ? 'on' : 'off'); -} -exports.setCommandEcho = setCommandEcho; -//----------------------------------------------------------------------- -// Results -//----------------------------------------------------------------------- -/** - * Sets the action status to failed. - * When the action exits it will be with an exit code of 1 - * @param message add error issue message - */ -function setFailed(message) { - process.exitCode = ExitCode.Failure; - error(message); -} -exports.setFailed = setFailed; -//----------------------------------------------------------------------- -// Logging Commands -//----------------------------------------------------------------------- -/** - * Gets whether Actions Step Debug is on or not - */ -function isDebug() { - return process.env['RUNNER_DEBUG'] === '1'; -} -exports.isDebug = isDebug; -/** - * Writes debug message to user log - * @param message debug message - */ -function debug(message) { - command_1.issueCommand('debug', {}, message); -} -exports.debug = debug; -/** - * Adds an error issue - * @param message error issue message. Errors will be converted to string via toString() - */ -function error(message) { - command_1.issue('error', message instanceof Error ? message.toString() : message); -} -exports.error = error; -/** - * Adds an warning issue - * @param message warning issue message. Errors will be converted to string via toString() - */ -function warning(message) { - command_1.issue('warning', message instanceof Error ? message.toString() : message); -} -exports.warning = warning; -/** - * Writes info to log with console.log. - * @param message info message - */ -function info(message) { - process.stdout.write(message + os.EOL); -} -exports.info = info; -/** - * Begin an output group. - * - * Output until the next `groupEnd` will be foldable in this group - * - * @param name The name of the output group - */ -function startGroup(name) { - command_1.issue('group', name); -} -exports.startGroup = startGroup; -/** - * End an output group. - */ -function endGroup() { - command_1.issue('endgroup'); -} -exports.endGroup = endGroup; -/** - * Wrap an asynchronous function call in a group. - * - * Returns the same type as the function itself. - * - * @param name The name of the group - * @param fn The function to wrap in the group - */ -function group(name, fn) { - return __awaiter(this, void 0, void 0, function* () { - startGroup(name); - let result; - try { - result = yield fn(); - } - finally { - endGroup(); - } - return result; - }); -} -exports.group = group; -//----------------------------------------------------------------------- -// Wrapper action state -//----------------------------------------------------------------------- -/** - * Saves state for current action, the state can only be retrieved by this action's post job execution. - * - * @param name name of the state to store - * @param value value to store. Non-string values will be converted to a string via JSON.stringify - */ -// eslint-disable-next-line @typescript-eslint/no-explicit-any -function saveState(name, value) { - command_1.issueCommand('save-state', { name }, value); -} -exports.saveState = saveState; -/** - * Gets the value of an state set by this action's main execution. - * - * @param name name of the state to get - * @returns string - */ -function getState(name) { - return process.env[`STATE_${name}`] || ''; -} -exports.getState = getState; -//# sourceMappingURL=core.js.map - -/***/ }), - -/***/ 29582: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -// For internal use, subject to change. -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; - result["default"] = mod; - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -// We use any as a valid input type -/* eslint-disable @typescript-eslint/no-explicit-any */ -const fs = __importStar(__webpack_require__(35747)); -const os = __importStar(__webpack_require__(12087)); -const utils_1 = __webpack_require__(74332); -function issueCommand(command, message) { - const filePath = process.env[`GITHUB_${command}`]; - if (!filePath) { - throw new Error(`Unable to find environment variable for file command ${command}`); - } - if (!fs.existsSync(filePath)) { - throw new Error(`Missing file at path: ${filePath}`); - } - fs.appendFileSync(filePath, `${utils_1.toCommandValue(message)}${os.EOL}`, { - encoding: 'utf8' - }); -} -exports.issueCommand = issueCommand; -//# sourceMappingURL=file-command.js.map - -/***/ }), - -/***/ 74332: -/***/ ((__unused_webpack_module, exports) => { - -"use strict"; - -// We use any as a valid input type -/* eslint-disable @typescript-eslint/no-explicit-any */ -Object.defineProperty(exports, "__esModule", ({ value: true })); -/** - * Sanitizes an input into a string so it can be passed into issueCommand safely - * @param input input to sanitize into a string - */ -function toCommandValue(input) { - if (input === null || input === undefined) { - return ''; - } - else if (typeof input === 'string' || input instanceof String) { - return input; - } - return JSON.stringify(input); -} -exports.toCommandValue = toCommandValue; -//# sourceMappingURL=utils.js.map - -/***/ }), - -/***/ 84873: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - -Object.defineProperty(exports, "__esModule", ({ value: true })); -exports.Context = void 0; -const fs_1 = __webpack_require__(35747); -const os_1 = __webpack_require__(12087); -class Context { - /** - * Hydrate the context from the environment - */ - constructor() { - this.payload = {}; - if (process.env.GITHUB_EVENT_PATH) { - if (fs_1.existsSync(process.env.GITHUB_EVENT_PATH)) { - this.payload = JSON.parse(fs_1.readFileSync(process.env.GITHUB_EVENT_PATH, { encoding: 'utf8' })); - } - else { - const path = process.env.GITHUB_EVENT_PATH; - process.stdout.write(`GITHUB_EVENT_PATH ${path} does not exist${os_1.EOL}`); - } - } - this.eventName = process.env.GITHUB_EVENT_NAME; - this.sha = process.env.GITHUB_SHA; - this.ref = process.env.GITHUB_REF; - this.workflow = process.env.GITHUB_WORKFLOW; - this.action = process.env.GITHUB_ACTION; - this.actor = process.env.GITHUB_ACTOR; - this.job = process.env.GITHUB_JOB; - this.runNumber = parseInt(process.env.GITHUB_RUN_NUMBER, 10); - this.runId = parseInt(process.env.GITHUB_RUN_ID, 10); - } - get issue() { - const payload = this.payload; - return Object.assign(Object.assign({}, this.repo), { number: (payload.issue || payload.pull_request || payload).number }); - } - get repo() { - if (process.env.GITHUB_REPOSITORY) { - const [owner, repo] = process.env.GITHUB_REPOSITORY.split('/'); - return { owner, repo }; - } - if (this.payload.repository) { - return { - owner: this.payload.repository.owner.login, - repo: this.payload.repository.name - }; - } - throw new Error("context.repo requires a GITHUB_REPOSITORY environment variable like 'owner/repo'"); - } -} -exports.Context = Context; -//# sourceMappingURL=context.js.map - -/***/ }), - -/***/ 29483: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } }); -}) : (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - o[k2] = m[k]; -})); -var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { - Object.defineProperty(o, "default", { enumerable: true, value: v }); -}) : function(o, v) { - o["default"] = v; -}); -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); - __setModuleDefault(result, mod); - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -exports.getOctokit = exports.context = void 0; -const Context = __importStar(__webpack_require__(84873)); -const utils_1 = __webpack_require__(24864); -exports.context = new Context.Context(); -/** - * Returns a hydrated octokit ready to use for GitHub Actions - * - * @param token the repo PAT or GITHUB_TOKEN - * @param options other options to set - */ -function getOctokit(token, options) { - return new utils_1.GitHub(utils_1.getOctokitOptions(token, options)); -} -exports.getOctokit = getOctokit; -//# sourceMappingURL=github.js.map - -/***/ }), - -/***/ 18145: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } }); -}) : (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - o[k2] = m[k]; -})); -var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { - Object.defineProperty(o, "default", { enumerable: true, value: v }); -}) : function(o, v) { - o["default"] = v; -}); -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); - __setModuleDefault(result, mod); - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -exports.getApiBaseUrl = exports.getProxyAgent = exports.getAuthString = void 0; -const httpClient = __importStar(__webpack_require__(66305)); -function getAuthString(token, options) { - if (!token && !options.auth) { - throw new Error('Parameter token or opts.auth is required'); - } - else if (token && options.auth) { - throw new Error('Parameters token and opts.auth may not both be specified'); - } - return typeof options.auth === 'string' ? options.auth : `token ${token}`; -} -exports.getAuthString = getAuthString; -function getProxyAgent(destinationUrl) { - const hc = new httpClient.HttpClient(); - return hc.getAgent(destinationUrl); -} -exports.getProxyAgent = getProxyAgent; -function getApiBaseUrl() { - return process.env['GITHUB_API_URL'] || 'https://api.github.com'; -} -exports.getApiBaseUrl = getApiBaseUrl; -//# sourceMappingURL=utils.js.map - -/***/ }), - -/***/ 24864: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; - -var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } }); -}) : (function(o, m, k, k2) { - if (k2 === undefined) k2 = k; - o[k2] = m[k]; -})); -var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { - Object.defineProperty(o, "default", { enumerable: true, value: v }); -}) : function(o, v) { - o["default"] = v; -}); -var __importStar = (this && this.__importStar) || function (mod) { - if (mod && mod.__esModule) return mod; - var result = {}; - if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k); - __setModuleDefault(result, mod); - return result; -}; -Object.defineProperty(exports, "__esModule", ({ value: true })); -exports.getOctokitOptions = exports.GitHub = exports.context = void 0; -const Context = __importStar(__webpack_require__(84873)); -const Utils = __importStar(__webpack_require__(18145)); -// octokit + plugins -const core_1 = __webpack_require__(40812); -const plugin_rest_endpoint_methods_1 = __webpack_require__(5462); -const plugin_paginate_rest_1 = __webpack_require__(19227); -exports.context = new Context.Context(); -const baseUrl = Utils.getApiBaseUrl(); -const defaults = { - baseUrl, - request: { - agent: Utils.getProxyAgent(baseUrl) - } -}; -exports.GitHub = core_1.Octokit.plugin(plugin_rest_endpoint_methods_1.restEndpointMethods, plugin_paginate_rest_1.paginateRest).defaults(defaults); -/** - * Convience function to correctly format Octokit Options to pass into the constructor. - * - * @param token the repo PAT or GITHUB_TOKEN - * @param options other options to set - */ -function getOctokitOptions(token, options) { - const opts = Object.assign({}, options || {}); // Shallow clone - don't mutate the object provided by the caller - // Auth - const auth = Utils.getAuthString(token, opts); - if (auth) { - opts.auth = auth; - } - return opts; -} -exports.getOctokitOptions = getOctokitOptions; -//# sourceMappingURL=utils.js.map - -/***/ }), - -/***/ 66305: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - -Object.defineProperty(exports, "__esModule", ({ value: true })); -const url = __webpack_require__(78835); -const http = __webpack_require__(98605); -const https = __webpack_require__(57211); -const pm = __webpack_require__(92901); -let tunnel; -var HttpCodes; -(function (HttpCodes) { - HttpCodes[HttpCodes["OK"] = 200] = "OK"; - HttpCodes[HttpCodes["MultipleChoices"] = 300] = "MultipleChoices"; - HttpCodes[HttpCodes["MovedPermanently"] = 301] = "MovedPermanently"; - HttpCodes[HttpCodes["ResourceMoved"] = 302] = "ResourceMoved"; - HttpCodes[HttpCodes["SeeOther"] = 303] = "SeeOther"; - HttpCodes[HttpCodes["NotModified"] = 304] = "NotModified"; - HttpCodes[HttpCodes["UseProxy"] = 305] = "UseProxy"; - HttpCodes[HttpCodes["SwitchProxy"] = 306] = "SwitchProxy"; - HttpCodes[HttpCodes["TemporaryRedirect"] = 307] = "TemporaryRedirect"; - HttpCodes[HttpCodes["PermanentRedirect"] = 308] = "PermanentRedirect"; - HttpCodes[HttpCodes["BadRequest"] = 400] = "BadRequest"; - HttpCodes[HttpCodes["Unauthorized"] = 401] = "Unauthorized"; - HttpCodes[HttpCodes["PaymentRequired"] = 402] = "PaymentRequired"; - HttpCodes[HttpCodes["Forbidden"] = 403] = "Forbidden"; - HttpCodes[HttpCodes["NotFound"] = 404] = "NotFound"; - HttpCodes[HttpCodes["MethodNotAllowed"] = 405] = "MethodNotAllowed"; - HttpCodes[HttpCodes["NotAcceptable"] = 406] = "NotAcceptable"; - HttpCodes[HttpCodes["ProxyAuthenticationRequired"] = 407] = "ProxyAuthenticationRequired"; - HttpCodes[HttpCodes["RequestTimeout"] = 408] = "RequestTimeout"; - HttpCodes[HttpCodes["Conflict"] = 409] = "Conflict"; - HttpCodes[HttpCodes["Gone"] = 410] = "Gone"; - HttpCodes[HttpCodes["TooManyRequests"] = 429] = "TooManyRequests"; - HttpCodes[HttpCodes["InternalServerError"] = 500] = "InternalServerError"; - HttpCodes[HttpCodes["NotImplemented"] = 501] = "NotImplemented"; - HttpCodes[HttpCodes["BadGateway"] = 502] = "BadGateway"; - HttpCodes[HttpCodes["ServiceUnavailable"] = 503] = "ServiceUnavailable"; - HttpCodes[HttpCodes["GatewayTimeout"] = 504] = "GatewayTimeout"; -})(HttpCodes = exports.HttpCodes || (exports.HttpCodes = {})); -var Headers; -(function (Headers) { - Headers["Accept"] = "accept"; - Headers["ContentType"] = "content-type"; -})(Headers = exports.Headers || (exports.Headers = {})); -var MediaTypes; -(function (MediaTypes) { - MediaTypes["ApplicationJson"] = "application/json"; -})(MediaTypes = exports.MediaTypes || (exports.MediaTypes = {})); -/** - * Returns the proxy URL, depending upon the supplied url and proxy environment variables. - * @param serverUrl The server URL where the request will be sent. For example, https://api.github.com - */ -function getProxyUrl(serverUrl) { - let proxyUrl = pm.getProxyUrl(url.parse(serverUrl)); - return proxyUrl ? proxyUrl.href : ''; -} -exports.getProxyUrl = getProxyUrl; -const HttpRedirectCodes = [ - HttpCodes.MovedPermanently, - HttpCodes.ResourceMoved, - HttpCodes.SeeOther, - HttpCodes.TemporaryRedirect, - HttpCodes.PermanentRedirect -]; -const HttpResponseRetryCodes = [ - HttpCodes.BadGateway, - HttpCodes.ServiceUnavailable, - HttpCodes.GatewayTimeout -]; -const RetryableHttpVerbs = ['OPTIONS', 'GET', 'DELETE', 'HEAD']; -const ExponentialBackoffCeiling = 10; -const ExponentialBackoffTimeSlice = 5; -class HttpClientResponse { - constructor(message) { - this.message = message; - } - readBody() { - return new Promise(async (resolve, reject) => { - let output = Buffer.alloc(0); - this.message.on('data', (chunk) => { - output = Buffer.concat([output, chunk]); - }); - this.message.on('end', () => { - resolve(output.toString()); - }); - }); - } -} -exports.HttpClientResponse = HttpClientResponse; -function isHttps(requestUrl) { - let parsedUrl = url.parse(requestUrl); - return parsedUrl.protocol === 'https:'; -} -exports.isHttps = isHttps; -class HttpClient { - constructor(userAgent, handlers, requestOptions) { - this._ignoreSslError = false; - this._allowRedirects = true; - this._allowRedirectDowngrade = false; - this._maxRedirects = 50; - this._allowRetries = false; - this._maxRetries = 1; - this._keepAlive = false; - this._disposed = false; - this.userAgent = userAgent; - this.handlers = handlers || []; - this.requestOptions = requestOptions; - if (requestOptions) { - if (requestOptions.ignoreSslError != null) { - this._ignoreSslError = requestOptions.ignoreSslError; - } - this._socketTimeout = requestOptions.socketTimeout; - if (requestOptions.allowRedirects != null) { - this._allowRedirects = requestOptions.allowRedirects; - } - if (requestOptions.allowRedirectDowngrade != null) { - this._allowRedirectDowngrade = requestOptions.allowRedirectDowngrade; - } - if (requestOptions.maxRedirects != null) { - this._maxRedirects = Math.max(requestOptions.maxRedirects, 0); - } - if (requestOptions.keepAlive != null) { - this._keepAlive = requestOptions.keepAlive; - } - if (requestOptions.allowRetries != null) { - this._allowRetries = requestOptions.allowRetries; - } - if (requestOptions.maxRetries != null) { - this._maxRetries = requestOptions.maxRetries; - } - } - } - options(requestUrl, additionalHeaders) { - return this.request('OPTIONS', requestUrl, null, additionalHeaders || {}); - } - get(requestUrl, additionalHeaders) { - return this.request('GET', requestUrl, null, additionalHeaders || {}); - } - del(requestUrl, additionalHeaders) { - return this.request('DELETE', requestUrl, null, additionalHeaders || {}); - } - post(requestUrl, data, additionalHeaders) { - return this.request('POST', requestUrl, data, additionalHeaders || {}); - } - patch(requestUrl, data, additionalHeaders) { - return this.request('PATCH', requestUrl, data, additionalHeaders || {}); - } - put(requestUrl, data, additionalHeaders) { - return this.request('PUT', requestUrl, data, additionalHeaders || {}); - } - head(requestUrl, additionalHeaders) { - return this.request('HEAD', requestUrl, null, additionalHeaders || {}); - } - sendStream(verb, requestUrl, stream, additionalHeaders) { - return this.request(verb, requestUrl, stream, additionalHeaders); - } - /** - * Gets a typed object from an endpoint - * Be aware that not found returns a null. Other errors (4xx, 5xx) reject the promise - */ - async getJson(requestUrl, additionalHeaders = {}) { - additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); - let res = await this.get(requestUrl, additionalHeaders); - return this._processResponse(res, this.requestOptions); - } - async postJson(requestUrl, obj, additionalHeaders = {}) { - let data = JSON.stringify(obj, null, 2); - additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); - additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); - let res = await this.post(requestUrl, data, additionalHeaders); - return this._processResponse(res, this.requestOptions); - } - async putJson(requestUrl, obj, additionalHeaders = {}) { - let data = JSON.stringify(obj, null, 2); - additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); - additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); - let res = await this.put(requestUrl, data, additionalHeaders); - return this._processResponse(res, this.requestOptions); - } - async patchJson(requestUrl, obj, additionalHeaders = {}) { - let data = JSON.stringify(obj, null, 2); - additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); - additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); - let res = await this.patch(requestUrl, data, additionalHeaders); - return this._processResponse(res, this.requestOptions); - } - /** - * Makes a raw http request. - * All other methods such as get, post, patch, and request ultimately call this. - * Prefer get, del, post and patch - */ - async request(verb, requestUrl, data, headers) { - if (this._disposed) { - throw new Error('Client has already been disposed.'); - } - let parsedUrl = url.parse(requestUrl); - let info = this._prepareRequest(verb, parsedUrl, headers); - // Only perform retries on reads since writes may not be idempotent. - let maxTries = this._allowRetries && RetryableHttpVerbs.indexOf(verb) != -1 - ? this._maxRetries + 1 - : 1; - let numTries = 0; - let response; - while (numTries < maxTries) { - response = await this.requestRaw(info, data); - // Check if it's an authentication challenge - if (response && - response.message && - response.message.statusCode === HttpCodes.Unauthorized) { - let authenticationHandler; - for (let i = 0; i < this.handlers.length; i++) { - if (this.handlers[i].canHandleAuthentication(response)) { - authenticationHandler = this.handlers[i]; - break; - } - } - if (authenticationHandler) { - return authenticationHandler.handleAuthentication(this, info, data); - } - else { - // We have received an unauthorized response but have no handlers to handle it. - // Let the response return to the caller. - return response; - } - } - let redirectsRemaining = this._maxRedirects; - while (HttpRedirectCodes.indexOf(response.message.statusCode) != -1 && - this._allowRedirects && - redirectsRemaining > 0) { - const redirectUrl = response.message.headers['location']; - if (!redirectUrl) { - // if there's no location to redirect to, we won't - break; - } - let parsedRedirectUrl = url.parse(redirectUrl); - if (parsedUrl.protocol == 'https:' && - parsedUrl.protocol != parsedRedirectUrl.protocol && - !this._allowRedirectDowngrade) { - throw new Error('Redirect from HTTPS to HTTP protocol. This downgrade is not allowed for security reasons. If you want to allow this behavior, set the allowRedirectDowngrade option to true.'); - } - // we need to finish reading the response before reassigning response - // which will leak the open socket. - await response.readBody(); - // strip authorization header if redirected to a different hostname - if (parsedRedirectUrl.hostname !== parsedUrl.hostname) { - for (let header in headers) { - // header names are case insensitive - if (header.toLowerCase() === 'authorization') { - delete headers[header]; - } - } - } - // let's make the request with the new redirectUrl - info = this._prepareRequest(verb, parsedRedirectUrl, headers); - response = await this.requestRaw(info, data); - redirectsRemaining--; - } - if (HttpResponseRetryCodes.indexOf(response.message.statusCode) == -1) { - // If not a retry code, return immediately instead of retrying - return response; - } - numTries += 1; - if (numTries < maxTries) { - await response.readBody(); - await this._performExponentialBackoff(numTries); - } - } - return response; - } - /** - * Needs to be called if keepAlive is set to true in request options. - */ - dispose() { - if (this._agent) { - this._agent.destroy(); - } - this._disposed = true; - } - /** - * Raw request. - * @param info - * @param data - */ - requestRaw(info, data) { - return new Promise((resolve, reject) => { - let callbackForResult = function (err, res) { - if (err) { - reject(err); - } - resolve(res); - }; - this.requestRawWithCallback(info, data, callbackForResult); - }); - } - /** - * Raw request with callback. - * @param info - * @param data - * @param onResult - */ - requestRawWithCallback(info, data, onResult) { - let socket; - if (typeof data === 'string') { - info.options.headers['Content-Length'] = Buffer.byteLength(data, 'utf8'); - } - let callbackCalled = false; - let handleResult = (err, res) => { - if (!callbackCalled) { - callbackCalled = true; - onResult(err, res); - } - }; - let req = info.httpModule.request(info.options, (msg) => { - let res = new HttpClientResponse(msg); - handleResult(null, res); - }); - req.on('socket', sock => { - socket = sock; - }); - // If we ever get disconnected, we want the socket to timeout eventually - req.setTimeout(this._socketTimeout || 3 * 60000, () => { - if (socket) { - socket.end(); - } - handleResult(new Error('Request timeout: ' + info.options.path), null); - }); - req.on('error', function (err) { - // err has statusCode property - // res should have headers - handleResult(err, null); - }); - if (data && typeof data === 'string') { - req.write(data, 'utf8'); - } - if (data && typeof data !== 'string') { - data.on('close', function () { - req.end(); - }); - data.pipe(req); - } - else { - req.end(); - } - } - /** - * Gets an http agent. This function is useful when you need an http agent that handles - * routing through a proxy server - depending upon the url and proxy environment variables. - * @param serverUrl The server URL where the request will be sent. For example, https://api.github.com - */ - getAgent(serverUrl) { - let parsedUrl = url.parse(serverUrl); - return this._getAgent(parsedUrl); - } - _prepareRequest(method, requestUrl, headers) { - const info = {}; - info.parsedUrl = requestUrl; - const usingSsl = info.parsedUrl.protocol === 'https:'; - info.httpModule = usingSsl ? https : http; - const defaultPort = usingSsl ? 443 : 80; - info.options = {}; - info.options.host = info.parsedUrl.hostname; - info.options.port = info.parsedUrl.port - ? parseInt(info.parsedUrl.port) - : defaultPort; - info.options.path = - (info.parsedUrl.pathname || '') + (info.parsedUrl.search || ''); - info.options.method = method; - info.options.headers = this._mergeHeaders(headers); - if (this.userAgent != null) { - info.options.headers['user-agent'] = this.userAgent; - } - info.options.agent = this._getAgent(info.parsedUrl); - // gives handlers an opportunity to participate - if (this.handlers) { - this.handlers.forEach(handler => { - handler.prepareRequest(info.options); - }); - } - return info; - } - _mergeHeaders(headers) { - const lowercaseKeys = obj => Object.keys(obj).reduce((c, k) => ((c[k.toLowerCase()] = obj[k]), c), {}); - if (this.requestOptions && this.requestOptions.headers) { - return Object.assign({}, lowercaseKeys(this.requestOptions.headers), lowercaseKeys(headers)); - } - return lowercaseKeys(headers || {}); - } - _getExistingOrDefaultHeader(additionalHeaders, header, _default) { - const lowercaseKeys = obj => Object.keys(obj).reduce((c, k) => ((c[k.toLowerCase()] = obj[k]), c), {}); - let clientHeader; - if (this.requestOptions && this.requestOptions.headers) { - clientHeader = lowercaseKeys(this.requestOptions.headers)[header]; - } - return additionalHeaders[header] || clientHeader || _default; - } - _getAgent(parsedUrl) { - let agent; - let proxyUrl = pm.getProxyUrl(parsedUrl); - let useProxy = proxyUrl && proxyUrl.hostname; - if (this._keepAlive && useProxy) { - agent = this._proxyAgent; - } - if (this._keepAlive && !useProxy) { - agent = this._agent; - } - // if agent is already assigned use that agent. - if (!!agent) { - return agent; - } - const usingSsl = parsedUrl.protocol === 'https:'; - let maxSockets = 100; - if (!!this.requestOptions) { - maxSockets = this.requestOptions.maxSockets || http.globalAgent.maxSockets; - } - if (useProxy) { - // If using proxy, need tunnel - if (!tunnel) { - tunnel = __webpack_require__(34603); - } - const agentOptions = { - maxSockets: maxSockets, - keepAlive: this._keepAlive, - proxy: { - proxyAuth: proxyUrl.auth, - host: proxyUrl.hostname, - port: proxyUrl.port - } - }; - let tunnelAgent; - const overHttps = proxyUrl.protocol === 'https:'; - if (usingSsl) { - tunnelAgent = overHttps ? tunnel.httpsOverHttps : tunnel.httpsOverHttp; - } - else { - tunnelAgent = overHttps ? tunnel.httpOverHttps : tunnel.httpOverHttp; - } - agent = tunnelAgent(agentOptions); - this._proxyAgent = agent; - } - // if reusing agent across request and tunneling agent isn't assigned create a new agent - if (this._keepAlive && !agent) { - const options = { keepAlive: this._keepAlive, maxSockets: maxSockets }; - agent = usingSsl ? new https.Agent(options) : new http.Agent(options); - this._agent = agent; - } - // if not using private agent and tunnel agent isn't setup then use global agent - if (!agent) { - agent = usingSsl ? https.globalAgent : http.globalAgent; - } - if (usingSsl && this._ignoreSslError) { - // we don't want to set NODE_TLS_REJECT_UNAUTHORIZED=0 since that will affect request for entire process - // http.RequestOptions doesn't expose a way to modify RequestOptions.agent.options - // we have to cast it to any and change it directly - agent.options = Object.assign(agent.options || {}, { - rejectUnauthorized: false - }); - } - return agent; - } - _performExponentialBackoff(retryNumber) { - retryNumber = Math.min(ExponentialBackoffCeiling, retryNumber); - const ms = ExponentialBackoffTimeSlice * Math.pow(2, retryNumber); - return new Promise(resolve => setTimeout(() => resolve(), ms)); - } - static dateTimeDeserializer(key, value) { - if (typeof value === 'string') { - let a = new Date(value); - if (!isNaN(a.valueOf())) { - return a; - } - } - return value; - } - async _processResponse(res, options) { - return new Promise(async (resolve, reject) => { - const statusCode = res.message.statusCode; - const response = { - statusCode: statusCode, - result: null, - headers: {} - }; - // not found leads to null obj returned - if (statusCode == HttpCodes.NotFound) { - resolve(response); - } - let obj; - let contents; - // get the result from the body - try { - contents = await res.readBody(); - if (contents && contents.length > 0) { - if (options && options.deserializeDates) { - obj = JSON.parse(contents, HttpClient.dateTimeDeserializer); - } - else { - obj = JSON.parse(contents); - } - response.result = obj; - } - response.headers = res.message.headers; - } - catch (err) { - // Invalid resource (contents not json); leaving result obj null - } - // note that 3xx redirects are handled by the http layer. - if (statusCode > 299) { - let msg; - // if exception/error in body, attempt to get better error - if (obj && obj.message) { - msg = obj.message; - } - else if (contents && contents.length > 0) { - // it may be the case that the exception is in the body message as string - msg = contents; - } - else { - msg = 'Failed request: (' + statusCode + ')'; - } - let err = new Error(msg); - // attach statusCode and body obj (if available) to the error object - err['statusCode'] = statusCode; - if (response.result) { - err['result'] = response.result; - } - reject(err); - } - else { - resolve(response); - } - }); - } -} -exports.HttpClient = HttpClient; - - -/***/ }), - -/***/ 92901: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - -Object.defineProperty(exports, "__esModule", ({ value: true })); -const url = __webpack_require__(78835); -function getProxyUrl(reqUrl) { - let usingSsl = reqUrl.protocol === 'https:'; - let proxyUrl; - if (checkBypass(reqUrl)) { - return proxyUrl; - } - let proxyVar; - if (usingSsl) { - proxyVar = process.env['https_proxy'] || process.env['HTTPS_PROXY']; - } - else { - proxyVar = process.env['http_proxy'] || process.env['HTTP_PROXY']; - } - if (proxyVar) { - proxyUrl = url.parse(proxyVar); - } - return proxyUrl; -} -exports.getProxyUrl = getProxyUrl; -function checkBypass(reqUrl) { - if (!reqUrl.hostname) { - return false; - } - let noProxy = process.env['no_proxy'] || process.env['NO_PROXY'] || ''; - if (!noProxy) { - return false; - } - // Determine the request port - let reqPort; - if (reqUrl.port) { - reqPort = Number(reqUrl.port); - } - else if (reqUrl.protocol === 'http:') { - reqPort = 80; - } - else if (reqUrl.protocol === 'https:') { - reqPort = 443; - } - // Format the request hostname and hostname with port - let upperReqHosts = [reqUrl.hostname.toUpperCase()]; - if (typeof reqPort === 'number') { - upperReqHosts.push(`${upperReqHosts[0]}:${reqPort}`); - } - // Compare request host against noproxy - for (let upperNoProxyItem of noProxy - .split(',') - .map(x => x.trim().toUpperCase()) - .filter(x => x)) { - if (upperReqHosts.some(x => x === upperNoProxyItem)) { - return true; - } - } - return false; -} -exports.checkBypass = checkBypass; - - -/***/ }), - -/***/ 22899: -/***/ ((__unused_webpack_module, exports) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -async function auth(token) { - const tokenType = token.split(/\./).length === 3 ? "app" : /^v\d+\./.test(token) ? "installation" : "oauth"; - return { - type: "token", - token: token, - tokenType - }; -} - -/** - * Prefix token for usage in the Authorization header - * - * @param token OAuth token or JSON Web Token - */ -function withAuthorizationPrefix(token) { - if (token.split(/\./).length === 3) { - return `bearer ${token}`; - } - - return `token ${token}`; -} - -async function hook(token, request, route, parameters) { - const endpoint = request.endpoint.merge(route, parameters); - endpoint.headers.authorization = withAuthorizationPrefix(token); - return request(endpoint); -} - -const createTokenAuth = function createTokenAuth(token) { - if (!token) { - throw new Error("[@octokit/auth-token] No token passed to createTokenAuth"); - } - - if (typeof token !== "string") { - throw new Error("[@octokit/auth-token] Token passed to createTokenAuth is not a string"); - } - - token = token.replace(/^(token|bearer) +/i, ""); - return Object.assign(auth.bind(null, token), { - hook: hook.bind(null, token) - }); -}; - -exports.createTokenAuth = createTokenAuth; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 40812: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -var universalUserAgent = __webpack_require__(1857); -var beforeAfterHook = __webpack_require__(46401); -var request = __webpack_require__(48826); -var graphql = __webpack_require__(3584); -var authToken = __webpack_require__(22899); - -function _defineProperty(obj, key, value) { - if (key in obj) { - Object.defineProperty(obj, key, { - value: value, - enumerable: true, - configurable: true, - writable: true - }); - } else { - obj[key] = value; - } - - return obj; -} - -function ownKeys(object, enumerableOnly) { - var keys = Object.keys(object); - - if (Object.getOwnPropertySymbols) { - var symbols = Object.getOwnPropertySymbols(object); - if (enumerableOnly) symbols = symbols.filter(function (sym) { - return Object.getOwnPropertyDescriptor(object, sym).enumerable; - }); - keys.push.apply(keys, symbols); - } - - return keys; -} - -function _objectSpread2(target) { - for (var i = 1; i < arguments.length; i++) { - var source = arguments[i] != null ? arguments[i] : {}; - - if (i % 2) { - ownKeys(Object(source), true).forEach(function (key) { - _defineProperty(target, key, source[key]); - }); - } else if (Object.getOwnPropertyDescriptors) { - Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); - } else { - ownKeys(Object(source)).forEach(function (key) { - Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); - }); - } - } - - return target; -} - -const VERSION = "3.1.2"; - -class Octokit { - constructor(options = {}) { - const hook = new beforeAfterHook.Collection(); - const requestDefaults = { - baseUrl: request.request.endpoint.DEFAULTS.baseUrl, - headers: {}, - request: Object.assign({}, options.request, { - hook: hook.bind(null, "request") - }), - mediaType: { - previews: [], - format: "" - } - }; // prepend default user agent with `options.userAgent` if set - - requestDefaults.headers["user-agent"] = [options.userAgent, `octokit-core.js/${VERSION} ${universalUserAgent.getUserAgent()}`].filter(Boolean).join(" "); - - if (options.baseUrl) { - requestDefaults.baseUrl = options.baseUrl; - } - - if (options.previews) { - requestDefaults.mediaType.previews = options.previews; - } - - if (options.timeZone) { - requestDefaults.headers["time-zone"] = options.timeZone; - } - - this.request = request.request.defaults(requestDefaults); - this.graphql = graphql.withCustomRequest(this.request).defaults(_objectSpread2(_objectSpread2({}, requestDefaults), {}, { - baseUrl: requestDefaults.baseUrl.replace(/\/api\/v3$/, "/api") - })); - this.log = Object.assign({ - debug: () => {}, - info: () => {}, - warn: console.warn.bind(console), - error: console.error.bind(console) - }, options.log); - this.hook = hook; // (1) If neither `options.authStrategy` nor `options.auth` are set, the `octokit` instance - // is unauthenticated. The `this.auth()` method is a no-op and no request hook is registred. - // (2) If only `options.auth` is set, use the default token authentication strategy. - // (3) If `options.authStrategy` is set then use it and pass in `options.auth`. Always pass own request as many strategies accept a custom request instance. - // TODO: type `options.auth` based on `options.authStrategy`. - - if (!options.authStrategy) { - if (!options.auth) { - // (1) - this.auth = async () => ({ - type: "unauthenticated" - }); - } else { - // (2) - const auth = authToken.createTokenAuth(options.auth); // @ts-ignore ¯\_(ツ)_/¯ - - hook.wrap("request", auth.hook); - this.auth = auth; - } - } else { - const auth = options.authStrategy(Object.assign({ - request: this.request - }, options.auth)); // @ts-ignore ¯\_(ツ)_/¯ - - hook.wrap("request", auth.hook); - this.auth = auth; - } // apply plugins - // https://stackoverflow.com/a/16345172 - - - const classConstructor = this.constructor; - classConstructor.plugins.forEach(plugin => { - Object.assign(this, plugin(this, options)); - }); - } - - static defaults(defaults) { - const OctokitWithDefaults = class extends this { - constructor(...args) { - const options = args[0] || {}; - - if (typeof defaults === "function") { - super(defaults(options)); - return; - } - - super(Object.assign({}, defaults, options, options.userAgent && defaults.userAgent ? { - userAgent: `${options.userAgent} ${defaults.userAgent}` - } : null)); - } - - }; - return OctokitWithDefaults; - } - /** - * Attach a plugin (or many) to your Octokit instance. - * - * @example - * const API = Octokit.plugin(plugin1, plugin2, plugin3, ...) - */ - - - static plugin(...newPlugins) { - var _a; - - const currentPlugins = this.plugins; - const NewOctokit = (_a = class extends this {}, _a.plugins = currentPlugins.concat(newPlugins.filter(plugin => !currentPlugins.includes(plugin))), _a); - return NewOctokit; - } - -} -Octokit.VERSION = VERSION; -Octokit.plugins = []; - -exports.Octokit = Octokit; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 70412: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -var isPlainObject = __webpack_require__(80641); -var universalUserAgent = __webpack_require__(1857); - -function lowercaseKeys(object) { - if (!object) { - return {}; - } - - return Object.keys(object).reduce((newObj, key) => { - newObj[key.toLowerCase()] = object[key]; - return newObj; - }, {}); -} - -function mergeDeep(defaults, options) { - const result = Object.assign({}, defaults); - Object.keys(options).forEach(key => { - if (isPlainObject.isPlainObject(options[key])) { - if (!(key in defaults)) Object.assign(result, { - [key]: options[key] - });else result[key] = mergeDeep(defaults[key], options[key]); - } else { - Object.assign(result, { - [key]: options[key] - }); - } - }); - return result; -} - -function removeUndefinedProperties(obj) { - for (const key in obj) { - if (obj[key] === undefined) { - delete obj[key]; - } - } - - return obj; -} - -function merge(defaults, route, options) { - if (typeof route === "string") { - let [method, url] = route.split(" "); - options = Object.assign(url ? { - method, - url - } : { - url: method - }, options); - } else { - options = Object.assign({}, route); - } // lowercase header names before merging with defaults to avoid duplicates - - - options.headers = lowercaseKeys(options.headers); // remove properties with undefined values before merging - - removeUndefinedProperties(options); - removeUndefinedProperties(options.headers); - const mergedOptions = mergeDeep(defaults || {}, options); // mediaType.previews arrays are merged, instead of overwritten - - if (defaults && defaults.mediaType.previews.length) { - mergedOptions.mediaType.previews = defaults.mediaType.previews.filter(preview => !mergedOptions.mediaType.previews.includes(preview)).concat(mergedOptions.mediaType.previews); - } - - mergedOptions.mediaType.previews = mergedOptions.mediaType.previews.map(preview => preview.replace(/-preview/, "")); - return mergedOptions; -} - -function addQueryParameters(url, parameters) { - const separator = /\?/.test(url) ? "&" : "?"; - const names = Object.keys(parameters); - - if (names.length === 0) { - return url; - } - - return url + separator + names.map(name => { - if (name === "q") { - return "q=" + parameters.q.split("+").map(encodeURIComponent).join("+"); - } - - return `${name}=${encodeURIComponent(parameters[name])}`; - }).join("&"); -} - -const urlVariableRegex = /\{[^}]+\}/g; - -function removeNonChars(variableName) { - return variableName.replace(/^\W+|\W+$/g, "").split(/,/); -} - -function extractUrlVariableNames(url) { - const matches = url.match(urlVariableRegex); - - if (!matches) { - return []; - } - - return matches.map(removeNonChars).reduce((a, b) => a.concat(b), []); -} - -function omit(object, keysToOmit) { - return Object.keys(object).filter(option => !keysToOmit.includes(option)).reduce((obj, key) => { - obj[key] = object[key]; - return obj; - }, {}); -} - -// Based on https://github.com/bramstein/url-template, licensed under BSD -// TODO: create separate package. -// -// Copyright (c) 2012-2014, Bram Stein -// All rights reserved. -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions -// are met: -// 1. Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// 2. Redistributions in binary form must reproduce the above copyright -// notice, this list of conditions and the following disclaimer in the -// documentation and/or other materials provided with the distribution. -// 3. The name of the author may not be used to endorse or promote products -// derived from this software without specific prior written permission. -// THIS SOFTWARE IS PROVIDED BY THE AUTHOR "AS IS" AND ANY EXPRESS OR IMPLIED -// WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF -// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO -// EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, -// INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, -// BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY -// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, -// EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -/* istanbul ignore file */ -function encodeReserved(str) { - return str.split(/(%[0-9A-Fa-f]{2})/g).map(function (part) { - if (!/%[0-9A-Fa-f]/.test(part)) { - part = encodeURI(part).replace(/%5B/g, "[").replace(/%5D/g, "]"); - } - - return part; - }).join(""); -} - -function encodeUnreserved(str) { - return encodeURIComponent(str).replace(/[!'()*]/g, function (c) { - return "%" + c.charCodeAt(0).toString(16).toUpperCase(); - }); -} - -function encodeValue(operator, value, key) { - value = operator === "+" || operator === "#" ? encodeReserved(value) : encodeUnreserved(value); - - if (key) { - return encodeUnreserved(key) + "=" + value; - } else { - return value; - } -} - -function isDefined(value) { - return value !== undefined && value !== null; -} - -function isKeyOperator(operator) { - return operator === ";" || operator === "&" || operator === "?"; -} - -function getValues(context, operator, key, modifier) { - var value = context[key], - result = []; - - if (isDefined(value) && value !== "") { - if (typeof value === "string" || typeof value === "number" || typeof value === "boolean") { - value = value.toString(); - - if (modifier && modifier !== "*") { - value = value.substring(0, parseInt(modifier, 10)); - } - - result.push(encodeValue(operator, value, isKeyOperator(operator) ? key : "")); - } else { - if (modifier === "*") { - if (Array.isArray(value)) { - value.filter(isDefined).forEach(function (value) { - result.push(encodeValue(operator, value, isKeyOperator(operator) ? key : "")); - }); - } else { - Object.keys(value).forEach(function (k) { - if (isDefined(value[k])) { - result.push(encodeValue(operator, value[k], k)); - } - }); - } - } else { - const tmp = []; - - if (Array.isArray(value)) { - value.filter(isDefined).forEach(function (value) { - tmp.push(encodeValue(operator, value)); - }); - } else { - Object.keys(value).forEach(function (k) { - if (isDefined(value[k])) { - tmp.push(encodeUnreserved(k)); - tmp.push(encodeValue(operator, value[k].toString())); - } - }); - } - - if (isKeyOperator(operator)) { - result.push(encodeUnreserved(key) + "=" + tmp.join(",")); - } else if (tmp.length !== 0) { - result.push(tmp.join(",")); - } - } - } - } else { - if (operator === ";") { - if (isDefined(value)) { - result.push(encodeUnreserved(key)); - } - } else if (value === "" && (operator === "&" || operator === "?")) { - result.push(encodeUnreserved(key) + "="); - } else if (value === "") { - result.push(""); - } - } - - return result; -} - -function parseUrl(template) { - return { - expand: expand.bind(null, template) - }; -} - -function expand(template, context) { - var operators = ["+", "#", ".", "/", ";", "?", "&"]; - return template.replace(/\{([^\{\}]+)\}|([^\{\}]+)/g, function (_, expression, literal) { - if (expression) { - let operator = ""; - const values = []; - - if (operators.indexOf(expression.charAt(0)) !== -1) { - operator = expression.charAt(0); - expression = expression.substr(1); - } - - expression.split(/,/g).forEach(function (variable) { - var tmp = /([^:\*]*)(?::(\d+)|(\*))?/.exec(variable); - values.push(getValues(context, operator, tmp[1], tmp[2] || tmp[3])); - }); - - if (operator && operator !== "+") { - var separator = ","; - - if (operator === "?") { - separator = "&"; - } else if (operator !== "#") { - separator = operator; - } - - return (values.length !== 0 ? operator : "") + values.join(separator); - } else { - return values.join(","); - } - } else { - return encodeReserved(literal); - } - }); -} - -function parse(options) { - // https://fetch.spec.whatwg.org/#methods - let method = options.method.toUpperCase(); // replace :varname with {varname} to make it RFC 6570 compatible - - let url = (options.url || "/").replace(/:([a-z]\w+)/g, "{$1}"); - let headers = Object.assign({}, options.headers); - let body; - let parameters = omit(options, ["method", "baseUrl", "url", "headers", "request", "mediaType"]); // extract variable names from URL to calculate remaining variables later - - const urlVariableNames = extractUrlVariableNames(url); - url = parseUrl(url).expand(parameters); - - if (!/^http/.test(url)) { - url = options.baseUrl + url; - } - - const omittedParameters = Object.keys(options).filter(option => urlVariableNames.includes(option)).concat("baseUrl"); - const remainingParameters = omit(parameters, omittedParameters); - const isBinaryRequest = /application\/octet-stream/i.test(headers.accept); - - if (!isBinaryRequest) { - if (options.mediaType.format) { - // e.g. application/vnd.github.v3+json => application/vnd.github.v3.raw - headers.accept = headers.accept.split(/,/).map(preview => preview.replace(/application\/vnd(\.\w+)(\.v3)?(\.\w+)?(\+json)?$/, `application/vnd$1$2.${options.mediaType.format}`)).join(","); - } - - if (options.mediaType.previews.length) { - const previewsFromAcceptHeader = headers.accept.match(/[\w-]+(?=-preview)/g) || []; - headers.accept = previewsFromAcceptHeader.concat(options.mediaType.previews).map(preview => { - const format = options.mediaType.format ? `.${options.mediaType.format}` : "+json"; - return `application/vnd.github.${preview}-preview${format}`; - }).join(","); - } - } // for GET/HEAD requests, set URL query parameters from remaining parameters - // for PATCH/POST/PUT/DELETE requests, set request body from remaining parameters - - - if (["GET", "HEAD"].includes(method)) { - url = addQueryParameters(url, remainingParameters); - } else { - if ("data" in remainingParameters) { - body = remainingParameters.data; - } else { - if (Object.keys(remainingParameters).length) { - body = remainingParameters; - } else { - headers["content-length"] = 0; - } - } - } // default content-type for JSON if body is set - - - if (!headers["content-type"] && typeof body !== "undefined") { - headers["content-type"] = "application/json; charset=utf-8"; - } // GitHub expects 'content-length: 0' header for PUT/PATCH requests without body. - // fetch does not allow to set `content-length` header, but we can set body to an empty string - - - if (["PATCH", "PUT"].includes(method) && typeof body === "undefined") { - body = ""; - } // Only return body/request keys if present - - - return Object.assign({ - method, - url, - headers - }, typeof body !== "undefined" ? { - body - } : null, options.request ? { - request: options.request - } : null); -} - -function endpointWithDefaults(defaults, route, options) { - return parse(merge(defaults, route, options)); -} - -function withDefaults(oldDefaults, newDefaults) { - const DEFAULTS = merge(oldDefaults, newDefaults); - const endpoint = endpointWithDefaults.bind(null, DEFAULTS); - return Object.assign(endpoint, { - DEFAULTS, - defaults: withDefaults.bind(null, DEFAULTS), - merge: merge.bind(null, DEFAULTS), - parse - }); -} - -const VERSION = "6.0.8"; - -const userAgent = `octokit-endpoint.js/${VERSION} ${universalUserAgent.getUserAgent()}`; // DEFAULTS has all properties set that EndpointOptions has, except url. -// So we use RequestParameters and add method as additional required property. - -const DEFAULTS = { - method: "GET", - baseUrl: "https://api.github.com", - headers: { - accept: "application/vnd.github.v3+json", - "user-agent": userAgent - }, - mediaType: { - format: "", - previews: [] - } -}; - -const endpoint = withDefaults(null, DEFAULTS); - -exports.endpoint = endpoint; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 3584: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -var request = __webpack_require__(48826); -var universalUserAgent = __webpack_require__(1857); - -const VERSION = "4.5.6"; - -class GraphqlError extends Error { - constructor(request, response) { - const message = response.data.errors[0].message; - super(message); - Object.assign(this, response.data); - Object.assign(this, { - headers: response.headers - }); - this.name = "GraphqlError"; - this.request = request; // Maintains proper stack trace (only available on V8) - - /* istanbul ignore next */ - - if (Error.captureStackTrace) { - Error.captureStackTrace(this, this.constructor); - } - } - -} - -const NON_VARIABLE_OPTIONS = ["method", "baseUrl", "url", "headers", "request", "query", "mediaType"]; -const GHES_V3_SUFFIX_REGEX = /\/api\/v3\/?$/; -function graphql(request, query, options) { - if (typeof query === "string" && options && "query" in options) { - return Promise.reject(new Error(`[@octokit/graphql] "query" cannot be used as variable name`)); - } - - const parsedOptions = typeof query === "string" ? Object.assign({ - query - }, options) : query; - const requestOptions = Object.keys(parsedOptions).reduce((result, key) => { - if (NON_VARIABLE_OPTIONS.includes(key)) { - result[key] = parsedOptions[key]; - return result; - } - - if (!result.variables) { - result.variables = {}; - } - - result.variables[key] = parsedOptions[key]; - return result; - }, {}); // workaround for GitHub Enterprise baseUrl set with /api/v3 suffix - // https://github.com/octokit/auth-app.js/issues/111#issuecomment-657610451 - - const baseUrl = parsedOptions.baseUrl || request.endpoint.DEFAULTS.baseUrl; - - if (GHES_V3_SUFFIX_REGEX.test(baseUrl)) { - requestOptions.url = baseUrl.replace(GHES_V3_SUFFIX_REGEX, "/api/graphql"); - } - - return request(requestOptions).then(response => { - if (response.data.errors) { - const headers = {}; - - for (const key of Object.keys(response.headers)) { - headers[key] = response.headers[key]; - } - - throw new GraphqlError(requestOptions, { - headers, - data: response.data - }); - } - - return response.data.data; - }); -} - -function withDefaults(request$1, newDefaults) { - const newRequest = request$1.defaults(newDefaults); - - const newApi = (query, options) => { - return graphql(newRequest, query, options); - }; - - return Object.assign(newApi, { - defaults: withDefaults.bind(null, newRequest), - endpoint: request.request.endpoint - }); -} - -const graphql$1 = withDefaults(request.request, { - headers: { - "user-agent": `octokit-graphql.js/${VERSION} ${universalUserAgent.getUserAgent()}` - }, - method: "POST", - url: "/graphql" -}); -function withCustomRequest(customRequest) { - return withDefaults(customRequest, { - method: "POST", - url: "/graphql" - }); -} - -exports.graphql = graphql$1; -exports.withCustomRequest = withCustomRequest; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 19227: -/***/ ((__unused_webpack_module, exports) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -const VERSION = "2.4.0"; - -/** - * Some “list” response that can be paginated have a different response structure - * - * They have a `total_count` key in the response (search also has `incomplete_results`, - * /installation/repositories also has `repository_selection`), as well as a key with - * the list of the items which name varies from endpoint to endpoint. - * - * Octokit normalizes these responses so that paginated results are always returned following - * the same structure. One challenge is that if the list response has only one page, no Link - * header is provided, so this header alone is not sufficient to check wether a response is - * paginated or not. - * - * We check if a "total_count" key is present in the response data, but also make sure that - * a "url" property is not, as the "Get the combined status for a specific ref" endpoint would - * otherwise match: https://developer.github.com/v3/repos/statuses/#get-the-combined-status-for-a-specific-ref - */ -function normalizePaginatedListResponse(response) { - const responseNeedsNormalization = "total_count" in response.data && !("url" in response.data); - if (!responseNeedsNormalization) return response; // keep the additional properties intact as there is currently no other way - // to retrieve the same information. - - const incompleteResults = response.data.incomplete_results; - const repositorySelection = response.data.repository_selection; - const totalCount = response.data.total_count; - delete response.data.incomplete_results; - delete response.data.repository_selection; - delete response.data.total_count; - const namespaceKey = Object.keys(response.data)[0]; - const data = response.data[namespaceKey]; - response.data = data; - - if (typeof incompleteResults !== "undefined") { - response.data.incomplete_results = incompleteResults; - } - - if (typeof repositorySelection !== "undefined") { - response.data.repository_selection = repositorySelection; - } - - response.data.total_count = totalCount; - return response; -} - -function iterator(octokit, route, parameters) { - const options = typeof route === "function" ? route.endpoint(parameters) : octokit.request.endpoint(route, parameters); - const requestMethod = typeof route === "function" ? route : octokit.request; - const method = options.method; - const headers = options.headers; - let url = options.url; - return { - [Symbol.asyncIterator]: () => ({ - next() { - if (!url) { - return Promise.resolve({ - done: true - }); - } - - return requestMethod({ - method, - url, - headers - }).then(normalizePaginatedListResponse).then(response => { - // `response.headers.link` format: - // '; rel="next", ; rel="last"' - // sets `url` to undefined if "next" URL is not present or `link` header is not set - url = ((response.headers.link || "").match(/<([^>]+)>;\s*rel="next"/) || [])[1]; - return { - value: response - }; - }); - } - - }) - }; -} - -function paginate(octokit, route, parameters, mapFn) { - if (typeof parameters === "function") { - mapFn = parameters; - parameters = undefined; - } - - return gather(octokit, [], iterator(octokit, route, parameters)[Symbol.asyncIterator](), mapFn); -} - -function gather(octokit, results, iterator, mapFn) { - return iterator.next().then(result => { - if (result.done) { - return results; - } - - let earlyExit = false; - - function done() { - earlyExit = true; - } - - results = results.concat(mapFn ? mapFn(result.value, done) : result.value.data); - - if (earlyExit) { - return results; - } - - return gather(octokit, results, iterator, mapFn); - }); -} - -/** - * @param octokit Octokit instance - * @param options Options passed to Octokit constructor - */ - -function paginateRest(octokit) { - return { - paginate: Object.assign(paginate.bind(null, octokit), { - iterator: iterator.bind(null, octokit) - }) - }; -} -paginateRest.VERSION = VERSION; - -exports.paginateRest = paginateRest; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 5462: -/***/ ((__unused_webpack_module, exports) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -const Endpoints = { - actions: { - addSelectedRepoToOrgSecret: ["PUT /orgs/{org}/actions/secrets/{secret_name}/repositories/{repository_id}"], - cancelWorkflowRun: ["POST /repos/{owner}/{repo}/actions/runs/{run_id}/cancel"], - createOrUpdateOrgSecret: ["PUT /orgs/{org}/actions/secrets/{secret_name}"], - createOrUpdateRepoSecret: ["PUT /repos/{owner}/{repo}/actions/secrets/{secret_name}"], - createRegistrationTokenForOrg: ["POST /orgs/{org}/actions/runners/registration-token"], - createRegistrationTokenForRepo: ["POST /repos/{owner}/{repo}/actions/runners/registration-token"], - createRemoveTokenForOrg: ["POST /orgs/{org}/actions/runners/remove-token"], - createRemoveTokenForRepo: ["POST /repos/{owner}/{repo}/actions/runners/remove-token"], - createWorkflowDispatch: ["POST /repos/{owner}/{repo}/actions/workflows/{workflow_id}/dispatches"], - deleteArtifact: ["DELETE /repos/{owner}/{repo}/actions/artifacts/{artifact_id}"], - deleteOrgSecret: ["DELETE /orgs/{org}/actions/secrets/{secret_name}"], - deleteRepoSecret: ["DELETE /repos/{owner}/{repo}/actions/secrets/{secret_name}"], - deleteSelfHostedRunnerFromOrg: ["DELETE /orgs/{org}/actions/runners/{runner_id}"], - deleteSelfHostedRunnerFromRepo: ["DELETE /repos/{owner}/{repo}/actions/runners/{runner_id}"], - deleteWorkflowRun: ["DELETE /repos/{owner}/{repo}/actions/runs/{run_id}"], - deleteWorkflowRunLogs: ["DELETE /repos/{owner}/{repo}/actions/runs/{run_id}/logs"], - downloadArtifact: ["GET /repos/{owner}/{repo}/actions/artifacts/{artifact_id}/{archive_format}"], - downloadJobLogsForWorkflowRun: ["GET /repos/{owner}/{repo}/actions/jobs/{job_id}/logs"], - downloadWorkflowRunLogs: ["GET /repos/{owner}/{repo}/actions/runs/{run_id}/logs"], - getArtifact: ["GET /repos/{owner}/{repo}/actions/artifacts/{artifact_id}"], - getJobForWorkflowRun: ["GET /repos/{owner}/{repo}/actions/jobs/{job_id}"], - getOrgPublicKey: ["GET /orgs/{org}/actions/secrets/public-key"], - getOrgSecret: ["GET /orgs/{org}/actions/secrets/{secret_name}"], - getRepoPublicKey: ["GET /repos/{owner}/{repo}/actions/secrets/public-key"], - getRepoSecret: ["GET /repos/{owner}/{repo}/actions/secrets/{secret_name}"], - getSelfHostedRunnerForOrg: ["GET /orgs/{org}/actions/runners/{runner_id}"], - getSelfHostedRunnerForRepo: ["GET /repos/{owner}/{repo}/actions/runners/{runner_id}"], - getWorkflow: ["GET /repos/{owner}/{repo}/actions/workflows/{workflow_id}"], - getWorkflowRun: ["GET /repos/{owner}/{repo}/actions/runs/{run_id}"], - getWorkflowRunUsage: ["GET /repos/{owner}/{repo}/actions/runs/{run_id}/timing"], - getWorkflowUsage: ["GET /repos/{owner}/{repo}/actions/workflows/{workflow_id}/timing"], - listArtifactsForRepo: ["GET /repos/{owner}/{repo}/actions/artifacts"], - listJobsForWorkflowRun: ["GET /repos/{owner}/{repo}/actions/runs/{run_id}/jobs"], - listOrgSecrets: ["GET /orgs/{org}/actions/secrets"], - listRepoSecrets: ["GET /repos/{owner}/{repo}/actions/secrets"], - listRepoWorkflows: ["GET /repos/{owner}/{repo}/actions/workflows"], - listRunnerApplicationsForOrg: ["GET /orgs/{org}/actions/runners/downloads"], - listRunnerApplicationsForRepo: ["GET /repos/{owner}/{repo}/actions/runners/downloads"], - listSelectedReposForOrgSecret: ["GET /orgs/{org}/actions/secrets/{secret_name}/repositories"], - listSelfHostedRunnersForOrg: ["GET /orgs/{org}/actions/runners"], - listSelfHostedRunnersForRepo: ["GET /repos/{owner}/{repo}/actions/runners"], - listWorkflowRunArtifacts: ["GET /repos/{owner}/{repo}/actions/runs/{run_id}/artifacts"], - listWorkflowRuns: ["GET /repos/{owner}/{repo}/actions/workflows/{workflow_id}/runs"], - listWorkflowRunsForRepo: ["GET /repos/{owner}/{repo}/actions/runs"], - reRunWorkflow: ["POST /repos/{owner}/{repo}/actions/runs/{run_id}/rerun"], - removeSelectedRepoFromOrgSecret: ["DELETE /orgs/{org}/actions/secrets/{secret_name}/repositories/{repository_id}"], - setSelectedReposForOrgSecret: ["PUT /orgs/{org}/actions/secrets/{secret_name}/repositories"] - }, - activity: { - checkRepoIsStarredByAuthenticatedUser: ["GET /user/starred/{owner}/{repo}"], - deleteRepoSubscription: ["DELETE /repos/{owner}/{repo}/subscription"], - deleteThreadSubscription: ["DELETE /notifications/threads/{thread_id}/subscription"], - getFeeds: ["GET /feeds"], - getRepoSubscription: ["GET /repos/{owner}/{repo}/subscription"], - getThread: ["GET /notifications/threads/{thread_id}"], - getThreadSubscriptionForAuthenticatedUser: ["GET /notifications/threads/{thread_id}/subscription"], - listEventsForAuthenticatedUser: ["GET /users/{username}/events"], - listNotificationsForAuthenticatedUser: ["GET /notifications"], - listOrgEventsForAuthenticatedUser: ["GET /users/{username}/events/orgs/{org}"], - listPublicEvents: ["GET /events"], - listPublicEventsForRepoNetwork: ["GET /networks/{owner}/{repo}/events"], - listPublicEventsForUser: ["GET /users/{username}/events/public"], - listPublicOrgEvents: ["GET /orgs/{org}/events"], - listReceivedEventsForUser: ["GET /users/{username}/received_events"], - listReceivedPublicEventsForUser: ["GET /users/{username}/received_events/public"], - listRepoEvents: ["GET /repos/{owner}/{repo}/events"], - listRepoNotificationsForAuthenticatedUser: ["GET /repos/{owner}/{repo}/notifications"], - listReposStarredByAuthenticatedUser: ["GET /user/starred"], - listReposStarredByUser: ["GET /users/{username}/starred"], - listReposWatchedByUser: ["GET /users/{username}/subscriptions"], - listStargazersForRepo: ["GET /repos/{owner}/{repo}/stargazers"], - listWatchedReposForAuthenticatedUser: ["GET /user/subscriptions"], - listWatchersForRepo: ["GET /repos/{owner}/{repo}/subscribers"], - markNotificationsAsRead: ["PUT /notifications"], - markRepoNotificationsAsRead: ["PUT /repos/{owner}/{repo}/notifications"], - markThreadAsRead: ["PATCH /notifications/threads/{thread_id}"], - setRepoSubscription: ["PUT /repos/{owner}/{repo}/subscription"], - setThreadSubscription: ["PUT /notifications/threads/{thread_id}/subscription"], - starRepoForAuthenticatedUser: ["PUT /user/starred/{owner}/{repo}"], - unstarRepoForAuthenticatedUser: ["DELETE /user/starred/{owner}/{repo}"] - }, - apps: { - addRepoToInstallation: ["PUT /user/installations/{installation_id}/repositories/{repository_id}"], - checkToken: ["POST /applications/{client_id}/token"], - createContentAttachment: ["POST /content_references/{content_reference_id}/attachments", { - mediaType: { - previews: ["corsair"] - } - }], - createFromManifest: ["POST /app-manifests/{code}/conversions"], - createInstallationAccessToken: ["POST /app/installations/{installation_id}/access_tokens"], - deleteAuthorization: ["DELETE /applications/{client_id}/grant"], - deleteInstallation: ["DELETE /app/installations/{installation_id}"], - deleteToken: ["DELETE /applications/{client_id}/token"], - getAuthenticated: ["GET /app"], - getBySlug: ["GET /apps/{app_slug}"], - getInstallation: ["GET /app/installations/{installation_id}"], - getOrgInstallation: ["GET /orgs/{org}/installation"], - getRepoInstallation: ["GET /repos/{owner}/{repo}/installation"], - getSubscriptionPlanForAccount: ["GET /marketplace_listing/accounts/{account_id}"], - getSubscriptionPlanForAccountStubbed: ["GET /marketplace_listing/stubbed/accounts/{account_id}"], - getUserInstallation: ["GET /users/{username}/installation"], - listAccountsForPlan: ["GET /marketplace_listing/plans/{plan_id}/accounts"], - listAccountsForPlanStubbed: ["GET /marketplace_listing/stubbed/plans/{plan_id}/accounts"], - listInstallationReposForAuthenticatedUser: ["GET /user/installations/{installation_id}/repositories"], - listInstallations: ["GET /app/installations"], - listInstallationsForAuthenticatedUser: ["GET /user/installations"], - listPlans: ["GET /marketplace_listing/plans"], - listPlansStubbed: ["GET /marketplace_listing/stubbed/plans"], - listReposAccessibleToInstallation: ["GET /installation/repositories"], - listSubscriptionsForAuthenticatedUser: ["GET /user/marketplace_purchases"], - listSubscriptionsForAuthenticatedUserStubbed: ["GET /user/marketplace_purchases/stubbed"], - removeRepoFromInstallation: ["DELETE /user/installations/{installation_id}/repositories/{repository_id}"], - resetToken: ["PATCH /applications/{client_id}/token"], - revokeInstallationAccessToken: ["DELETE /installation/token"], - suspendInstallation: ["PUT /app/installations/{installation_id}/suspended"], - unsuspendInstallation: ["DELETE /app/installations/{installation_id}/suspended"] - }, - billing: { - getGithubActionsBillingOrg: ["GET /orgs/{org}/settings/billing/actions"], - getGithubActionsBillingUser: ["GET /users/{username}/settings/billing/actions"], - getGithubPackagesBillingOrg: ["GET /orgs/{org}/settings/billing/packages"], - getGithubPackagesBillingUser: ["GET /users/{username}/settings/billing/packages"], - getSharedStorageBillingOrg: ["GET /orgs/{org}/settings/billing/shared-storage"], - getSharedStorageBillingUser: ["GET /users/{username}/settings/billing/shared-storage"] - }, - checks: { - create: ["POST /repos/{owner}/{repo}/check-runs", { - mediaType: { - previews: ["antiope"] - } - }], - createSuite: ["POST /repos/{owner}/{repo}/check-suites", { - mediaType: { - previews: ["antiope"] - } - }], - get: ["GET /repos/{owner}/{repo}/check-runs/{check_run_id}", { - mediaType: { - previews: ["antiope"] - } - }], - getSuite: ["GET /repos/{owner}/{repo}/check-suites/{check_suite_id}", { - mediaType: { - previews: ["antiope"] - } - }], - listAnnotations: ["GET /repos/{owner}/{repo}/check-runs/{check_run_id}/annotations", { - mediaType: { - previews: ["antiope"] - } - }], - listForRef: ["GET /repos/{owner}/{repo}/commits/{ref}/check-runs", { - mediaType: { - previews: ["antiope"] - } - }], - listForSuite: ["GET /repos/{owner}/{repo}/check-suites/{check_suite_id}/check-runs", { - mediaType: { - previews: ["antiope"] - } - }], - listSuitesForRef: ["GET /repos/{owner}/{repo}/commits/{ref}/check-suites", { - mediaType: { - previews: ["antiope"] - } - }], - rerequestSuite: ["POST /repos/{owner}/{repo}/check-suites/{check_suite_id}/rerequest", { - mediaType: { - previews: ["antiope"] - } - }], - setSuitesPreferences: ["PATCH /repos/{owner}/{repo}/check-suites/preferences", { - mediaType: { - previews: ["antiope"] - } - }], - update: ["PATCH /repos/{owner}/{repo}/check-runs/{check_run_id}", { - mediaType: { - previews: ["antiope"] - } - }] - }, - codeScanning: { - getAlert: ["GET /repos/{owner}/{repo}/code-scanning/alerts/{alert_number}", {}, { - renamedParameters: { - alert_id: "alert_number" - } - }], - listAlertsForRepo: ["GET /repos/{owner}/{repo}/code-scanning/alerts"], - listRecentAnalyses: ["GET /repos/{owner}/{repo}/code-scanning/analyses"], - updateAlert: ["PATCH /repos/{owner}/{repo}/code-scanning/alerts/{alert_number}"], - uploadSarif: ["POST /repos/{owner}/{repo}/code-scanning/sarifs"] - }, - codesOfConduct: { - getAllCodesOfConduct: ["GET /codes_of_conduct", { - mediaType: { - previews: ["scarlet-witch"] - } - }], - getConductCode: ["GET /codes_of_conduct/{key}", { - mediaType: { - previews: ["scarlet-witch"] - } - }], - getForRepo: ["GET /repos/{owner}/{repo}/community/code_of_conduct", { - mediaType: { - previews: ["scarlet-witch"] - } - }] - }, - emojis: { - get: ["GET /emojis"] - }, - gists: { - checkIsStarred: ["GET /gists/{gist_id}/star"], - create: ["POST /gists"], - createComment: ["POST /gists/{gist_id}/comments"], - delete: ["DELETE /gists/{gist_id}"], - deleteComment: ["DELETE /gists/{gist_id}/comments/{comment_id}"], - fork: ["POST /gists/{gist_id}/forks"], - get: ["GET /gists/{gist_id}"], - getComment: ["GET /gists/{gist_id}/comments/{comment_id}"], - getRevision: ["GET /gists/{gist_id}/{sha}"], - list: ["GET /gists"], - listComments: ["GET /gists/{gist_id}/comments"], - listCommits: ["GET /gists/{gist_id}/commits"], - listForUser: ["GET /users/{username}/gists"], - listForks: ["GET /gists/{gist_id}/forks"], - listPublic: ["GET /gists/public"], - listStarred: ["GET /gists/starred"], - star: ["PUT /gists/{gist_id}/star"], - unstar: ["DELETE /gists/{gist_id}/star"], - update: ["PATCH /gists/{gist_id}"], - updateComment: ["PATCH /gists/{gist_id}/comments/{comment_id}"] - }, - git: { - createBlob: ["POST /repos/{owner}/{repo}/git/blobs"], - createCommit: ["POST /repos/{owner}/{repo}/git/commits"], - createRef: ["POST /repos/{owner}/{repo}/git/refs"], - createTag: ["POST /repos/{owner}/{repo}/git/tags"], - createTree: ["POST /repos/{owner}/{repo}/git/trees"], - deleteRef: ["DELETE /repos/{owner}/{repo}/git/refs/{ref}"], - getBlob: ["GET /repos/{owner}/{repo}/git/blobs/{file_sha}"], - getCommit: ["GET /repos/{owner}/{repo}/git/commits/{commit_sha}"], - getRef: ["GET /repos/{owner}/{repo}/git/ref/{ref}"], - getTag: ["GET /repos/{owner}/{repo}/git/tags/{tag_sha}"], - getTree: ["GET /repos/{owner}/{repo}/git/trees/{tree_sha}"], - listMatchingRefs: ["GET /repos/{owner}/{repo}/git/matching-refs/{ref}"], - updateRef: ["PATCH /repos/{owner}/{repo}/git/refs/{ref}"] - }, - gitignore: { - getAllTemplates: ["GET /gitignore/templates"], - getTemplate: ["GET /gitignore/templates/{name}"] - }, - interactions: { - getRestrictionsForOrg: ["GET /orgs/{org}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }], - getRestrictionsForRepo: ["GET /repos/{owner}/{repo}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }], - removeRestrictionsForOrg: ["DELETE /orgs/{org}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }], - removeRestrictionsForRepo: ["DELETE /repos/{owner}/{repo}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }], - setRestrictionsForOrg: ["PUT /orgs/{org}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }], - setRestrictionsForRepo: ["PUT /repos/{owner}/{repo}/interaction-limits", { - mediaType: { - previews: ["sombra"] - } - }] - }, - issues: { - addAssignees: ["POST /repos/{owner}/{repo}/issues/{issue_number}/assignees"], - addLabels: ["POST /repos/{owner}/{repo}/issues/{issue_number}/labels"], - checkUserCanBeAssigned: ["GET /repos/{owner}/{repo}/assignees/{assignee}"], - create: ["POST /repos/{owner}/{repo}/issues"], - createComment: ["POST /repos/{owner}/{repo}/issues/{issue_number}/comments"], - createLabel: ["POST /repos/{owner}/{repo}/labels"], - createMilestone: ["POST /repos/{owner}/{repo}/milestones"], - deleteComment: ["DELETE /repos/{owner}/{repo}/issues/comments/{comment_id}"], - deleteLabel: ["DELETE /repos/{owner}/{repo}/labels/{name}"], - deleteMilestone: ["DELETE /repos/{owner}/{repo}/milestones/{milestone_number}"], - get: ["GET /repos/{owner}/{repo}/issues/{issue_number}"], - getComment: ["GET /repos/{owner}/{repo}/issues/comments/{comment_id}"], - getEvent: ["GET /repos/{owner}/{repo}/issues/events/{event_id}"], - getLabel: ["GET /repos/{owner}/{repo}/labels/{name}"], - getMilestone: ["GET /repos/{owner}/{repo}/milestones/{milestone_number}"], - list: ["GET /issues"], - listAssignees: ["GET /repos/{owner}/{repo}/assignees"], - listComments: ["GET /repos/{owner}/{repo}/issues/{issue_number}/comments"], - listCommentsForRepo: ["GET /repos/{owner}/{repo}/issues/comments"], - listEvents: ["GET /repos/{owner}/{repo}/issues/{issue_number}/events"], - listEventsForRepo: ["GET /repos/{owner}/{repo}/issues/events"], - listEventsForTimeline: ["GET /repos/{owner}/{repo}/issues/{issue_number}/timeline", { - mediaType: { - previews: ["mockingbird"] - } - }], - listForAuthenticatedUser: ["GET /user/issues"], - listForOrg: ["GET /orgs/{org}/issues"], - listForRepo: ["GET /repos/{owner}/{repo}/issues"], - listLabelsForMilestone: ["GET /repos/{owner}/{repo}/milestones/{milestone_number}/labels"], - listLabelsForRepo: ["GET /repos/{owner}/{repo}/labels"], - listLabelsOnIssue: ["GET /repos/{owner}/{repo}/issues/{issue_number}/labels"], - listMilestones: ["GET /repos/{owner}/{repo}/milestones"], - lock: ["PUT /repos/{owner}/{repo}/issues/{issue_number}/lock"], - removeAllLabels: ["DELETE /repos/{owner}/{repo}/issues/{issue_number}/labels"], - removeAssignees: ["DELETE /repos/{owner}/{repo}/issues/{issue_number}/assignees"], - removeLabel: ["DELETE /repos/{owner}/{repo}/issues/{issue_number}/labels/{name}"], - setLabels: ["PUT /repos/{owner}/{repo}/issues/{issue_number}/labels"], - unlock: ["DELETE /repos/{owner}/{repo}/issues/{issue_number}/lock"], - update: ["PATCH /repos/{owner}/{repo}/issues/{issue_number}"], - updateComment: ["PATCH /repos/{owner}/{repo}/issues/comments/{comment_id}"], - updateLabel: ["PATCH /repos/{owner}/{repo}/labels/{name}"], - updateMilestone: ["PATCH /repos/{owner}/{repo}/milestones/{milestone_number}"] - }, - licenses: { - get: ["GET /licenses/{license}"], - getAllCommonlyUsed: ["GET /licenses"], - getForRepo: ["GET /repos/{owner}/{repo}/license"] - }, - markdown: { - render: ["POST /markdown"], - renderRaw: ["POST /markdown/raw", { - headers: { - "content-type": "text/plain; charset=utf-8" - } - }] - }, - meta: { - get: ["GET /meta"] - }, - migrations: { - cancelImport: ["DELETE /repos/{owner}/{repo}/import"], - deleteArchiveForAuthenticatedUser: ["DELETE /user/migrations/{migration_id}/archive", { - mediaType: { - previews: ["wyandotte"] - } - }], - deleteArchiveForOrg: ["DELETE /orgs/{org}/migrations/{migration_id}/archive", { - mediaType: { - previews: ["wyandotte"] - } - }], - downloadArchiveForOrg: ["GET /orgs/{org}/migrations/{migration_id}/archive", { - mediaType: { - previews: ["wyandotte"] - } - }], - getArchiveForAuthenticatedUser: ["GET /user/migrations/{migration_id}/archive", { - mediaType: { - previews: ["wyandotte"] - } - }], - getCommitAuthors: ["GET /repos/{owner}/{repo}/import/authors"], - getImportStatus: ["GET /repos/{owner}/{repo}/import"], - getLargeFiles: ["GET /repos/{owner}/{repo}/import/large_files"], - getStatusForAuthenticatedUser: ["GET /user/migrations/{migration_id}", { - mediaType: { - previews: ["wyandotte"] - } - }], - getStatusForOrg: ["GET /orgs/{org}/migrations/{migration_id}", { - mediaType: { - previews: ["wyandotte"] - } - }], - listForAuthenticatedUser: ["GET /user/migrations", { - mediaType: { - previews: ["wyandotte"] - } - }], - listForOrg: ["GET /orgs/{org}/migrations", { - mediaType: { - previews: ["wyandotte"] - } - }], - listReposForOrg: ["GET /orgs/{org}/migrations/{migration_id}/repositories", { - mediaType: { - previews: ["wyandotte"] - } - }], - listReposForUser: ["GET /user/migrations/{migration_id}/repositories", { - mediaType: { - previews: ["wyandotte"] - } - }], - mapCommitAuthor: ["PATCH /repos/{owner}/{repo}/import/authors/{author_id}"], - setLfsPreference: ["PATCH /repos/{owner}/{repo}/import/lfs"], - startForAuthenticatedUser: ["POST /user/migrations"], - startForOrg: ["POST /orgs/{org}/migrations"], - startImport: ["PUT /repos/{owner}/{repo}/import"], - unlockRepoForAuthenticatedUser: ["DELETE /user/migrations/{migration_id}/repos/{repo_name}/lock", { - mediaType: { - previews: ["wyandotte"] - } - }], - unlockRepoForOrg: ["DELETE /orgs/{org}/migrations/{migration_id}/repos/{repo_name}/lock", { - mediaType: { - previews: ["wyandotte"] - } - }], - updateImport: ["PATCH /repos/{owner}/{repo}/import"] - }, - orgs: { - blockUser: ["PUT /orgs/{org}/blocks/{username}"], - checkBlockedUser: ["GET /orgs/{org}/blocks/{username}"], - checkMembershipForUser: ["GET /orgs/{org}/members/{username}"], - checkPublicMembershipForUser: ["GET /orgs/{org}/public_members/{username}"], - convertMemberToOutsideCollaborator: ["PUT /orgs/{org}/outside_collaborators/{username}"], - createInvitation: ["POST /orgs/{org}/invitations"], - createWebhook: ["POST /orgs/{org}/hooks"], - deleteWebhook: ["DELETE /orgs/{org}/hooks/{hook_id}"], - get: ["GET /orgs/{org}"], - getMembershipForAuthenticatedUser: ["GET /user/memberships/orgs/{org}"], - getMembershipForUser: ["GET /orgs/{org}/memberships/{username}"], - getWebhook: ["GET /orgs/{org}/hooks/{hook_id}"], - list: ["GET /organizations"], - listAppInstallations: ["GET /orgs/{org}/installations"], - listBlockedUsers: ["GET /orgs/{org}/blocks"], - listForAuthenticatedUser: ["GET /user/orgs"], - listForUser: ["GET /users/{username}/orgs"], - listInvitationTeams: ["GET /orgs/{org}/invitations/{invitation_id}/teams"], - listMembers: ["GET /orgs/{org}/members"], - listMembershipsForAuthenticatedUser: ["GET /user/memberships/orgs"], - listOutsideCollaborators: ["GET /orgs/{org}/outside_collaborators"], - listPendingInvitations: ["GET /orgs/{org}/invitations"], - listPublicMembers: ["GET /orgs/{org}/public_members"], - listWebhooks: ["GET /orgs/{org}/hooks"], - pingWebhook: ["POST /orgs/{org}/hooks/{hook_id}/pings"], - removeMember: ["DELETE /orgs/{org}/members/{username}"], - removeMembershipForUser: ["DELETE /orgs/{org}/memberships/{username}"], - removeOutsideCollaborator: ["DELETE /orgs/{org}/outside_collaborators/{username}"], - removePublicMembershipForAuthenticatedUser: ["DELETE /orgs/{org}/public_members/{username}"], - setMembershipForUser: ["PUT /orgs/{org}/memberships/{username}"], - setPublicMembershipForAuthenticatedUser: ["PUT /orgs/{org}/public_members/{username}"], - unblockUser: ["DELETE /orgs/{org}/blocks/{username}"], - update: ["PATCH /orgs/{org}"], - updateMembershipForAuthenticatedUser: ["PATCH /user/memberships/orgs/{org}"], - updateWebhook: ["PATCH /orgs/{org}/hooks/{hook_id}"] - }, - projects: { - addCollaborator: ["PUT /projects/{project_id}/collaborators/{username}", { - mediaType: { - previews: ["inertia"] - } - }], - createCard: ["POST /projects/columns/{column_id}/cards", { - mediaType: { - previews: ["inertia"] - } - }], - createColumn: ["POST /projects/{project_id}/columns", { - mediaType: { - previews: ["inertia"] - } - }], - createForAuthenticatedUser: ["POST /user/projects", { - mediaType: { - previews: ["inertia"] - } - }], - createForOrg: ["POST /orgs/{org}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - createForRepo: ["POST /repos/{owner}/{repo}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - delete: ["DELETE /projects/{project_id}", { - mediaType: { - previews: ["inertia"] - } - }], - deleteCard: ["DELETE /projects/columns/cards/{card_id}", { - mediaType: { - previews: ["inertia"] - } - }], - deleteColumn: ["DELETE /projects/columns/{column_id}", { - mediaType: { - previews: ["inertia"] - } - }], - get: ["GET /projects/{project_id}", { - mediaType: { - previews: ["inertia"] - } - }], - getCard: ["GET /projects/columns/cards/{card_id}", { - mediaType: { - previews: ["inertia"] - } - }], - getColumn: ["GET /projects/columns/{column_id}", { - mediaType: { - previews: ["inertia"] - } - }], - getPermissionForUser: ["GET /projects/{project_id}/collaborators/{username}/permission", { - mediaType: { - previews: ["inertia"] - } - }], - listCards: ["GET /projects/columns/{column_id}/cards", { - mediaType: { - previews: ["inertia"] - } - }], - listCollaborators: ["GET /projects/{project_id}/collaborators", { - mediaType: { - previews: ["inertia"] - } - }], - listColumns: ["GET /projects/{project_id}/columns", { - mediaType: { - previews: ["inertia"] - } - }], - listForOrg: ["GET /orgs/{org}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - listForRepo: ["GET /repos/{owner}/{repo}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - listForUser: ["GET /users/{username}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - moveCard: ["POST /projects/columns/cards/{card_id}/moves", { - mediaType: { - previews: ["inertia"] - } - }], - moveColumn: ["POST /projects/columns/{column_id}/moves", { - mediaType: { - previews: ["inertia"] - } - }], - removeCollaborator: ["DELETE /projects/{project_id}/collaborators/{username}", { - mediaType: { - previews: ["inertia"] - } - }], - update: ["PATCH /projects/{project_id}", { - mediaType: { - previews: ["inertia"] - } - }], - updateCard: ["PATCH /projects/columns/cards/{card_id}", { - mediaType: { - previews: ["inertia"] - } - }], - updateColumn: ["PATCH /projects/columns/{column_id}", { - mediaType: { - previews: ["inertia"] - } - }] - }, - pulls: { - checkIfMerged: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/merge"], - create: ["POST /repos/{owner}/{repo}/pulls"], - createReplyForReviewComment: ["POST /repos/{owner}/{repo}/pulls/{pull_number}/comments/{comment_id}/replies"], - createReview: ["POST /repos/{owner}/{repo}/pulls/{pull_number}/reviews"], - createReviewComment: ["POST /repos/{owner}/{repo}/pulls/{pull_number}/comments"], - deletePendingReview: ["DELETE /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}"], - deleteReviewComment: ["DELETE /repos/{owner}/{repo}/pulls/comments/{comment_id}"], - dismissReview: ["PUT /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}/dismissals"], - get: ["GET /repos/{owner}/{repo}/pulls/{pull_number}"], - getReview: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}"], - getReviewComment: ["GET /repos/{owner}/{repo}/pulls/comments/{comment_id}"], - list: ["GET /repos/{owner}/{repo}/pulls"], - listCommentsForReview: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}/comments"], - listCommits: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/commits"], - listFiles: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/files"], - listRequestedReviewers: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/requested_reviewers"], - listReviewComments: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/comments"], - listReviewCommentsForRepo: ["GET /repos/{owner}/{repo}/pulls/comments"], - listReviews: ["GET /repos/{owner}/{repo}/pulls/{pull_number}/reviews"], - merge: ["PUT /repos/{owner}/{repo}/pulls/{pull_number}/merge"], - removeRequestedReviewers: ["DELETE /repos/{owner}/{repo}/pulls/{pull_number}/requested_reviewers"], - requestReviewers: ["POST /repos/{owner}/{repo}/pulls/{pull_number}/requested_reviewers"], - submitReview: ["POST /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}/events"], - update: ["PATCH /repos/{owner}/{repo}/pulls/{pull_number}"], - updateBranch: ["PUT /repos/{owner}/{repo}/pulls/{pull_number}/update-branch", { - mediaType: { - previews: ["lydian"] - } - }], - updateReview: ["PUT /repos/{owner}/{repo}/pulls/{pull_number}/reviews/{review_id}"], - updateReviewComment: ["PATCH /repos/{owner}/{repo}/pulls/comments/{comment_id}"] - }, - rateLimit: { - get: ["GET /rate_limit"] - }, - reactions: { - createForCommitComment: ["POST /repos/{owner}/{repo}/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - createForIssue: ["POST /repos/{owner}/{repo}/issues/{issue_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - createForIssueComment: ["POST /repos/{owner}/{repo}/issues/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - createForPullRequestReviewComment: ["POST /repos/{owner}/{repo}/pulls/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - createForTeamDiscussionCommentInOrg: ["POST /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - createForTeamDiscussionInOrg: ["POST /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForCommitComment: ["DELETE /repos/{owner}/{repo}/comments/{comment_id}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForIssue: ["DELETE /repos/{owner}/{repo}/issues/{issue_number}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForIssueComment: ["DELETE /repos/{owner}/{repo}/issues/comments/{comment_id}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForPullRequestComment: ["DELETE /repos/{owner}/{repo}/pulls/comments/{comment_id}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForTeamDiscussion: ["DELETE /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteForTeamDiscussionComment: ["DELETE /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}/reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - deleteLegacy: ["DELETE /reactions/{reaction_id}", { - mediaType: { - previews: ["squirrel-girl"] - } - }, { - deprecated: "octokit.reactions.deleteLegacy() is deprecated, see https://developer.github.com/v3/reactions/#delete-a-reaction-legacy" - }], - listForCommitComment: ["GET /repos/{owner}/{repo}/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - listForIssue: ["GET /repos/{owner}/{repo}/issues/{issue_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - listForIssueComment: ["GET /repos/{owner}/{repo}/issues/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - listForPullRequestReviewComment: ["GET /repos/{owner}/{repo}/pulls/comments/{comment_id}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - listForTeamDiscussionCommentInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }], - listForTeamDiscussionInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/reactions", { - mediaType: { - previews: ["squirrel-girl"] - } - }] - }, - repos: { - acceptInvitation: ["PATCH /user/repository_invitations/{invitation_id}"], - addAppAccessRestrictions: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/apps", {}, { - mapToData: "apps" - }], - addCollaborator: ["PUT /repos/{owner}/{repo}/collaborators/{username}"], - addStatusCheckContexts: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks/contexts", {}, { - mapToData: "contexts" - }], - addTeamAccessRestrictions: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/teams", {}, { - mapToData: "teams" - }], - addUserAccessRestrictions: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/users", {}, { - mapToData: "users" - }], - checkCollaborator: ["GET /repos/{owner}/{repo}/collaborators/{username}"], - checkVulnerabilityAlerts: ["GET /repos/{owner}/{repo}/vulnerability-alerts", { - mediaType: { - previews: ["dorian"] - } - }], - compareCommits: ["GET /repos/{owner}/{repo}/compare/{base}...{head}"], - createCommitComment: ["POST /repos/{owner}/{repo}/commits/{commit_sha}/comments"], - createCommitSignatureProtection: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/required_signatures", { - mediaType: { - previews: ["zzzax"] - } - }], - createCommitStatus: ["POST /repos/{owner}/{repo}/statuses/{sha}"], - createDeployKey: ["POST /repos/{owner}/{repo}/keys"], - createDeployment: ["POST /repos/{owner}/{repo}/deployments"], - createDeploymentStatus: ["POST /repos/{owner}/{repo}/deployments/{deployment_id}/statuses"], - createDispatchEvent: ["POST /repos/{owner}/{repo}/dispatches"], - createForAuthenticatedUser: ["POST /user/repos"], - createFork: ["POST /repos/{owner}/{repo}/forks"], - createInOrg: ["POST /orgs/{org}/repos"], - createOrUpdateFileContents: ["PUT /repos/{owner}/{repo}/contents/{path}"], - createPagesSite: ["POST /repos/{owner}/{repo}/pages", { - mediaType: { - previews: ["switcheroo"] - } - }], - createRelease: ["POST /repos/{owner}/{repo}/releases"], - createUsingTemplate: ["POST /repos/{template_owner}/{template_repo}/generate", { - mediaType: { - previews: ["baptiste"] - } - }], - createWebhook: ["POST /repos/{owner}/{repo}/hooks"], - declineInvitation: ["DELETE /user/repository_invitations/{invitation_id}"], - delete: ["DELETE /repos/{owner}/{repo}"], - deleteAccessRestrictions: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/restrictions"], - deleteAdminBranchProtection: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/enforce_admins"], - deleteBranchProtection: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection"], - deleteCommitComment: ["DELETE /repos/{owner}/{repo}/comments/{comment_id}"], - deleteCommitSignatureProtection: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/required_signatures", { - mediaType: { - previews: ["zzzax"] - } - }], - deleteDeployKey: ["DELETE /repos/{owner}/{repo}/keys/{key_id}"], - deleteDeployment: ["DELETE /repos/{owner}/{repo}/deployments/{deployment_id}"], - deleteFile: ["DELETE /repos/{owner}/{repo}/contents/{path}"], - deleteInvitation: ["DELETE /repos/{owner}/{repo}/invitations/{invitation_id}"], - deletePagesSite: ["DELETE /repos/{owner}/{repo}/pages", { - mediaType: { - previews: ["switcheroo"] - } - }], - deletePullRequestReviewProtection: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/required_pull_request_reviews"], - deleteRelease: ["DELETE /repos/{owner}/{repo}/releases/{release_id}"], - deleteReleaseAsset: ["DELETE /repos/{owner}/{repo}/releases/assets/{asset_id}"], - deleteWebhook: ["DELETE /repos/{owner}/{repo}/hooks/{hook_id}"], - disableAutomatedSecurityFixes: ["DELETE /repos/{owner}/{repo}/automated-security-fixes", { - mediaType: { - previews: ["london"] - } - }], - disableVulnerabilityAlerts: ["DELETE /repos/{owner}/{repo}/vulnerability-alerts", { - mediaType: { - previews: ["dorian"] - } - }], - downloadArchive: ["GET /repos/{owner}/{repo}/{archive_format}/{ref}"], - enableAutomatedSecurityFixes: ["PUT /repos/{owner}/{repo}/automated-security-fixes", { - mediaType: { - previews: ["london"] - } - }], - enableVulnerabilityAlerts: ["PUT /repos/{owner}/{repo}/vulnerability-alerts", { - mediaType: { - previews: ["dorian"] - } - }], - get: ["GET /repos/{owner}/{repo}"], - getAccessRestrictions: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/restrictions"], - getAdminBranchProtection: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/enforce_admins"], - getAllStatusCheckContexts: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks/contexts"], - getAllTopics: ["GET /repos/{owner}/{repo}/topics", { - mediaType: { - previews: ["mercy"] - } - }], - getAppsWithAccessToProtectedBranch: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/apps"], - getBranch: ["GET /repos/{owner}/{repo}/branches/{branch}"], - getBranchProtection: ["GET /repos/{owner}/{repo}/branches/{branch}/protection"], - getClones: ["GET /repos/{owner}/{repo}/traffic/clones"], - getCodeFrequencyStats: ["GET /repos/{owner}/{repo}/stats/code_frequency"], - getCollaboratorPermissionLevel: ["GET /repos/{owner}/{repo}/collaborators/{username}/permission"], - getCombinedStatusForRef: ["GET /repos/{owner}/{repo}/commits/{ref}/status"], - getCommit: ["GET /repos/{owner}/{repo}/commits/{ref}"], - getCommitActivityStats: ["GET /repos/{owner}/{repo}/stats/commit_activity"], - getCommitComment: ["GET /repos/{owner}/{repo}/comments/{comment_id}"], - getCommitSignatureProtection: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/required_signatures", { - mediaType: { - previews: ["zzzax"] - } - }], - getCommunityProfileMetrics: ["GET /repos/{owner}/{repo}/community/profile", { - mediaType: { - previews: ["black-panther"] - } - }], - getContent: ["GET /repos/{owner}/{repo}/contents/{path}"], - getContributorsStats: ["GET /repos/{owner}/{repo}/stats/contributors"], - getDeployKey: ["GET /repos/{owner}/{repo}/keys/{key_id}"], - getDeployment: ["GET /repos/{owner}/{repo}/deployments/{deployment_id}"], - getDeploymentStatus: ["GET /repos/{owner}/{repo}/deployments/{deployment_id}/statuses/{status_id}"], - getLatestPagesBuild: ["GET /repos/{owner}/{repo}/pages/builds/latest"], - getLatestRelease: ["GET /repos/{owner}/{repo}/releases/latest"], - getPages: ["GET /repos/{owner}/{repo}/pages"], - getPagesBuild: ["GET /repos/{owner}/{repo}/pages/builds/{build_id}"], - getParticipationStats: ["GET /repos/{owner}/{repo}/stats/participation"], - getPullRequestReviewProtection: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/required_pull_request_reviews"], - getPunchCardStats: ["GET /repos/{owner}/{repo}/stats/punch_card"], - getReadme: ["GET /repos/{owner}/{repo}/readme"], - getRelease: ["GET /repos/{owner}/{repo}/releases/{release_id}"], - getReleaseAsset: ["GET /repos/{owner}/{repo}/releases/assets/{asset_id}"], - getReleaseByTag: ["GET /repos/{owner}/{repo}/releases/tags/{tag}"], - getStatusChecksProtection: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks"], - getTeamsWithAccessToProtectedBranch: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/teams"], - getTopPaths: ["GET /repos/{owner}/{repo}/traffic/popular/paths"], - getTopReferrers: ["GET /repos/{owner}/{repo}/traffic/popular/referrers"], - getUsersWithAccessToProtectedBranch: ["GET /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/users"], - getViews: ["GET /repos/{owner}/{repo}/traffic/views"], - getWebhook: ["GET /repos/{owner}/{repo}/hooks/{hook_id}"], - listBranches: ["GET /repos/{owner}/{repo}/branches"], - listBranchesForHeadCommit: ["GET /repos/{owner}/{repo}/commits/{commit_sha}/branches-where-head", { - mediaType: { - previews: ["groot"] - } - }], - listCollaborators: ["GET /repos/{owner}/{repo}/collaborators"], - listCommentsForCommit: ["GET /repos/{owner}/{repo}/commits/{commit_sha}/comments"], - listCommitCommentsForRepo: ["GET /repos/{owner}/{repo}/comments"], - listCommitStatusesForRef: ["GET /repos/{owner}/{repo}/commits/{ref}/statuses"], - listCommits: ["GET /repos/{owner}/{repo}/commits"], - listContributors: ["GET /repos/{owner}/{repo}/contributors"], - listDeployKeys: ["GET /repos/{owner}/{repo}/keys"], - listDeploymentStatuses: ["GET /repos/{owner}/{repo}/deployments/{deployment_id}/statuses"], - listDeployments: ["GET /repos/{owner}/{repo}/deployments"], - listForAuthenticatedUser: ["GET /user/repos"], - listForOrg: ["GET /orgs/{org}/repos"], - listForUser: ["GET /users/{username}/repos"], - listForks: ["GET /repos/{owner}/{repo}/forks"], - listInvitations: ["GET /repos/{owner}/{repo}/invitations"], - listInvitationsForAuthenticatedUser: ["GET /user/repository_invitations"], - listLanguages: ["GET /repos/{owner}/{repo}/languages"], - listPagesBuilds: ["GET /repos/{owner}/{repo}/pages/builds"], - listPublic: ["GET /repositories"], - listPullRequestsAssociatedWithCommit: ["GET /repos/{owner}/{repo}/commits/{commit_sha}/pulls", { - mediaType: { - previews: ["groot"] - } - }], - listReleaseAssets: ["GET /repos/{owner}/{repo}/releases/{release_id}/assets"], - listReleases: ["GET /repos/{owner}/{repo}/releases"], - listTags: ["GET /repos/{owner}/{repo}/tags"], - listTeams: ["GET /repos/{owner}/{repo}/teams"], - listWebhooks: ["GET /repos/{owner}/{repo}/hooks"], - merge: ["POST /repos/{owner}/{repo}/merges"], - pingWebhook: ["POST /repos/{owner}/{repo}/hooks/{hook_id}/pings"], - removeAppAccessRestrictions: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/apps", {}, { - mapToData: "apps" - }], - removeCollaborator: ["DELETE /repos/{owner}/{repo}/collaborators/{username}"], - removeStatusCheckContexts: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks/contexts", {}, { - mapToData: "contexts" - }], - removeStatusCheckProtection: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks"], - removeTeamAccessRestrictions: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/teams", {}, { - mapToData: "teams" - }], - removeUserAccessRestrictions: ["DELETE /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/users", {}, { - mapToData: "users" - }], - replaceAllTopics: ["PUT /repos/{owner}/{repo}/topics", { - mediaType: { - previews: ["mercy"] - } - }], - requestPagesBuild: ["POST /repos/{owner}/{repo}/pages/builds"], - setAdminBranchProtection: ["POST /repos/{owner}/{repo}/branches/{branch}/protection/enforce_admins"], - setAppAccessRestrictions: ["PUT /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/apps", {}, { - mapToData: "apps" - }], - setStatusCheckContexts: ["PUT /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks/contexts", {}, { - mapToData: "contexts" - }], - setTeamAccessRestrictions: ["PUT /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/teams", {}, { - mapToData: "teams" - }], - setUserAccessRestrictions: ["PUT /repos/{owner}/{repo}/branches/{branch}/protection/restrictions/users", {}, { - mapToData: "users" - }], - testPushWebhook: ["POST /repos/{owner}/{repo}/hooks/{hook_id}/tests"], - transfer: ["POST /repos/{owner}/{repo}/transfer"], - update: ["PATCH /repos/{owner}/{repo}"], - updateBranchProtection: ["PUT /repos/{owner}/{repo}/branches/{branch}/protection"], - updateCommitComment: ["PATCH /repos/{owner}/{repo}/comments/{comment_id}"], - updateInformationAboutPagesSite: ["PUT /repos/{owner}/{repo}/pages"], - updateInvitation: ["PATCH /repos/{owner}/{repo}/invitations/{invitation_id}"], - updatePullRequestReviewProtection: ["PATCH /repos/{owner}/{repo}/branches/{branch}/protection/required_pull_request_reviews"], - updateRelease: ["PATCH /repos/{owner}/{repo}/releases/{release_id}"], - updateReleaseAsset: ["PATCH /repos/{owner}/{repo}/releases/assets/{asset_id}"], - updateStatusCheckPotection: ["PATCH /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks"], - updateWebhook: ["PATCH /repos/{owner}/{repo}/hooks/{hook_id}"], - uploadReleaseAsset: ["POST /repos/{owner}/{repo}/releases/{release_id}/assets{?name,label}", { - baseUrl: "https://uploads.github.com" - }] - }, - search: { - code: ["GET /search/code"], - commits: ["GET /search/commits", { - mediaType: { - previews: ["cloak"] - } - }], - issuesAndPullRequests: ["GET /search/issues"], - labels: ["GET /search/labels"], - repos: ["GET /search/repositories"], - topics: ["GET /search/topics", { - mediaType: { - previews: ["mercy"] - } - }], - users: ["GET /search/users"] - }, - teams: { - addOrUpdateMembershipForUserInOrg: ["PUT /orgs/{org}/teams/{team_slug}/memberships/{username}"], - addOrUpdateProjectPermissionsInOrg: ["PUT /orgs/{org}/teams/{team_slug}/projects/{project_id}", { - mediaType: { - previews: ["inertia"] - } - }], - addOrUpdateRepoPermissionsInOrg: ["PUT /orgs/{org}/teams/{team_slug}/repos/{owner}/{repo}"], - checkPermissionsForProjectInOrg: ["GET /orgs/{org}/teams/{team_slug}/projects/{project_id}", { - mediaType: { - previews: ["inertia"] - } - }], - checkPermissionsForRepoInOrg: ["GET /orgs/{org}/teams/{team_slug}/repos/{owner}/{repo}"], - create: ["POST /orgs/{org}/teams"], - createDiscussionCommentInOrg: ["POST /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments"], - createDiscussionInOrg: ["POST /orgs/{org}/teams/{team_slug}/discussions"], - deleteDiscussionCommentInOrg: ["DELETE /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}"], - deleteDiscussionInOrg: ["DELETE /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}"], - deleteInOrg: ["DELETE /orgs/{org}/teams/{team_slug}"], - getByName: ["GET /orgs/{org}/teams/{team_slug}"], - getDiscussionCommentInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}"], - getDiscussionInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}"], - getMembershipForUserInOrg: ["GET /orgs/{org}/teams/{team_slug}/memberships/{username}"], - list: ["GET /orgs/{org}/teams"], - listChildInOrg: ["GET /orgs/{org}/teams/{team_slug}/teams"], - listDiscussionCommentsInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments"], - listDiscussionsInOrg: ["GET /orgs/{org}/teams/{team_slug}/discussions"], - listForAuthenticatedUser: ["GET /user/teams"], - listMembersInOrg: ["GET /orgs/{org}/teams/{team_slug}/members"], - listPendingInvitationsInOrg: ["GET /orgs/{org}/teams/{team_slug}/invitations"], - listProjectsInOrg: ["GET /orgs/{org}/teams/{team_slug}/projects", { - mediaType: { - previews: ["inertia"] - } - }], - listReposInOrg: ["GET /orgs/{org}/teams/{team_slug}/repos"], - removeMembershipForUserInOrg: ["DELETE /orgs/{org}/teams/{team_slug}/memberships/{username}"], - removeProjectInOrg: ["DELETE /orgs/{org}/teams/{team_slug}/projects/{project_id}"], - removeRepoInOrg: ["DELETE /orgs/{org}/teams/{team_slug}/repos/{owner}/{repo}"], - updateDiscussionCommentInOrg: ["PATCH /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}/comments/{comment_number}"], - updateDiscussionInOrg: ["PATCH /orgs/{org}/teams/{team_slug}/discussions/{discussion_number}"], - updateInOrg: ["PATCH /orgs/{org}/teams/{team_slug}"] - }, - users: { - addEmailForAuthenticated: ["POST /user/emails"], - block: ["PUT /user/blocks/{username}"], - checkBlocked: ["GET /user/blocks/{username}"], - checkFollowingForUser: ["GET /users/{username}/following/{target_user}"], - checkPersonIsFollowedByAuthenticated: ["GET /user/following/{username}"], - createGpgKeyForAuthenticated: ["POST /user/gpg_keys"], - createPublicSshKeyForAuthenticated: ["POST /user/keys"], - deleteEmailForAuthenticated: ["DELETE /user/emails"], - deleteGpgKeyForAuthenticated: ["DELETE /user/gpg_keys/{gpg_key_id}"], - deletePublicSshKeyForAuthenticated: ["DELETE /user/keys/{key_id}"], - follow: ["PUT /user/following/{username}"], - getAuthenticated: ["GET /user"], - getByUsername: ["GET /users/{username}"], - getContextForUser: ["GET /users/{username}/hovercard"], - getGpgKeyForAuthenticated: ["GET /user/gpg_keys/{gpg_key_id}"], - getPublicSshKeyForAuthenticated: ["GET /user/keys/{key_id}"], - list: ["GET /users"], - listBlockedByAuthenticated: ["GET /user/blocks"], - listEmailsForAuthenticated: ["GET /user/emails"], - listFollowedByAuthenticated: ["GET /user/following"], - listFollowersForAuthenticatedUser: ["GET /user/followers"], - listFollowersForUser: ["GET /users/{username}/followers"], - listFollowingForUser: ["GET /users/{username}/following"], - listGpgKeysForAuthenticated: ["GET /user/gpg_keys"], - listGpgKeysForUser: ["GET /users/{username}/gpg_keys"], - listPublicEmailsForAuthenticated: ["GET /user/public_emails"], - listPublicKeysForUser: ["GET /users/{username}/keys"], - listPublicSshKeysForAuthenticated: ["GET /user/keys"], - setPrimaryEmailVisibilityForAuthenticated: ["PATCH /user/email/visibility"], - unblock: ["DELETE /user/blocks/{username}"], - unfollow: ["DELETE /user/following/{username}"], - updateAuthenticated: ["PATCH /user"] - } -}; - -const VERSION = "4.2.0"; - -function endpointsToMethods(octokit, endpointsMap) { - const newMethods = {}; - - for (const [scope, endpoints] of Object.entries(endpointsMap)) { - for (const [methodName, endpoint] of Object.entries(endpoints)) { - const [route, defaults, decorations] = endpoint; - const [method, url] = route.split(/ /); - const endpointDefaults = Object.assign({ - method, - url - }, defaults); - - if (!newMethods[scope]) { - newMethods[scope] = {}; - } - - const scopeMethods = newMethods[scope]; - - if (decorations) { - scopeMethods[methodName] = decorate(octokit, scope, methodName, endpointDefaults, decorations); - continue; - } - - scopeMethods[methodName] = octokit.request.defaults(endpointDefaults); - } - } - - return newMethods; -} - -function decorate(octokit, scope, methodName, defaults, decorations) { - const requestWithDefaults = octokit.request.defaults(defaults); - /* istanbul ignore next */ - - function withDecorations(...args) { - // @ts-ignore https://github.com/microsoft/TypeScript/issues/25488 - let options = requestWithDefaults.endpoint.merge(...args); // There are currently no other decorations than `.mapToData` - - if (decorations.mapToData) { - options = Object.assign({}, options, { - data: options[decorations.mapToData], - [decorations.mapToData]: undefined - }); - return requestWithDefaults(options); - } - - if (decorations.renamed) { - const [newScope, newMethodName] = decorations.renamed; - octokit.log.warn(`octokit.${scope}.${methodName}() has been renamed to octokit.${newScope}.${newMethodName}()`); - } - - if (decorations.deprecated) { - octokit.log.warn(decorations.deprecated); - } - - if (decorations.renamedParameters) { - // @ts-ignore https://github.com/microsoft/TypeScript/issues/25488 - const options = requestWithDefaults.endpoint.merge(...args); - - for (const [name, alias] of Object.entries(decorations.renamedParameters)) { - if (name in options) { - octokit.log.warn(`"${name}" parameter is deprecated for "octokit.${scope}.${methodName}()". Use "${alias}" instead`); - - if (!(alias in options)) { - options[alias] = options[name]; - } - - delete options[name]; - } - } - - return requestWithDefaults(options); - } // @ts-ignore https://github.com/microsoft/TypeScript/issues/25488 - - - return requestWithDefaults(...args); - } - - return Object.assign(withDecorations, requestWithDefaults); -} - -/** - * This plugin is a 1:1 copy of internal @octokit/rest plugins. The primary - * goal is to rebuild @octokit/rest on top of @octokit/core. Once that is - * done, we will remove the registerEndpoints methods and return the methods - * directly as with the other plugins. At that point we will also remove the - * legacy workarounds and deprecations. - * - * See the plan at - * https://github.com/octokit/plugin-rest-endpoint-methods.js/pull/1 - */ - -function restEndpointMethods(octokit) { - return endpointsToMethods(octokit, Endpoints); -} -restEndpointMethods.VERSION = VERSION; - -exports.restEndpointMethods = restEndpointMethods; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 48364: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } - -var deprecation = __webpack_require__(86649); -var once = _interopDefault(__webpack_require__(86343)); - -const logOnce = once(deprecation => console.warn(deprecation)); -/** - * Error with extra properties to help with debugging - */ - -class RequestError extends Error { - constructor(message, statusCode, options) { - super(message); // Maintains proper stack trace (only available on V8) - - /* istanbul ignore next */ - - if (Error.captureStackTrace) { - Error.captureStackTrace(this, this.constructor); - } - - this.name = "HttpError"; - this.status = statusCode; - Object.defineProperty(this, "code", { - get() { - logOnce(new deprecation.Deprecation("[@octokit/request-error] `error.code` is deprecated, use `error.status`.")); - return statusCode; - } - - }); - this.headers = options.headers || {}; // redact request credentials without mutating original request options - - const requestCopy = Object.assign({}, options.request); - - if (options.request.headers.authorization) { - requestCopy.headers = Object.assign({}, options.request.headers, { - authorization: options.request.headers.authorization.replace(/ .*$/, " [REDACTED]") - }); - } - - requestCopy.url = requestCopy.url // client_id & client_secret can be passed as URL query parameters to increase rate limit - // see https://developer.github.com/v3/#increasing-the-unauthenticated-rate-limit-for-oauth-applications - .replace(/\bclient_secret=\w+/g, "client_secret=[REDACTED]") // OAuth tokens can be passed as URL query parameters, although it is not recommended - // see https://developer.github.com/v3/#oauth2-token-sent-in-a-header - .replace(/\baccess_token=\w+/g, "access_token=[REDACTED]"); - this.request = requestCopy; - } - -} - -exports.RequestError = RequestError; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 48826: -/***/ ((__unused_webpack_module, exports, __webpack_require__) => { - -"use strict"; - - -Object.defineProperty(exports, "__esModule", ({ value: true })); - -function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } - -var endpoint = __webpack_require__(70412); -var universalUserAgent = __webpack_require__(1857); -var isPlainObject = __webpack_require__(80641); -var nodeFetch = _interopDefault(__webpack_require__(22434)); -var requestError = __webpack_require__(48364); - -const VERSION = "5.4.9"; - -function getBufferResponse(response) { - return response.arrayBuffer(); -} - -function fetchWrapper(requestOptions) { - if (isPlainObject.isPlainObject(requestOptions.body) || Array.isArray(requestOptions.body)) { - requestOptions.body = JSON.stringify(requestOptions.body); - } - - let headers = {}; - let status; - let url; - const fetch = requestOptions.request && requestOptions.request.fetch || nodeFetch; - return fetch(requestOptions.url, Object.assign({ - method: requestOptions.method, - body: requestOptions.body, - headers: requestOptions.headers, - redirect: requestOptions.redirect - }, requestOptions.request)).then(response => { - url = response.url; - status = response.status; - - for (const keyAndValue of response.headers) { - headers[keyAndValue[0]] = keyAndValue[1]; - } - - if (status === 204 || status === 205) { - return; - } // GitHub API returns 200 for HEAD requests - - - if (requestOptions.method === "HEAD") { - if (status < 400) { - return; - } - - throw new requestError.RequestError(response.statusText, status, { - headers, - request: requestOptions - }); - } - - if (status === 304) { - throw new requestError.RequestError("Not modified", status, { - headers, - request: requestOptions - }); - } - - if (status >= 400) { - return response.text().then(message => { - const error = new requestError.RequestError(message, status, { - headers, - request: requestOptions - }); - - try { - let responseBody = JSON.parse(error.message); - Object.assign(error, responseBody); - let errors = responseBody.errors; // Assumption `errors` would always be in Array format - - error.message = error.message + ": " + errors.map(JSON.stringify).join(", "); - } catch (e) {// ignore, see octokit/rest.js#684 - } - - throw error; - }); - } - - const contentType = response.headers.get("content-type"); - - if (/application\/json/.test(contentType)) { - return response.json(); - } - - if (!contentType || /^text\/|charset=utf-8$/.test(contentType)) { - return response.text(); - } - - return getBufferResponse(response); - }).then(data => { - return { - status, - url, - headers, - data - }; - }).catch(error => { - if (error instanceof requestError.RequestError) { - throw error; - } - - throw new requestError.RequestError(error.message, 500, { - headers, - request: requestOptions - }); - }); -} - -function withDefaults(oldEndpoint, newDefaults) { - const endpoint = oldEndpoint.defaults(newDefaults); - - const newApi = function (route, parameters) { - const endpointOptions = endpoint.merge(route, parameters); - - if (!endpointOptions.request || !endpointOptions.request.hook) { - return fetchWrapper(endpoint.parse(endpointOptions)); - } - - const request = (route, parameters) => { - return fetchWrapper(endpoint.parse(endpoint.merge(route, parameters))); - }; - - Object.assign(request, { - endpoint, - defaults: withDefaults.bind(null, endpoint) - }); - return endpointOptions.request.hook(request, endpointOptions); - }; - - return Object.assign(newApi, { - endpoint, - defaults: withDefaults.bind(null, endpoint) - }); -} - -const request = withDefaults(endpoint.endpoint, { - headers: { - "user-agent": `octokit-request.js/${VERSION} ${universalUserAgent.getUserAgent()}` - } -}); - -exports.request = request; -//# sourceMappingURL=index.js.map - - -/***/ }), - -/***/ 67208: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; - -var __importDefault = (this && this.__importDefault) || function (mod) { - return (mod && mod.__esModule) ? mod : { "default": mod }; -}; -const events_1 = __webpack_require__(28614); -const promisify_1 = __importDefault(__webpack_require__(2929)); -function isAgentBase(v) { - return Boolean(v) && typeof v.addRequest === 'function'; -} -function isHttpAgent(v) { - return Boolean(v) && typeof v.addRequest === 'function'; -} -function isSecureEndpoint() { - const { stack } = new Error(); - if (typeof stack !== 'string') - return false; - return stack.split('\n').some(l => l.indexOf('(https.js:') !== -1); -} -function createAgent(callback, opts) { - return new createAgent.Agent(callback, opts); -} -(function (createAgent) { - /** - * Base `http.Agent` implementation. - * No pooling/keep-alive is implemented by default. - * - * @param {Function} callback - * @api public - */ - class Agent extends events_1.EventEmitter { - constructor(callback, _opts) { - super(); - // The callback gets promisified lazily - this.promisifiedCallback = undefined; - let opts = _opts; - if (typeof callback === 'function') { - this.callback = callback; - } - else if (callback) { - opts = callback; - } - // timeout for the socket to be returned from the callback - this.timeout = null; - if (opts && typeof opts.timeout === 'number') { - this.timeout = opts.timeout; - } - this.options = opts || {}; - this.maxFreeSockets = 1; - this.maxSockets = 1; - this.sockets = []; - this.requests = []; - } - get defaultPort() { - if (typeof this.explicitDefaultPort === 'number') { - return this.explicitDefaultPort; - } - else { - return isSecureEndpoint() ? 443 : 80; - } - } - set defaultPort(v) { - this.explicitDefaultPort = v; - } - get protocol() { - if (typeof this.explicitProtocol === 'string') { - return this.explicitProtocol; - } - else { - return isSecureEndpoint() ? 'https:' : 'http:'; - } - } - set protocol(v) { - this.explicitProtocol = v; - } - callback(req, opts, fn) { - throw new Error('"agent-base" has no default implementation, you must subclass and override `callback()`'); - } - /** - * Called by node-core's "_http_client.js" module when creating - * a new HTTP request with this Agent instance. - * - * @api public - */ - addRequest(req, _opts) { - const ownOpts = Object.assign({}, _opts); - if (typeof ownOpts.secureEndpoint !== 'boolean') { - ownOpts.secureEndpoint = isSecureEndpoint(); - } - // Set default `host` for HTTP to localhost - if (ownOpts.host == null) { - ownOpts.host = 'localhost'; - } - // Set default `port` for HTTP if none was explicitly specified - if (ownOpts.port == null) { - ownOpts.port = ownOpts.secureEndpoint ? 443 : 80; - } - const opts = Object.assign(Object.assign({}, this.options), ownOpts); - if (opts.host && opts.path) { - // If both a `host` and `path` are specified then it's most likely the - // result of a `url.parse()` call... we need to remove the `path` portion so - // that `net.connect()` doesn't attempt to open that as a unix socket file. - delete opts.path; - } - delete opts.agent; - delete opts.hostname; - delete opts._defaultAgent; - delete opts.defaultPort; - delete opts.createConnection; - // Hint to use "Connection: close" - // XXX: non-documented `http` module API :( - req._last = true; - req.shouldKeepAlive = false; - // Create the `stream.Duplex` instance - let timedOut = false; - let timeout = null; - const timeoutMs = this.timeout; - const freeSocket = this.freeSocket; - function onerror(err) { - if (req._hadError) - return; - req.emit('error', err); - // For Safety. Some additional errors might fire later on - // and we need to make sure we don't double-fire the error event. - req._hadError = true; - } - function ontimeout() { - timeout = null; - timedOut = true; - const err = new Error(`A "socket" was not created for HTTP request before ${timeoutMs}ms`); - err.code = 'ETIMEOUT'; - onerror(err); - } - function callbackError(err) { - if (timedOut) - return; - if (timeout !== null) { - clearTimeout(timeout); - timeout = null; - } - onerror(err); - } - function onsocket(socket) { - let sock; - function onfree() { - freeSocket(sock, opts); - } - if (timedOut) - return; - if (timeout != null) { - clearTimeout(timeout); - timeout = null; - } - if (isAgentBase(socket) || isHttpAgent(socket)) { - // `socket` is actually an `http.Agent` instance, so - // relinquish responsibility for this `req` to the Agent - // from here on - socket.addRequest(req, opts); - return; - } - if (socket) { - sock = socket; - sock.on('free', onfree); - req.onSocket(sock); - return; - } - const err = new Error(`no Duplex stream was returned to agent-base for \`${req.method} ${req.path}\``); - onerror(err); - } - if (typeof this.callback !== 'function') { - onerror(new Error('`callback` is not defined')); - return; - } - if (!this.promisifiedCallback) { - if (this.callback.length >= 3) { - // Legacy callback function - convert to a Promise - this.promisifiedCallback = promisify_1.default(this.callback); - } - else { - this.promisifiedCallback = this.callback; - } - } - if (typeof timeoutMs === 'number' && timeoutMs > 0) { - timeout = setTimeout(ontimeout, timeoutMs); - } - if ('port' in opts && typeof opts.port !== 'number') { - opts.port = Number(opts.port); - } - try { - Promise.resolve(this.promisifiedCallback(req, opts)).then(onsocket, callbackError); - } - catch (err) { - Promise.reject(err).catch(callbackError); - } - } - freeSocket(socket, opts) { - // TODO reuse sockets - socket.destroy(); - } - destroy() { } - } - createAgent.Agent = Agent; -})(createAgent || (createAgent = {})); -// So that `instanceof` works correctly -createAgent.prototype = createAgent.Agent.prototype; -module.exports = createAgent; -//# sourceMappingURL=index.js.map - -/***/ }), - -/***/ 2929: -/***/ ((__unused_webpack_module, exports) => { - -"use strict"; - -Object.defineProperty(exports, "__esModule", ({ value: true })); -function promisify(fn) { - return function (req, opts) { - return new Promise((resolve, reject) => { - fn.call(this, req, opts, (err, rtn) => { - if (err) { - reject(err); - } - else { - resolve(rtn); - } - }); - }); - }; -} -exports.default = promisify; -//# sourceMappingURL=promisify.js.map - -/***/ }), - -/***/ 2390: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -module.exports = __webpack_require__(64579); - -/***/ }), - -/***/ 38007: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var settle = __webpack_require__(29801); -var buildFullPath = __webpack_require__(92074); -var buildURL = __webpack_require__(87481); -var http = __webpack_require__(98605); -var https = __webpack_require__(57211); -var httpFollow = __webpack_require__(75955).http; -var httpsFollow = __webpack_require__(75955).https; -var url = __webpack_require__(78835); -var zlib = __webpack_require__(78761); -var pkg = __webpack_require__(35131); -var createError = __webpack_require__(3034); -var enhanceError = __webpack_require__(95261); - -var isHttps = /https:?/; - -/*eslint consistent-return:0*/ -module.exports = function httpAdapter(config) { - return new Promise(function dispatchHttpRequest(resolvePromise, rejectPromise) { - var resolve = function resolve(value) { - resolvePromise(value); - }; - var reject = function reject(value) { - rejectPromise(value); - }; - var data = config.data; - var headers = config.headers; - - // Set User-Agent (required by some servers) - // Only set header if it hasn't been set in config - // See https://github.com/axios/axios/issues/69 - if (!headers['User-Agent'] && !headers['user-agent']) { - headers['User-Agent'] = 'axios/' + pkg.version; - } - - if (data && !utils.isStream(data)) { - if (Buffer.isBuffer(data)) { - // Nothing to do... - } else if (utils.isArrayBuffer(data)) { - data = Buffer.from(new Uint8Array(data)); - } else if (utils.isString(data)) { - data = Buffer.from(data, 'utf-8'); - } else { - return reject(createError( - 'Data after transformation must be a string, an ArrayBuffer, a Buffer, or a Stream', - config - )); - } - - // Add Content-Length header if data exists - headers['Content-Length'] = data.length; - } - - // HTTP basic authentication - var auth = undefined; - if (config.auth) { - var username = config.auth.username || ''; - var password = config.auth.password || ''; - auth = username + ':' + password; - } - - // Parse url - var fullPath = buildFullPath(config.baseURL, config.url); - var parsed = url.parse(fullPath); - var protocol = parsed.protocol || 'http:'; - - if (!auth && parsed.auth) { - var urlAuth = parsed.auth.split(':'); - var urlUsername = urlAuth[0] || ''; - var urlPassword = urlAuth[1] || ''; - auth = urlUsername + ':' + urlPassword; - } - - if (auth) { - delete headers.Authorization; - } - - var isHttpsRequest = isHttps.test(protocol); - var agent = isHttpsRequest ? config.httpsAgent : config.httpAgent; - - var options = { - path: buildURL(parsed.path, config.params, config.paramsSerializer).replace(/^\?/, ''), - method: config.method.toUpperCase(), - headers: headers, - agent: agent, - agents: { http: config.httpAgent, https: config.httpsAgent }, - auth: auth - }; - - if (config.socketPath) { - options.socketPath = config.socketPath; - } else { - options.hostname = parsed.hostname; - options.port = parsed.port; - } - - var proxy = config.proxy; - if (!proxy && proxy !== false) { - var proxyEnv = protocol.slice(0, -1) + '_proxy'; - var proxyUrl = process.env[proxyEnv] || process.env[proxyEnv.toUpperCase()]; - if (proxyUrl) { - var parsedProxyUrl = url.parse(proxyUrl); - var noProxyEnv = process.env.no_proxy || process.env.NO_PROXY; - var shouldProxy = true; - - if (noProxyEnv) { - var noProxy = noProxyEnv.split(',').map(function trim(s) { - return s.trim(); - }); - - shouldProxy = !noProxy.some(function proxyMatch(proxyElement) { - if (!proxyElement) { - return false; - } - if (proxyElement === '*') { - return true; - } - if (proxyElement[0] === '.' && - parsed.hostname.substr(parsed.hostname.length - proxyElement.length) === proxyElement) { - return true; - } - - return parsed.hostname === proxyElement; - }); - } - - - if (shouldProxy) { - proxy = { - host: parsedProxyUrl.hostname, - port: parsedProxyUrl.port - }; - - if (parsedProxyUrl.auth) { - var proxyUrlAuth = parsedProxyUrl.auth.split(':'); - proxy.auth = { - username: proxyUrlAuth[0], - password: proxyUrlAuth[1] - }; - } - } - } - } - - if (proxy) { - options.hostname = proxy.host; - options.host = proxy.host; - options.headers.host = parsed.hostname + (parsed.port ? ':' + parsed.port : ''); - options.port = proxy.port; - options.path = protocol + '//' + parsed.hostname + (parsed.port ? ':' + parsed.port : '') + options.path; - - // Basic proxy authorization - if (proxy.auth) { - var base64 = Buffer.from(proxy.auth.username + ':' + proxy.auth.password, 'utf8').toString('base64'); - options.headers['Proxy-Authorization'] = 'Basic ' + base64; - } - } - - var transport; - var isHttpsProxy = isHttpsRequest && (proxy ? isHttps.test(proxy.protocol) : true); - if (config.transport) { - transport = config.transport; - } else if (config.maxRedirects === 0) { - transport = isHttpsProxy ? https : http; - } else { - if (config.maxRedirects) { - options.maxRedirects = config.maxRedirects; - } - transport = isHttpsProxy ? httpsFollow : httpFollow; - } - - if (config.maxBodyLength > -1) { - options.maxBodyLength = config.maxBodyLength; - } - - // Create the request - var req = transport.request(options, function handleResponse(res) { - if (req.aborted) return; - - // uncompress the response body transparently if required - var stream = res; - - // return the last request in case of redirects - var lastRequest = res.req || req; - - - // if no content, is HEAD request or decompress disabled we should not decompress - if (res.statusCode !== 204 && lastRequest.method !== 'HEAD' && config.decompress !== false) { - switch (res.headers['content-encoding']) { - /*eslint default-case:0*/ - case 'gzip': - case 'compress': - case 'deflate': - // add the unzipper to the body stream processing pipeline - stream = stream.pipe(zlib.createUnzip()); - - // remove the content-encoding in order to not confuse downstream operations - delete res.headers['content-encoding']; - break; - } - } - - var response = { - status: res.statusCode, - statusText: res.statusMessage, - headers: res.headers, - config: config, - request: lastRequest - }; - - if (config.responseType === 'stream') { - response.data = stream; - settle(resolve, reject, response); - } else { - var responseBuffer = []; - stream.on('data', function handleStreamData(chunk) { - responseBuffer.push(chunk); - - // make sure the content length is not over the maxContentLength if specified - if (config.maxContentLength > -1 && Buffer.concat(responseBuffer).length > config.maxContentLength) { - stream.destroy(); - reject(createError('maxContentLength size of ' + config.maxContentLength + ' exceeded', - config, null, lastRequest)); - } - }); - - stream.on('error', function handleStreamError(err) { - if (req.aborted) return; - reject(enhanceError(err, config, null, lastRequest)); - }); - - stream.on('end', function handleStreamEnd() { - var responseData = Buffer.concat(responseBuffer); - if (config.responseType !== 'arraybuffer') { - responseData = responseData.toString(config.responseEncoding); - if (!config.responseEncoding || config.responseEncoding === 'utf8') { - responseData = utils.stripBOM(responseData); - } - } - - response.data = responseData; - settle(resolve, reject, response); - }); - } - }); - - // Handle errors - req.on('error', function handleRequestError(err) { - if (req.aborted && err.code !== 'ERR_FR_TOO_MANY_REDIRECTS') return; - reject(enhanceError(err, config, null, req)); - }); - - // Handle request timeout - if (config.timeout) { - // Sometime, the response will be very slow, and does not respond, the connect event will be block by event loop system. - // And timer callback will be fired, and abort() will be invoked before connection, then get "socket hang up" and code ECONNRESET. - // At this time, if we have a large number of request, nodejs will hang up some socket on background. and the number will up and up. - // And then these socket which be hang up will devoring CPU little by little. - // ClientRequest.setTimeout will be fired on the specify milliseconds, and can make sure that abort() will be fired after connect. - req.setTimeout(config.timeout, function handleRequestTimeout() { - req.abort(); - reject(createError('timeout of ' + config.timeout + 'ms exceeded', config, 'ECONNABORTED', req)); - }); - } - - if (config.cancelToken) { - // Handle cancellation - config.cancelToken.promise.then(function onCanceled(cancel) { - if (req.aborted) return; - - req.abort(); - reject(cancel); - }); - } - - // Send the request - if (utils.isStream(data)) { - data.on('error', function handleStreamError(err) { - reject(enhanceError(err, config, null, req)); - }).pipe(req); - } else { - req.end(data); - } - }); -}; - - -/***/ }), - -/***/ 63500: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var settle = __webpack_require__(29801); -var cookies = __webpack_require__(47536); -var buildURL = __webpack_require__(87481); -var buildFullPath = __webpack_require__(92074); -var parseHeaders = __webpack_require__(77912); -var isURLSameOrigin = __webpack_require__(11682); -var createError = __webpack_require__(3034); - -module.exports = function xhrAdapter(config) { - return new Promise(function dispatchXhrRequest(resolve, reject) { - var requestData = config.data; - var requestHeaders = config.headers; - - if (utils.isFormData(requestData)) { - delete requestHeaders['Content-Type']; // Let the browser set it - } - - if ( - (utils.isBlob(requestData) || utils.isFile(requestData)) && - requestData.type - ) { - delete requestHeaders['Content-Type']; // Let the browser set it - } - - var request = new XMLHttpRequest(); - - // HTTP basic authentication - if (config.auth) { - var username = config.auth.username || ''; - var password = unescape(encodeURIComponent(config.auth.password)) || ''; - requestHeaders.Authorization = 'Basic ' + btoa(username + ':' + password); - } - - var fullPath = buildFullPath(config.baseURL, config.url); - request.open(config.method.toUpperCase(), buildURL(fullPath, config.params, config.paramsSerializer), true); - - // Set the request timeout in MS - request.timeout = config.timeout; - - // Listen for ready state - request.onreadystatechange = function handleLoad() { - if (!request || request.readyState !== 4) { - return; - } - - // The request errored out and we didn't get a response, this will be - // handled by onerror instead - // With one exception: request that using file: protocol, most browsers - // will return status as 0 even though it's a successful request - if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) { - return; - } - - // Prepare the response - var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null; - var responseData = !config.responseType || config.responseType === 'text' ? request.responseText : request.response; - var response = { - data: responseData, - status: request.status, - statusText: request.statusText, - headers: responseHeaders, - config: config, - request: request - }; - - settle(resolve, reject, response); - - // Clean up request - request = null; - }; - - // Handle browser request cancellation (as opposed to a manual cancellation) - request.onabort = function handleAbort() { - if (!request) { - return; - } - - reject(createError('Request aborted', config, 'ECONNABORTED', request)); - - // Clean up request - request = null; - }; - - // Handle low level network errors - request.onerror = function handleError() { - // Real errors are hidden from us by the browser - // onerror should only fire if it's a network error - reject(createError('Network Error', config, null, request)); - - // Clean up request - request = null; - }; - - // Handle timeout - request.ontimeout = function handleTimeout() { - var timeoutErrorMessage = 'timeout of ' + config.timeout + 'ms exceeded'; - if (config.timeoutErrorMessage) { - timeoutErrorMessage = config.timeoutErrorMessage; - } - reject(createError(timeoutErrorMessage, config, 'ECONNABORTED', - request)); - - // Clean up request - request = null; - }; - - // Add xsrf header - // This is only done if running in a standard browser environment. - // Specifically not if we're in a web worker, or react-native. - if (utils.isStandardBrowserEnv()) { - // Add xsrf header - var xsrfValue = (config.withCredentials || isURLSameOrigin(fullPath)) && config.xsrfCookieName ? - cookies.read(config.xsrfCookieName) : - undefined; - - if (xsrfValue) { - requestHeaders[config.xsrfHeaderName] = xsrfValue; - } - } - - // Add headers to the request - if ('setRequestHeader' in request) { - utils.forEach(requestHeaders, function setRequestHeader(val, key) { - if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { - // Remove Content-Type if data is undefined - delete requestHeaders[key]; - } else { - // Otherwise add header to the request - request.setRequestHeader(key, val); - } - }); - } - - // Add withCredentials to request if needed - if (!utils.isUndefined(config.withCredentials)) { - request.withCredentials = !!config.withCredentials; - } - - // Add responseType to request if needed - if (config.responseType) { - try { - request.responseType = config.responseType; - } catch (e) { - // Expected DOMException thrown by browsers not compatible XMLHttpRequest Level 2. - // But, this can be suppressed for 'json' type as it can be parsed by default 'transformResponse' function. - if (config.responseType !== 'json') { - throw e; - } - } - } - - // Handle progress if needed - if (typeof config.onDownloadProgress === 'function') { - request.addEventListener('progress', config.onDownloadProgress); - } - - // Not all browsers support upload events - if (typeof config.onUploadProgress === 'function' && request.upload) { - request.upload.addEventListener('progress', config.onUploadProgress); - } - - if (config.cancelToken) { - // Handle cancellation - config.cancelToken.promise.then(function onCanceled(cancel) { - if (!request) { - return; - } - - request.abort(); - reject(cancel); - // Clean up request - request = null; - }); - } - - if (!requestData) { - requestData = null; - } - - // Send the request - request.send(requestData); - }); -}; - - -/***/ }), - -/***/ 64579: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var bind = __webpack_require__(69339); -var Axios = __webpack_require__(10353); -var mergeConfig = __webpack_require__(59807); -var defaults = __webpack_require__(6769); - -/** - * Create an instance of Axios - * - * @param {Object} defaultConfig The default config for the instance - * @return {Axios} A new instance of Axios - */ -function createInstance(defaultConfig) { - var context = new Axios(defaultConfig); - var instance = bind(Axios.prototype.request, context); - - // Copy axios.prototype to instance - utils.extend(instance, Axios.prototype, context); - - // Copy context to instance - utils.extend(instance, context); - - return instance; -} - -// Create the default instance to be exported -var axios = createInstance(defaults); - -// Expose Axios class to allow class inheritance -axios.Axios = Axios; - -// Factory for creating new instances -axios.create = function create(instanceConfig) { - return createInstance(mergeConfig(axios.defaults, instanceConfig)); -}; - -// Expose Cancel & CancelToken -axios.Cancel = __webpack_require__(56305); -axios.CancelToken = __webpack_require__(99576); -axios.isCancel = __webpack_require__(57822); - -// Expose all/spread -axios.all = function all(promises) { - return Promise.all(promises); -}; -axios.spread = __webpack_require__(83202); - -module.exports = axios; - -// Allow use of default import syntax in TypeScript -module.exports.default = axios; - - -/***/ }), - -/***/ 56305: -/***/ ((module) => { - -"use strict"; - - -/** - * A `Cancel` is an object that is thrown when an operation is canceled. - * - * @class - * @param {string=} message The message. - */ -function Cancel(message) { - this.message = message; -} - -Cancel.prototype.toString = function toString() { - return 'Cancel' + (this.message ? ': ' + this.message : ''); -}; - -Cancel.prototype.__CANCEL__ = true; - -module.exports = Cancel; - - -/***/ }), - -/***/ 99576: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var Cancel = __webpack_require__(56305); - -/** - * A `CancelToken` is an object that can be used to request cancellation of an operation. - * - * @class - * @param {Function} executor The executor function. - */ -function CancelToken(executor) { - if (typeof executor !== 'function') { - throw new TypeError('executor must be a function.'); - } - - var resolvePromise; - this.promise = new Promise(function promiseExecutor(resolve) { - resolvePromise = resolve; - }); - - var token = this; - executor(function cancel(message) { - if (token.reason) { - // Cancellation has already been requested - return; - } - - token.reason = new Cancel(message); - resolvePromise(token.reason); - }); -} - -/** - * Throws a `Cancel` if cancellation has been requested. - */ -CancelToken.prototype.throwIfRequested = function throwIfRequested() { - if (this.reason) { - throw this.reason; - } -}; - -/** - * Returns an object that contains a new `CancelToken` and a function that, when called, - * cancels the `CancelToken`. - */ -CancelToken.source = function source() { - var cancel; - var token = new CancelToken(function executor(c) { - cancel = c; - }); - return { - token: token, - cancel: cancel - }; -}; - -module.exports = CancelToken; - - -/***/ }), - -/***/ 57822: -/***/ ((module) => { - -"use strict"; - - -module.exports = function isCancel(value) { - return !!(value && value.__CANCEL__); -}; - - -/***/ }), - -/***/ 10353: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var buildURL = __webpack_require__(87481); -var InterceptorManager = __webpack_require__(88030); -var dispatchRequest = __webpack_require__(18944); -var mergeConfig = __webpack_require__(59807); - -/** - * Create a new instance of Axios - * - * @param {Object} instanceConfig The default config for the instance - */ -function Axios(instanceConfig) { - this.defaults = instanceConfig; - this.interceptors = { - request: new InterceptorManager(), - response: new InterceptorManager() - }; -} - -/** - * Dispatch a request - * - * @param {Object} config The config specific for this request (merged with this.defaults) - */ -Axios.prototype.request = function request(config) { - /*eslint no-param-reassign:0*/ - // Allow for axios('example/url'[, config]) a la fetch API - if (typeof config === 'string') { - config = arguments[1] || {}; - config.url = arguments[0]; - } else { - config = config || {}; - } - - config = mergeConfig(this.defaults, config); - - // Set config.method - if (config.method) { - config.method = config.method.toLowerCase(); - } else if (this.defaults.method) { - config.method = this.defaults.method.toLowerCase(); - } else { - config.method = 'get'; - } - - // Hook up interceptors middleware - var chain = [dispatchRequest, undefined]; - var promise = Promise.resolve(config); - - this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) { - chain.unshift(interceptor.fulfilled, interceptor.rejected); - }); - - this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { - chain.push(interceptor.fulfilled, interceptor.rejected); - }); - - while (chain.length) { - promise = promise.then(chain.shift(), chain.shift()); - } - - return promise; -}; - -Axios.prototype.getUri = function getUri(config) { - config = mergeConfig(this.defaults, config); - return buildURL(config.url, config.params, config.paramsSerializer).replace(/^\?/, ''); -}; - -// Provide aliases for supported request methods -utils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { - /*eslint func-names:0*/ - Axios.prototype[method] = function(url, config) { - return this.request(mergeConfig(config || {}, { - method: method, - url: url - })); - }; -}); - -utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { - /*eslint func-names:0*/ - Axios.prototype[method] = function(url, data, config) { - return this.request(mergeConfig(config || {}, { - method: method, - url: url, - data: data - })); - }; -}); - -module.exports = Axios; - - -/***/ }), - -/***/ 88030: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -function InterceptorManager() { - this.handlers = []; -} - -/** - * Add a new interceptor to the stack - * - * @param {Function} fulfilled The function to handle `then` for a `Promise` - * @param {Function} rejected The function to handle `reject` for a `Promise` - * - * @return {Number} An ID used to remove interceptor later - */ -InterceptorManager.prototype.use = function use(fulfilled, rejected) { - this.handlers.push({ - fulfilled: fulfilled, - rejected: rejected - }); - return this.handlers.length - 1; -}; - -/** - * Remove an interceptor from the stack - * - * @param {Number} id The ID that was returned by `use` - */ -InterceptorManager.prototype.eject = function eject(id) { - if (this.handlers[id]) { - this.handlers[id] = null; - } -}; - -/** - * Iterate over all the registered interceptors - * - * This method is particularly useful for skipping over any - * interceptors that may have become `null` calling `eject`. - * - * @param {Function} fn The function to call for each interceptor - */ -InterceptorManager.prototype.forEach = function forEach(fn) { - utils.forEach(this.handlers, function forEachHandler(h) { - if (h !== null) { - fn(h); - } - }); -}; - -module.exports = InterceptorManager; - - -/***/ }), - -/***/ 92074: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var isAbsoluteURL = __webpack_require__(55470); -var combineURLs = __webpack_require__(65824); - -/** - * Creates a new URL by combining the baseURL with the requestedURL, - * only when the requestedURL is not already an absolute URL. - * If the requestURL is absolute, this function returns the requestedURL untouched. - * - * @param {string} baseURL The base URL - * @param {string} requestedURL Absolute or relative URL to combine - * @returns {string} The combined full path - */ -module.exports = function buildFullPath(baseURL, requestedURL) { - if (baseURL && !isAbsoluteURL(requestedURL)) { - return combineURLs(baseURL, requestedURL); - } - return requestedURL; -}; - - -/***/ }), - -/***/ 3034: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var enhanceError = __webpack_require__(95261); - -/** - * Create an Error with the specified message, config, error code, request and response. - * - * @param {string} message The error message. - * @param {Object} config The config. - * @param {string} [code] The error code (for example, 'ECONNABORTED'). - * @param {Object} [request] The request. - * @param {Object} [response] The response. - * @returns {Error} The created error. - */ -module.exports = function createError(message, config, code, request, response) { - var error = new Error(message); - return enhanceError(error, config, code, request, response); -}; - - -/***/ }), - -/***/ 18944: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var transformData = __webpack_require__(62479); -var isCancel = __webpack_require__(57822); -var defaults = __webpack_require__(6769); - -/** - * Throws a `Cancel` if cancellation has been requested. - */ -function throwIfCancellationRequested(config) { - if (config.cancelToken) { - config.cancelToken.throwIfRequested(); - } -} - -/** - * Dispatch a request to the server using the configured adapter. - * - * @param {object} config The config that is to be used for the request - * @returns {Promise} The Promise to be fulfilled - */ -module.exports = function dispatchRequest(config) { - throwIfCancellationRequested(config); - - // Ensure headers exist - config.headers = config.headers || {}; - - // Transform request data - config.data = transformData( - config.data, - config.headers, - config.transformRequest - ); - - // Flatten headers - config.headers = utils.merge( - config.headers.common || {}, - config.headers[config.method] || {}, - config.headers - ); - - utils.forEach( - ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], - function cleanHeaderConfig(method) { - delete config.headers[method]; - } - ); - - var adapter = config.adapter || defaults.adapter; - - return adapter(config).then(function onAdapterResolution(response) { - throwIfCancellationRequested(config); - - // Transform response data - response.data = transformData( - response.data, - response.headers, - config.transformResponse - ); - - return response; - }, function onAdapterRejection(reason) { - if (!isCancel(reason)) { - throwIfCancellationRequested(config); - - // Transform response data - if (reason && reason.response) { - reason.response.data = transformData( - reason.response.data, - reason.response.headers, - config.transformResponse - ); - } - } - - return Promise.reject(reason); - }); -}; - - -/***/ }), - -/***/ 95261: -/***/ ((module) => { - -"use strict"; - - -/** - * Update an Error with the specified config, error code, and response. - * - * @param {Error} error The error to update. - * @param {Object} config The config. - * @param {string} [code] The error code (for example, 'ECONNABORTED'). - * @param {Object} [request] The request. - * @param {Object} [response] The response. - * @returns {Error} The error. - */ -module.exports = function enhanceError(error, config, code, request, response) { - error.config = config; - if (code) { - error.code = code; - } - - error.request = request; - error.response = response; - error.isAxiosError = true; - - error.toJSON = function toJSON() { - return { - // Standard - message: this.message, - name: this.name, - // Microsoft - description: this.description, - number: this.number, - // Mozilla - fileName: this.fileName, - lineNumber: this.lineNumber, - columnNumber: this.columnNumber, - stack: this.stack, - // Axios - config: this.config, - code: this.code - }; - }; - return error; -}; - - -/***/ }), - -/***/ 59807: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -/** - * Config-specific merge-function which creates a new config-object - * by merging two configuration objects together. - * - * @param {Object} config1 - * @param {Object} config2 - * @returns {Object} New object resulting from merging config2 to config1 - */ -module.exports = function mergeConfig(config1, config2) { - // eslint-disable-next-line no-param-reassign - config2 = config2 || {}; - var config = {}; - - var valueFromConfig2Keys = ['url', 'method', 'data']; - var mergeDeepPropertiesKeys = ['headers', 'auth', 'proxy', 'params']; - var defaultToConfig2Keys = [ - 'baseURL', 'transformRequest', 'transformResponse', 'paramsSerializer', - 'timeout', 'timeoutMessage', 'withCredentials', 'adapter', 'responseType', 'xsrfCookieName', - 'xsrfHeaderName', 'onUploadProgress', 'onDownloadProgress', 'decompress', - 'maxContentLength', 'maxBodyLength', 'maxRedirects', 'transport', 'httpAgent', - 'httpsAgent', 'cancelToken', 'socketPath', 'responseEncoding' - ]; - var directMergeKeys = ['validateStatus']; - - function getMergedValue(target, source) { - if (utils.isPlainObject(target) && utils.isPlainObject(source)) { - return utils.merge(target, source); - } else if (utils.isPlainObject(source)) { - return utils.merge({}, source); - } else if (utils.isArray(source)) { - return source.slice(); - } - return source; - } - - function mergeDeepProperties(prop) { - if (!utils.isUndefined(config2[prop])) { - config[prop] = getMergedValue(config1[prop], config2[prop]); - } else if (!utils.isUndefined(config1[prop])) { - config[prop] = getMergedValue(undefined, config1[prop]); - } - } - - utils.forEach(valueFromConfig2Keys, function valueFromConfig2(prop) { - if (!utils.isUndefined(config2[prop])) { - config[prop] = getMergedValue(undefined, config2[prop]); - } - }); - - utils.forEach(mergeDeepPropertiesKeys, mergeDeepProperties); - - utils.forEach(defaultToConfig2Keys, function defaultToConfig2(prop) { - if (!utils.isUndefined(config2[prop])) { - config[prop] = getMergedValue(undefined, config2[prop]); - } else if (!utils.isUndefined(config1[prop])) { - config[prop] = getMergedValue(undefined, config1[prop]); - } - }); - - utils.forEach(directMergeKeys, function merge(prop) { - if (prop in config2) { - config[prop] = getMergedValue(config1[prop], config2[prop]); - } else if (prop in config1) { - config[prop] = getMergedValue(undefined, config1[prop]); - } - }); - - var axiosKeys = valueFromConfig2Keys - .concat(mergeDeepPropertiesKeys) - .concat(defaultToConfig2Keys) - .concat(directMergeKeys); - - var otherKeys = Object - .keys(config1) - .concat(Object.keys(config2)) - .filter(function filterAxiosKeys(key) { - return axiosKeys.indexOf(key) === -1; - }); - - utils.forEach(otherKeys, mergeDeepProperties); - - return config; -}; - - -/***/ }), - -/***/ 29801: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var createError = __webpack_require__(3034); - -/** - * Resolve or reject a Promise based on response status. - * - * @param {Function} resolve A function that resolves the promise. - * @param {Function} reject A function that rejects the promise. - * @param {object} response The response. - */ -module.exports = function settle(resolve, reject, response) { - var validateStatus = response.config.validateStatus; - if (!response.status || !validateStatus || validateStatus(response.status)) { - resolve(response); - } else { - reject(createError( - 'Request failed with status code ' + response.status, - response.config, - null, - response.request, - response - )); - } -}; - - -/***/ }), - -/***/ 62479: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -/** - * Transform the data for a request or a response - * - * @param {Object|String} data The data to be transformed - * @param {Array} headers The headers for the request or response - * @param {Array|Function} fns A single function or Array of functions - * @returns {*} The resulting transformed data - */ -module.exports = function transformData(data, headers, fns) { - /*eslint no-param-reassign:0*/ - utils.forEach(fns, function transform(fn) { - data = fn(data, headers); - }); - - return data; -}; - - -/***/ }), - -/***/ 6769: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); -var normalizeHeaderName = __webpack_require__(53293); - -var DEFAULT_CONTENT_TYPE = { - 'Content-Type': 'application/x-www-form-urlencoded' -}; - -function setContentTypeIfUnset(headers, value) { - if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) { - headers['Content-Type'] = value; - } -} - -function getDefaultAdapter() { - var adapter; - if (typeof XMLHttpRequest !== 'undefined') { - // For browsers use XHR adapter - adapter = __webpack_require__(63500); - } else if (typeof process !== 'undefined' && Object.prototype.toString.call(process) === '[object process]') { - // For node use HTTP adapter - adapter = __webpack_require__(38007); - } - return adapter; -} - -var defaults = { - adapter: getDefaultAdapter(), - - transformRequest: [function transformRequest(data, headers) { - normalizeHeaderName(headers, 'Accept'); - normalizeHeaderName(headers, 'Content-Type'); - if (utils.isFormData(data) || - utils.isArrayBuffer(data) || - utils.isBuffer(data) || - utils.isStream(data) || - utils.isFile(data) || - utils.isBlob(data) - ) { - return data; - } - if (utils.isArrayBufferView(data)) { - return data.buffer; - } - if (utils.isURLSearchParams(data)) { - setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8'); - return data.toString(); - } - if (utils.isObject(data)) { - setContentTypeIfUnset(headers, 'application/json;charset=utf-8'); - return JSON.stringify(data); - } - return data; - }], - - transformResponse: [function transformResponse(data) { - /*eslint no-param-reassign:0*/ - if (typeof data === 'string') { - try { - data = JSON.parse(data); - } catch (e) { /* Ignore */ } - } - return data; - }], - - /** - * A timeout in milliseconds to abort a request. If set to 0 (default) a - * timeout is not created. - */ - timeout: 0, - - xsrfCookieName: 'XSRF-TOKEN', - xsrfHeaderName: 'X-XSRF-TOKEN', - - maxContentLength: -1, - maxBodyLength: -1, - - validateStatus: function validateStatus(status) { - return status >= 200 && status < 300; - } -}; - -defaults.headers = { - common: { - 'Accept': 'application/json, text/plain, */*' - } -}; - -utils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { - defaults.headers[method] = {}; -}); - -utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { - defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE); -}); - -module.exports = defaults; - - -/***/ }), - -/***/ 69339: -/***/ ((module) => { - -"use strict"; - - -module.exports = function bind(fn, thisArg) { - return function wrap() { - var args = new Array(arguments.length); - for (var i = 0; i < args.length; i++) { - args[i] = arguments[i]; - } - return fn.apply(thisArg, args); - }; -}; - - -/***/ }), - -/***/ 87481: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -function encode(val) { - return encodeURIComponent(val). - replace(/%3A/gi, ':'). - replace(/%24/g, '$'). - replace(/%2C/gi, ','). - replace(/%20/g, '+'). - replace(/%5B/gi, '['). - replace(/%5D/gi, ']'); -} - -/** - * Build a URL by appending params to the end - * - * @param {string} url The base of the url (e.g., http://www.google.com) - * @param {object} [params] The params to be appended - * @returns {string} The formatted url - */ -module.exports = function buildURL(url, params, paramsSerializer) { - /*eslint no-param-reassign:0*/ - if (!params) { - return url; - } - - var serializedParams; - if (paramsSerializer) { - serializedParams = paramsSerializer(params); - } else if (utils.isURLSearchParams(params)) { - serializedParams = params.toString(); - } else { - var parts = []; - - utils.forEach(params, function serialize(val, key) { - if (val === null || typeof val === 'undefined') { - return; - } - - if (utils.isArray(val)) { - key = key + '[]'; - } else { - val = [val]; - } - - utils.forEach(val, function parseValue(v) { - if (utils.isDate(v)) { - v = v.toISOString(); - } else if (utils.isObject(v)) { - v = JSON.stringify(v); - } - parts.push(encode(key) + '=' + encode(v)); - }); - }); - - serializedParams = parts.join('&'); - } - - if (serializedParams) { - var hashmarkIndex = url.indexOf('#'); - if (hashmarkIndex !== -1) { - url = url.slice(0, hashmarkIndex); - } - - url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; - } - - return url; -}; - - -/***/ }), - -/***/ 65824: -/***/ ((module) => { - -"use strict"; - - -/** - * Creates a new URL by combining the specified URLs - * - * @param {string} baseURL The base URL - * @param {string} relativeURL The relative URL - * @returns {string} The combined URL - */ -module.exports = function combineURLs(baseURL, relativeURL) { - return relativeURL - ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') - : baseURL; -}; - - -/***/ }), - -/***/ 47536: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -module.exports = ( - utils.isStandardBrowserEnv() ? - - // Standard browser envs support document.cookie - (function standardBrowserEnv() { - return { - write: function write(name, value, expires, path, domain, secure) { - var cookie = []; - cookie.push(name + '=' + encodeURIComponent(value)); - - if (utils.isNumber(expires)) { - cookie.push('expires=' + new Date(expires).toGMTString()); - } - - if (utils.isString(path)) { - cookie.push('path=' + path); - } - - if (utils.isString(domain)) { - cookie.push('domain=' + domain); - } - - if (secure === true) { - cookie.push('secure'); - } - - document.cookie = cookie.join('; '); - }, - - read: function read(name) { - var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); - return (match ? decodeURIComponent(match[3]) : null); - }, - - remove: function remove(name) { - this.write(name, '', Date.now() - 86400000); - } - }; - })() : - - // Non standard browser env (web workers, react-native) lack needed support. - (function nonStandardBrowserEnv() { - return { - write: function write() {}, - read: function read() { return null; }, - remove: function remove() {} - }; - })() -); - - -/***/ }), - -/***/ 55470: -/***/ ((module) => { - -"use strict"; - - -/** - * Determines whether the specified URL is absolute - * - * @param {string} url The URL to test - * @returns {boolean} True if the specified URL is absolute, otherwise false - */ -module.exports = function isAbsoluteURL(url) { - // A URL is considered absolute if it begins with "://" or "//" (protocol-relative URL). - // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed - // by any combination of letters, digits, plus, period, or hyphen. - return /^([a-z][a-z\d\+\-\.]*:)?\/\//i.test(url); -}; - - -/***/ }), - -/***/ 11682: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -module.exports = ( - utils.isStandardBrowserEnv() ? - - // Standard browser envs have full support of the APIs needed to test - // whether the request URL is of the same origin as current location. - (function standardBrowserEnv() { - var msie = /(msie|trident)/i.test(navigator.userAgent); - var urlParsingNode = document.createElement('a'); - var originURL; - - /** - * Parse a URL to discover it's components - * - * @param {String} url The URL to be parsed - * @returns {Object} - */ - function resolveURL(url) { - var href = url; - - if (msie) { - // IE needs attribute set twice to normalize properties - urlParsingNode.setAttribute('href', href); - href = urlParsingNode.href; - } - - urlParsingNode.setAttribute('href', href); - - // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils - return { - href: urlParsingNode.href, - protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '', - host: urlParsingNode.host, - search: urlParsingNode.search ? urlParsingNode.search.replace(/^\?/, '') : '', - hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '', - hostname: urlParsingNode.hostname, - port: urlParsingNode.port, - pathname: (urlParsingNode.pathname.charAt(0) === '/') ? - urlParsingNode.pathname : - '/' + urlParsingNode.pathname - }; - } - - originURL = resolveURL(window.location.href); - - /** - * Determine if a URL shares the same origin as the current location - * - * @param {String} requestURL The URL to test - * @returns {boolean} True if URL shares the same origin, otherwise false - */ - return function isURLSameOrigin(requestURL) { - var parsed = (utils.isString(requestURL)) ? resolveURL(requestURL) : requestURL; - return (parsed.protocol === originURL.protocol && - parsed.host === originURL.host); - }; - })() : - - // Non standard browser envs (web workers, react-native) lack needed support. - (function nonStandardBrowserEnv() { - return function isURLSameOrigin() { - return true; - }; - })() -); - - -/***/ }), - -/***/ 53293: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -module.exports = function normalizeHeaderName(headers, normalizedName) { - utils.forEach(headers, function processHeader(value, name) { - if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { - headers[normalizedName] = value; - delete headers[name]; - } - }); -}; - - -/***/ }), - -/***/ 77912: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var utils = __webpack_require__(19520); - -// Headers whose duplicates are ignored by node -// c.f. https://nodejs.org/api/http.html#http_message_headers -var ignoreDuplicateOf = [ - 'age', 'authorization', 'content-length', 'content-type', 'etag', - 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since', - 'last-modified', 'location', 'max-forwards', 'proxy-authorization', - 'referer', 'retry-after', 'user-agent' -]; - -/** - * Parse headers into an object - * - * ``` - * Date: Wed, 27 Aug 2014 08:58:49 GMT - * Content-Type: application/json - * Connection: keep-alive - * Transfer-Encoding: chunked - * ``` - * - * @param {String} headers Headers needing to be parsed - * @returns {Object} Headers parsed into an object - */ -module.exports = function parseHeaders(headers) { - var parsed = {}; - var key; - var val; - var i; - - if (!headers) { return parsed; } - - utils.forEach(headers.split('\n'), function parser(line) { - i = line.indexOf(':'); - key = utils.trim(line.substr(0, i)).toLowerCase(); - val = utils.trim(line.substr(i + 1)); - - if (key) { - if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) { - return; - } - if (key === 'set-cookie') { - parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); - } else { - parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; - } - } - }); - - return parsed; -}; - - -/***/ }), - -/***/ 83202: -/***/ ((module) => { - -"use strict"; - - -/** - * Syntactic sugar for invoking a function and expanding an array for arguments. - * - * Common use case would be to use `Function.prototype.apply`. - * - * ```js - * function f(x, y, z) {} - * var args = [1, 2, 3]; - * f.apply(null, args); - * ``` - * - * With `spread` this example can be re-written. - * - * ```js - * spread(function(x, y, z) {})([1, 2, 3]); - * ``` - * - * @param {Function} callback - * @returns {Function} - */ -module.exports = function spread(callback) { - return function wrap(arr) { - return callback.apply(null, arr); - }; -}; - - -/***/ }), - -/***/ 19520: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var bind = __webpack_require__(69339); - -/*global toString:true*/ - -// utils is a library of generic helper functions non-specific to axios - -var toString = Object.prototype.toString; - -/** - * Determine if a value is an Array - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an Array, otherwise false - */ -function isArray(val) { - return toString.call(val) === '[object Array]'; -} - -/** - * Determine if a value is undefined - * - * @param {Object} val The value to test - * @returns {boolean} True if the value is undefined, otherwise false - */ -function isUndefined(val) { - return typeof val === 'undefined'; -} - -/** - * Determine if a value is a Buffer - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Buffer, otherwise false - */ -function isBuffer(val) { - return val !== null && !isUndefined(val) && val.constructor !== null && !isUndefined(val.constructor) - && typeof val.constructor.isBuffer === 'function' && val.constructor.isBuffer(val); -} - -/** - * Determine if a value is an ArrayBuffer - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an ArrayBuffer, otherwise false - */ -function isArrayBuffer(val) { - return toString.call(val) === '[object ArrayBuffer]'; -} - -/** - * Determine if a value is a FormData - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an FormData, otherwise false - */ -function isFormData(val) { - return (typeof FormData !== 'undefined') && (val instanceof FormData); -} - -/** - * Determine if a value is a view on an ArrayBuffer - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false - */ -function isArrayBufferView(val) { - var result; - if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) { - result = ArrayBuffer.isView(val); - } else { - result = (val) && (val.buffer) && (val.buffer instanceof ArrayBuffer); - } - return result; -} - -/** - * Determine if a value is a String - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a String, otherwise false - */ -function isString(val) { - return typeof val === 'string'; -} - -/** - * Determine if a value is a Number - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Number, otherwise false - */ -function isNumber(val) { - return typeof val === 'number'; -} - -/** - * Determine if a value is an Object - * - * @param {Object} val The value to test - * @returns {boolean} True if value is an Object, otherwise false - */ -function isObject(val) { - return val !== null && typeof val === 'object'; -} - -/** - * Determine if a value is a plain Object - * - * @param {Object} val The value to test - * @return {boolean} True if value is a plain Object, otherwise false - */ -function isPlainObject(val) { - if (toString.call(val) !== '[object Object]') { - return false; - } - - var prototype = Object.getPrototypeOf(val); - return prototype === null || prototype === Object.prototype; -} - -/** - * Determine if a value is a Date - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Date, otherwise false - */ -function isDate(val) { - return toString.call(val) === '[object Date]'; -} - -/** - * Determine if a value is a File - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a File, otherwise false - */ -function isFile(val) { - return toString.call(val) === '[object File]'; -} - -/** - * Determine if a value is a Blob - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Blob, otherwise false - */ -function isBlob(val) { - return toString.call(val) === '[object Blob]'; -} - -/** - * Determine if a value is a Function - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Function, otherwise false - */ -function isFunction(val) { - return toString.call(val) === '[object Function]'; -} - -/** - * Determine if a value is a Stream - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a Stream, otherwise false - */ -function isStream(val) { - return isObject(val) && isFunction(val.pipe); -} - -/** - * Determine if a value is a URLSearchParams object - * - * @param {Object} val The value to test - * @returns {boolean} True if value is a URLSearchParams object, otherwise false - */ -function isURLSearchParams(val) { - return typeof URLSearchParams !== 'undefined' && val instanceof URLSearchParams; -} - -/** - * Trim excess whitespace off the beginning and end of a string - * - * @param {String} str The String to trim - * @returns {String} The String freed of excess whitespace - */ -function trim(str) { - return str.replace(/^\s*/, '').replace(/\s*$/, ''); -} - -/** - * Determine if we're running in a standard browser environment - * - * This allows axios to run in a web worker, and react-native. - * Both environments support XMLHttpRequest, but not fully standard globals. - * - * web workers: - * typeof window -> undefined - * typeof document -> undefined - * - * react-native: - * navigator.product -> 'ReactNative' - * nativescript - * navigator.product -> 'NativeScript' or 'NS' - */ -function isStandardBrowserEnv() { - if (typeof navigator !== 'undefined' && (navigator.product === 'ReactNative' || - navigator.product === 'NativeScript' || - navigator.product === 'NS')) { - return false; - } - return ( - typeof window !== 'undefined' && - typeof document !== 'undefined' - ); -} - -/** - * Iterate over an Array or an Object invoking a function for each item. - * - * If `obj` is an Array callback will be called passing - * the value, index, and complete array for each item. - * - * If 'obj' is an Object callback will be called passing - * the value, key, and complete object for each property. - * - * @param {Object|Array} obj The object to iterate - * @param {Function} fn The callback to invoke for each item - */ -function forEach(obj, fn) { - // Don't bother if no value provided - if (obj === null || typeof obj === 'undefined') { - return; - } - - // Force an array if not already something iterable - if (typeof obj !== 'object') { - /*eslint no-param-reassign:0*/ - obj = [obj]; - } - - if (isArray(obj)) { - // Iterate over array values - for (var i = 0, l = obj.length; i < l; i++) { - fn.call(null, obj[i], i, obj); - } - } else { - // Iterate over object keys - for (var key in obj) { - if (Object.prototype.hasOwnProperty.call(obj, key)) { - fn.call(null, obj[key], key, obj); - } - } - } -} - -/** - * Accepts varargs expecting each argument to be an object, then - * immutably merges the properties of each object and returns result. - * - * When multiple objects contain the same key the later object in - * the arguments list will take precedence. - * - * Example: - * - * ```js - * var result = merge({foo: 123}, {foo: 456}); - * console.log(result.foo); // outputs 456 - * ``` - * - * @param {Object} obj1 Object to merge - * @returns {Object} Result of all merge properties - */ -function merge(/* obj1, obj2, obj3, ... */) { - var result = {}; - function assignValue(val, key) { - if (isPlainObject(result[key]) && isPlainObject(val)) { - result[key] = merge(result[key], val); - } else if (isPlainObject(val)) { - result[key] = merge({}, val); - } else if (isArray(val)) { - result[key] = val.slice(); - } else { - result[key] = val; - } - } - - for (var i = 0, l = arguments.length; i < l; i++) { - forEach(arguments[i], assignValue); - } - return result; -} - -/** - * Extends object a by mutably adding to it the properties of object b. - * - * @param {Object} a The object to be extended - * @param {Object} b The object to copy properties from - * @param {Object} thisArg The object to bind function to - * @return {Object} The resulting value of object a - */ -function extend(a, b, thisArg) { - forEach(b, function assignValue(val, key) { - if (thisArg && typeof val === 'function') { - a[key] = bind(val, thisArg); - } else { - a[key] = val; - } - }); - return a; -} - -/** - * Remove byte order marker. This catches EF BB BF (the UTF-8 BOM) - * - * @param {string} content with BOM - * @return {string} content value without BOM - */ -function stripBOM(content) { - if (content.charCodeAt(0) === 0xFEFF) { - content = content.slice(1); - } - return content; -} - -module.exports = { - isArray: isArray, - isArrayBuffer: isArrayBuffer, - isBuffer: isBuffer, - isFormData: isFormData, - isArrayBufferView: isArrayBufferView, - isString: isString, - isNumber: isNumber, - isObject: isObject, - isPlainObject: isPlainObject, - isUndefined: isUndefined, - isDate: isDate, - isFile: isFile, - isBlob: isBlob, - isFunction: isFunction, - isStream: isStream, - isURLSearchParams: isURLSearchParams, - isStandardBrowserEnv: isStandardBrowserEnv, - forEach: forEach, - merge: merge, - extend: extend, - trim: trim, - stripBOM: stripBOM -}; - - -/***/ }), - -/***/ 15893: -/***/ ((module) => { - -"use strict"; - -module.exports = balanced; -function balanced(a, b, str) { - if (a instanceof RegExp) a = maybeMatch(a, str); - if (b instanceof RegExp) b = maybeMatch(b, str); - - var r = range(a, b, str); - - return r && { - start: r[0], - end: r[1], - pre: str.slice(0, r[0]), - body: str.slice(r[0] + a.length, r[1]), - post: str.slice(r[1] + b.length) - }; -} - -function maybeMatch(reg, str) { - var m = str.match(reg); - return m ? m[0] : null; -} - -balanced.range = range; -function range(a, b, str) { - var begs, beg, left, right, result; - var ai = str.indexOf(a); - var bi = str.indexOf(b, ai + 1); - var i = ai; - - if (ai >= 0 && bi > 0) { - begs = []; - left = str.length; - - while (i >= 0 && !result) { - if (i == ai) { - begs.push(i); - ai = str.indexOf(a, i + 1); - } else if (begs.length == 1) { - result = [ begs.pop(), bi ]; - } else { - beg = begs.pop(); - if (beg < left) { - left = beg; - right = bi; - } - - bi = str.indexOf(b, i + 1); - } - - i = ai < bi && ai >= 0 ? ai : bi; - } - - if (begs.length) { - result = [ left, right ]; - } - } - - return result; -} - - -/***/ }), - -/***/ 46401: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -var register = __webpack_require__(27798) -var addHook = __webpack_require__(82446) -var removeHook = __webpack_require__(16436) - -// bind with array of arguments: https://stackoverflow.com/a/21792913 -var bind = Function.bind -var bindable = bind.bind(bind) - -function bindApi (hook, state, name) { - var removeHookRef = bindable(removeHook, null).apply(null, name ? [state, name] : [state]) - hook.api = { remove: removeHookRef } - hook.remove = removeHookRef - - ;['before', 'error', 'after', 'wrap'].forEach(function (kind) { - var args = name ? [state, kind, name] : [state, kind] - hook[kind] = hook.api[kind] = bindable(addHook, null).apply(null, args) - }) -} - -function HookSingular () { - var singularHookName = 'h' - var singularHookState = { - registry: {} - } - var singularHook = register.bind(null, singularHookState, singularHookName) - bindApi(singularHook, singularHookState, singularHookName) - return singularHook -} - -function HookCollection () { - var state = { - registry: {} - } - - var hook = register.bind(null, state) - bindApi(hook, state) - - return hook -} - -var collectionHookDeprecationMessageDisplayed = false -function Hook () { - if (!collectionHookDeprecationMessageDisplayed) { - console.warn('[before-after-hook]: "Hook()" repurposing warning, use "Hook.Collection()". Read more: https://git.io/upgrade-before-after-hook-to-1.4') - collectionHookDeprecationMessageDisplayed = true - } - return HookCollection() -} - -Hook.Singular = HookSingular.bind() -Hook.Collection = HookCollection.bind() - -module.exports = Hook -// expose constructors as a named property for TypeScript -module.exports.Hook = Hook -module.exports.Singular = Hook.Singular -module.exports.Collection = Hook.Collection - - -/***/ }), - -/***/ 82446: -/***/ ((module) => { - -module.exports = addHook - -function addHook (state, kind, name, hook) { - var orig = hook - if (!state.registry[name]) { - state.registry[name] = [] - } - - if (kind === 'before') { - hook = function (method, options) { - return Promise.resolve() - .then(orig.bind(null, options)) - .then(method.bind(null, options)) - } - } - - if (kind === 'after') { - hook = function (method, options) { - var result - return Promise.resolve() - .then(method.bind(null, options)) - .then(function (result_) { - result = result_ - return orig(result, options) - }) - .then(function () { - return result - }) - } - } - - if (kind === 'error') { - hook = function (method, options) { - return Promise.resolve() - .then(method.bind(null, options)) - .catch(function (error) { - return orig(error, options) - }) - } - } - - state.registry[name].push({ - hook: hook, - orig: orig - }) -} - - -/***/ }), - -/***/ 27798: -/***/ ((module) => { - -module.exports = register - -function register (state, name, method, options) { - if (typeof method !== 'function') { - throw new Error('method for before hook must be a function') - } - - if (!options) { - options = {} - } - - if (Array.isArray(name)) { - return name.reverse().reduce(function (callback, name) { - return register.bind(null, state, name, callback, options) - }, method)() - } - - return Promise.resolve() - .then(function () { - if (!state.registry[name]) { - return method(options) - } - - return (state.registry[name]).reduce(function (method, registered) { - return registered.hook.bind(null, method, options) - }, method)() - }) -} - - -/***/ }), - -/***/ 16436: -/***/ ((module) => { - -module.exports = removeHook - -function removeHook (state, name, method) { - if (!state.registry[name]) { - return - } - - var index = state.registry[name] - .map(function (registered) { return registered.orig }) - .indexOf(method) - - if (index === -1) { - return - } - - state.registry[name].splice(index, 1) -} - - -/***/ }), - -/***/ 66616: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -const { Buffer } = __webpack_require__(64293) -const symbol = Symbol.for('BufferList') - -function BufferList (buf) { - if (!(this instanceof BufferList)) { - return new BufferList(buf) - } - - BufferList._init.call(this, buf) -} - -BufferList._init = function _init (buf) { - Object.defineProperty(this, symbol, { value: true }) - - this._bufs = [] - this.length = 0 - - if (buf) { - this.append(buf) - } -} - -BufferList.prototype._new = function _new (buf) { - return new BufferList(buf) -} - -BufferList.prototype._offset = function _offset (offset) { - if (offset === 0) { - return [0, 0] - } - - let tot = 0 - - for (let i = 0; i < this._bufs.length; i++) { - const _t = tot + this._bufs[i].length - if (offset < _t || i === this._bufs.length - 1) { - return [i, offset - tot] - } - tot = _t - } -} - -BufferList.prototype._reverseOffset = function (blOffset) { - const bufferId = blOffset[0] - let offset = blOffset[1] - - for (let i = 0; i < bufferId; i++) { - offset += this._bufs[i].length - } - - return offset -} - -BufferList.prototype.get = function get (index) { - if (index > this.length || index < 0) { - return undefined - } - - const offset = this._offset(index) - - return this._bufs[offset[0]][offset[1]] -} - -BufferList.prototype.slice = function slice (start, end) { - if (typeof start === 'number' && start < 0) { - start += this.length - } - - if (typeof end === 'number' && end < 0) { - end += this.length - } - - return this.copy(null, 0, start, end) -} - -BufferList.prototype.copy = function copy (dst, dstStart, srcStart, srcEnd) { - if (typeof srcStart !== 'number' || srcStart < 0) { - srcStart = 0 - } - - if (typeof srcEnd !== 'number' || srcEnd > this.length) { - srcEnd = this.length - } - - if (srcStart >= this.length) { - return dst || Buffer.alloc(0) - } - - if (srcEnd <= 0) { - return dst || Buffer.alloc(0) - } - - const copy = !!dst - const off = this._offset(srcStart) - const len = srcEnd - srcStart - let bytes = len - let bufoff = (copy && dstStart) || 0 - let start = off[1] - - // copy/slice everything - if (srcStart === 0 && srcEnd === this.length) { - if (!copy) { - // slice, but full concat if multiple buffers - return this._bufs.length === 1 - ? this._bufs[0] - : Buffer.concat(this._bufs, this.length) - } - - // copy, need to copy individual buffers - for (let i = 0; i < this._bufs.length; i++) { - this._bufs[i].copy(dst, bufoff) - bufoff += this._bufs[i].length - } - - return dst - } - - // easy, cheap case where it's a subset of one of the buffers - if (bytes <= this._bufs[off[0]].length - start) { - return copy - ? this._bufs[off[0]].copy(dst, dstStart, start, start + bytes) - : this._bufs[off[0]].slice(start, start + bytes) - } - - if (!copy) { - // a slice, we need something to copy in to - dst = Buffer.allocUnsafe(len) - } - - for (let i = off[0]; i < this._bufs.length; i++) { - const l = this._bufs[i].length - start - - if (bytes > l) { - this._bufs[i].copy(dst, bufoff, start) - bufoff += l - } else { - this._bufs[i].copy(dst, bufoff, start, start + bytes) - bufoff += l - break - } - - bytes -= l - - if (start) { - start = 0 - } - } - - // safeguard so that we don't return uninitialized memory - if (dst.length > bufoff) return dst.slice(0, bufoff) - - return dst -} - -BufferList.prototype.shallowSlice = function shallowSlice (start, end) { - start = start || 0 - end = typeof end !== 'number' ? this.length : end - - if (start < 0) { - start += this.length - } - - if (end < 0) { - end += this.length - } - - if (start === end) { - return this._new() - } - - const startOffset = this._offset(start) - const endOffset = this._offset(end) - const buffers = this._bufs.slice(startOffset[0], endOffset[0] + 1) - - if (endOffset[1] === 0) { - buffers.pop() - } else { - buffers[buffers.length - 1] = buffers[buffers.length - 1].slice(0, endOffset[1]) - } - - if (startOffset[1] !== 0) { - buffers[0] = buffers[0].slice(startOffset[1]) - } - - return this._new(buffers) -} - -BufferList.prototype.toString = function toString (encoding, start, end) { - return this.slice(start, end).toString(encoding) -} - -BufferList.prototype.consume = function consume (bytes) { - // first, normalize the argument, in accordance with how Buffer does it - bytes = Math.trunc(bytes) - // do nothing if not a positive number - if (Number.isNaN(bytes) || bytes <= 0) return this - - while (this._bufs.length) { - if (bytes >= this._bufs[0].length) { - bytes -= this._bufs[0].length - this.length -= this._bufs[0].length - this._bufs.shift() - } else { - this._bufs[0] = this._bufs[0].slice(bytes) - this.length -= bytes - break - } - } - - return this -} - -BufferList.prototype.duplicate = function duplicate () { - const copy = this._new() - - for (let i = 0; i < this._bufs.length; i++) { - copy.append(this._bufs[i]) - } - - return copy -} - -BufferList.prototype.append = function append (buf) { - if (buf == null) { - return this - } - - if (buf.buffer) { - // append a view of the underlying ArrayBuffer - this._appendBuffer(Buffer.from(buf.buffer, buf.byteOffset, buf.byteLength)) - } else if (Array.isArray(buf)) { - for (let i = 0; i < buf.length; i++) { - this.append(buf[i]) - } - } else if (this._isBufferList(buf)) { - // unwrap argument into individual BufferLists - for (let i = 0; i < buf._bufs.length; i++) { - this.append(buf._bufs[i]) - } - } else { - // coerce number arguments to strings, since Buffer(number) does - // uninitialized memory allocation - if (typeof buf === 'number') { - buf = buf.toString() - } - - this._appendBuffer(Buffer.from(buf)) - } - - return this -} - -BufferList.prototype._appendBuffer = function appendBuffer (buf) { - this._bufs.push(buf) - this.length += buf.length -} - -BufferList.prototype.indexOf = function (search, offset, encoding) { - if (encoding === undefined && typeof offset === 'string') { - encoding = offset - offset = undefined - } - - if (typeof search === 'function' || Array.isArray(search)) { - throw new TypeError('The "value" argument must be one of type string, Buffer, BufferList, or Uint8Array.') - } else if (typeof search === 'number') { - search = Buffer.from([search]) - } else if (typeof search === 'string') { - search = Buffer.from(search, encoding) - } else if (this._isBufferList(search)) { - search = search.slice() - } else if (Array.isArray(search.buffer)) { - search = Buffer.from(search.buffer, search.byteOffset, search.byteLength) - } else if (!Buffer.isBuffer(search)) { - search = Buffer.from(search) - } - - offset = Number(offset || 0) - - if (isNaN(offset)) { - offset = 0 - } - - if (offset < 0) { - offset = this.length + offset - } - - if (offset < 0) { - offset = 0 - } - - if (search.length === 0) { - return offset > this.length ? this.length : offset - } - - const blOffset = this._offset(offset) - let blIndex = blOffset[0] // index of which internal buffer we're working on - let buffOffset = blOffset[1] // offset of the internal buffer we're working on - - // scan over each buffer - for (; blIndex < this._bufs.length; blIndex++) { - const buff = this._bufs[blIndex] - - while (buffOffset < buff.length) { - const availableWindow = buff.length - buffOffset - - if (availableWindow >= search.length) { - const nativeSearchResult = buff.indexOf(search, buffOffset) - - if (nativeSearchResult !== -1) { - return this._reverseOffset([blIndex, nativeSearchResult]) - } - - buffOffset = buff.length - search.length + 1 // end of native search window - } else { - const revOffset = this._reverseOffset([blIndex, buffOffset]) - - if (this._match(revOffset, search)) { - return revOffset - } - - buffOffset++ - } - } - - buffOffset = 0 - } - - return -1 -} - -BufferList.prototype._match = function (offset, search) { - if (this.length - offset < search.length) { - return false - } - - for (let searchOffset = 0; searchOffset < search.length; searchOffset++) { - if (this.get(offset + searchOffset) !== search[searchOffset]) { - return false - } - } - return true -} - -;(function () { - const methods = { - readDoubleBE: 8, - readDoubleLE: 8, - readFloatBE: 4, - readFloatLE: 4, - readInt32BE: 4, - readInt32LE: 4, - readUInt32BE: 4, - readUInt32LE: 4, - readInt16BE: 2, - readInt16LE: 2, - readUInt16BE: 2, - readUInt16LE: 2, - readInt8: 1, - readUInt8: 1, - readIntBE: null, - readIntLE: null, - readUIntBE: null, - readUIntLE: null - } - - for (const m in methods) { - (function (m) { - if (methods[m] === null) { - BufferList.prototype[m] = function (offset, byteLength) { - return this.slice(offset, offset + byteLength)[m](0, byteLength) - } - } else { - BufferList.prototype[m] = function (offset) { - return this.slice(offset, offset + methods[m])[m](0) - } - } - }(m)) - } -}()) - -// Used internally by the class and also as an indicator of this object being -// a `BufferList`. It's not possible to use `instanceof BufferList` in a browser -// environment because there could be multiple different copies of the -// BufferList class and some `BufferList`s might be `BufferList`s. -BufferList.prototype._isBufferList = function _isBufferList (b) { - return b instanceof BufferList || BufferList.isBufferList(b) -} - -BufferList.isBufferList = function isBufferList (b) { - return b != null && b[symbol] -} - -module.exports = BufferList - - -/***/ }), - -/***/ 96986: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -const DuplexStream = __webpack_require__(30009).Duplex -const inherits = __webpack_require__(94835) -const BufferList = __webpack_require__(66616) - -function BufferListStream (callback) { - if (!(this instanceof BufferListStream)) { - return new BufferListStream(callback) - } - - if (typeof callback === 'function') { - this._callback = callback - - const piper = function piper (err) { - if (this._callback) { - this._callback(err) - this._callback = null - } - }.bind(this) - - this.on('pipe', function onPipe (src) { - src.on('error', piper) - }) - this.on('unpipe', function onUnpipe (src) { - src.removeListener('error', piper) - }) - - callback = null - } - - BufferList._init.call(this, callback) - DuplexStream.call(this) -} - -inherits(BufferListStream, DuplexStream) -Object.assign(BufferListStream.prototype, BufferList.prototype) - -BufferListStream.prototype._new = function _new (callback) { - return new BufferListStream(callback) -} - -BufferListStream.prototype._write = function _write (buf, encoding, callback) { - this._appendBuffer(buf) - - if (typeof callback === 'function') { - callback() - } -} - -BufferListStream.prototype._read = function _read (size) { - if (!this.length) { - return this.push(null) - } - - size = Math.min(size, this.length) - this.push(this.slice(0, size)) - this.consume(size) -} - -BufferListStream.prototype.end = function end (chunk) { - DuplexStream.prototype.end.call(this, chunk) - - if (this._callback) { - this._callback(null, this.slice()) - this._callback = null - } -} - -BufferListStream.prototype._destroy = function _destroy (err, cb) { - this._bufs.length = 0 - this.length = 0 - cb(err) -} - -BufferListStream.prototype._isBufferList = function _isBufferList (b) { - return b instanceof BufferListStream || b instanceof BufferList || BufferListStream.isBufferList(b) -} - -BufferListStream.isBufferList = BufferList.isBufferList - -module.exports = BufferListStream -module.exports.BufferListStream = BufferListStream -module.exports.BufferList = BufferList - - -/***/ }), - -/***/ 94835: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -try { - var util = __webpack_require__(31669); - /* istanbul ignore next */ - if (typeof util.inherits !== 'function') throw ''; - module.exports = util.inherits; -} catch (e) { - /* istanbul ignore next */ - module.exports = __webpack_require__(72739); -} - - -/***/ }), - -/***/ 72739: -/***/ ((module) => { - -if (typeof Object.create === 'function') { - // implementation from standard node.js 'util' module - module.exports = function inherits(ctor, superCtor) { - if (superCtor) { - ctor.super_ = superCtor - ctor.prototype = Object.create(superCtor.prototype, { - constructor: { - value: ctor, - enumerable: false, - writable: true, - configurable: true - } - }) - } - }; -} else { - // old school shim for old browsers - module.exports = function inherits(ctor, superCtor) { - if (superCtor) { - ctor.super_ = superCtor - var TempCtor = function () {} - TempCtor.prototype = superCtor.prototype - ctor.prototype = new TempCtor() - ctor.prototype.constructor = ctor - } - } -} - - -/***/ }), - -/***/ 71947: -/***/ ((module) => { - -"use strict"; - - -const codes = {}; - -function createErrorType(code, message, Base) { - if (!Base) { - Base = Error - } - - function getMessage (arg1, arg2, arg3) { - if (typeof message === 'string') { - return message - } else { - return message(arg1, arg2, arg3) - } - } - - class NodeError extends Base { - constructor (arg1, arg2, arg3) { - super(getMessage(arg1, arg2, arg3)); - } - } - - NodeError.prototype.name = Base.name; - NodeError.prototype.code = code; - - codes[code] = NodeError; -} - -// https://github.com/nodejs/node/blob/v10.8.0/lib/internal/errors.js -function oneOf(expected, thing) { - if (Array.isArray(expected)) { - const len = expected.length; - expected = expected.map((i) => String(i)); - if (len > 2) { - return `one of ${thing} ${expected.slice(0, len - 1).join(', ')}, or ` + - expected[len - 1]; - } else if (len === 2) { - return `one of ${thing} ${expected[0]} or ${expected[1]}`; - } else { - return `of ${thing} ${expected[0]}`; - } - } else { - return `of ${thing} ${String(expected)}`; - } -} - -// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/startsWith -function startsWith(str, search, pos) { - return str.substr(!pos || pos < 0 ? 0 : +pos, search.length) === search; -} - -// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/endsWith -function endsWith(str, search, this_len) { - if (this_len === undefined || this_len > str.length) { - this_len = str.length; - } - return str.substring(this_len - search.length, this_len) === search; -} - -// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/includes -function includes(str, search, start) { - if (typeof start !== 'number') { - start = 0; - } - - if (start + search.length > str.length) { - return false; - } else { - return str.indexOf(search, start) !== -1; - } -} - -createErrorType('ERR_INVALID_OPT_VALUE', function (name, value) { - return 'The value "' + value + '" is invalid for option "' + name + '"' -}, TypeError); -createErrorType('ERR_INVALID_ARG_TYPE', function (name, expected, actual) { - // determiner: 'must be' or 'must not be' - let determiner; - if (typeof expected === 'string' && startsWith(expected, 'not ')) { - determiner = 'must not be'; - expected = expected.replace(/^not /, ''); - } else { - determiner = 'must be'; - } - - let msg; - if (endsWith(name, ' argument')) { - // For cases like 'first argument' - msg = `The ${name} ${determiner} ${oneOf(expected, 'type')}`; - } else { - const type = includes(name, '.') ? 'property' : 'argument'; - msg = `The "${name}" ${type} ${determiner} ${oneOf(expected, 'type')}`; - } - - msg += `. Received type ${typeof actual}`; - return msg; -}, TypeError); -createErrorType('ERR_STREAM_PUSH_AFTER_EOF', 'stream.push() after EOF'); -createErrorType('ERR_METHOD_NOT_IMPLEMENTED', function (name) { - return 'The ' + name + ' method is not implemented' -}); -createErrorType('ERR_STREAM_PREMATURE_CLOSE', 'Premature close'); -createErrorType('ERR_STREAM_DESTROYED', function (name) { - return 'Cannot call ' + name + ' after a stream was destroyed'; -}); -createErrorType('ERR_MULTIPLE_CALLBACK', 'Callback called multiple times'); -createErrorType('ERR_STREAM_CANNOT_PIPE', 'Cannot pipe, not readable'); -createErrorType('ERR_STREAM_WRITE_AFTER_END', 'write after end'); -createErrorType('ERR_STREAM_NULL_VALUES', 'May not write null values to stream', TypeError); -createErrorType('ERR_UNKNOWN_ENCODING', function (arg) { - return 'Unknown encoding: ' + arg -}, TypeError); -createErrorType('ERR_STREAM_UNSHIFT_AFTER_END_EVENT', 'stream.unshift() after end event'); - -module.exports.q = codes; - - -/***/ }), - -/***/ 18084: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. -// a duplex stream is just a stream that is both readable and writable. -// Since JS doesn't have multiple prototypal inheritance, this class -// prototypally inherits from Readable, and then parasitically from -// Writable. - -/**/ - -var objectKeys = Object.keys || function (obj) { - var keys = []; - - for (var key in obj) { - keys.push(key); - } - - return keys; -}; -/**/ - - -module.exports = Duplex; - -var Readable = __webpack_require__(11864); - -var Writable = __webpack_require__(92042); - -__webpack_require__(94835)(Duplex, Readable); - -{ - // Allow the keys array to be GC'ed. - var keys = objectKeys(Writable.prototype); - - for (var v = 0; v < keys.length; v++) { - var method = keys[v]; - if (!Duplex.prototype[method]) Duplex.prototype[method] = Writable.prototype[method]; - } -} - -function Duplex(options) { - if (!(this instanceof Duplex)) return new Duplex(options); - Readable.call(this, options); - Writable.call(this, options); - this.allowHalfOpen = true; - - if (options) { - if (options.readable === false) this.readable = false; - if (options.writable === false) this.writable = false; - - if (options.allowHalfOpen === false) { - this.allowHalfOpen = false; - this.once('end', onend); - } - } -} - -Object.defineProperty(Duplex.prototype, 'writableHighWaterMark', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState.highWaterMark; - } -}); -Object.defineProperty(Duplex.prototype, 'writableBuffer', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState && this._writableState.getBuffer(); - } -}); -Object.defineProperty(Duplex.prototype, 'writableLength', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState.length; - } -}); // the no-half-open enforcer - -function onend() { - // If the writable side ended, then we're ok. - if (this._writableState.ended) return; // no more data can be written. - // But allow more writes to happen in this tick. - - process.nextTick(onEndNT, this); -} - -function onEndNT(self) { - self.end(); -} - -Object.defineProperty(Duplex.prototype, 'destroyed', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - if (this._readableState === undefined || this._writableState === undefined) { - return false; - } - - return this._readableState.destroyed && this._writableState.destroyed; - }, - set: function set(value) { - // we ignore the value if the stream - // has not been initialized yet - if (this._readableState === undefined || this._writableState === undefined) { - return; - } // backward compatibility, the user is explicitly - // managing destroyed - - - this._readableState.destroyed = value; - this._writableState.destroyed = value; - } -}); - -/***/ }), - -/***/ 11798: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. -// a passthrough stream. -// basically just the most minimal sort of Transform stream. -// Every written chunk gets output as-is. - - -module.exports = PassThrough; - -var Transform = __webpack_require__(57173); - -__webpack_require__(94835)(PassThrough, Transform); - -function PassThrough(options) { - if (!(this instanceof PassThrough)) return new PassThrough(options); - Transform.call(this, options); -} - -PassThrough.prototype._transform = function (chunk, encoding, cb) { - cb(null, chunk); -}; - -/***/ }), - -/***/ 11864: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. - - -module.exports = Readable; -/**/ - -var Duplex; -/**/ - -Readable.ReadableState = ReadableState; -/**/ - -var EE = __webpack_require__(28614).EventEmitter; - -var EElistenerCount = function EElistenerCount(emitter, type) { - return emitter.listeners(type).length; -}; -/**/ - -/**/ - - -var Stream = __webpack_require__(47640); -/**/ - - -var Buffer = __webpack_require__(64293).Buffer; - -var OurUint8Array = global.Uint8Array || function () {}; - -function _uint8ArrayToBuffer(chunk) { - return Buffer.from(chunk); -} - -function _isUint8Array(obj) { - return Buffer.isBuffer(obj) || obj instanceof OurUint8Array; -} -/**/ - - -var debugUtil = __webpack_require__(31669); - -var debug; - -if (debugUtil && debugUtil.debuglog) { - debug = debugUtil.debuglog('stream'); -} else { - debug = function debug() {}; -} -/**/ - - -var BufferList = __webpack_require__(38568); - -var destroyImpl = __webpack_require__(22126); - -var _require = __webpack_require__(14286), - getHighWaterMark = _require.getHighWaterMark; - -var _require$codes = __webpack_require__(71947)/* .codes */ .q, - ERR_INVALID_ARG_TYPE = _require$codes.ERR_INVALID_ARG_TYPE, - ERR_STREAM_PUSH_AFTER_EOF = _require$codes.ERR_STREAM_PUSH_AFTER_EOF, - ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED, - ERR_STREAM_UNSHIFT_AFTER_END_EVENT = _require$codes.ERR_STREAM_UNSHIFT_AFTER_END_EVENT; // Lazy loaded to improve the startup performance. - - -var StringDecoder; -var createReadableStreamAsyncIterator; -var from; - -__webpack_require__(94835)(Readable, Stream); - -var errorOrDestroy = destroyImpl.errorOrDestroy; -var kProxyEvents = ['error', 'close', 'destroy', 'pause', 'resume']; - -function prependListener(emitter, event, fn) { - // Sadly this is not cacheable as some libraries bundle their own - // event emitter implementation with them. - if (typeof emitter.prependListener === 'function') return emitter.prependListener(event, fn); // This is a hack to make sure that our error handler is attached before any - // userland ones. NEVER DO THIS. This is here only because this code needs - // to continue to work with older versions of Node.js that do not include - // the prependListener() method. The goal is to eventually remove this hack. - - if (!emitter._events || !emitter._events[event]) emitter.on(event, fn);else if (Array.isArray(emitter._events[event])) emitter._events[event].unshift(fn);else emitter._events[event] = [fn, emitter._events[event]]; -} - -function ReadableState(options, stream, isDuplex) { - Duplex = Duplex || __webpack_require__(18084); - options = options || {}; // Duplex streams are both readable and writable, but share - // the same options object. - // However, some cases require setting options to different - // values for the readable and the writable sides of the duplex stream. - // These options can be provided separately as readableXXX and writableXXX. - - if (typeof isDuplex !== 'boolean') isDuplex = stream instanceof Duplex; // object stream flag. Used to make read(n) ignore n and to - // make all the buffer merging and length checks go away - - this.objectMode = !!options.objectMode; - if (isDuplex) this.objectMode = this.objectMode || !!options.readableObjectMode; // the point at which it stops calling _read() to fill the buffer - // Note: 0 is a valid value, means "don't call _read preemptively ever" - - this.highWaterMark = getHighWaterMark(this, options, 'readableHighWaterMark', isDuplex); // A linked list is used to store data chunks instead of an array because the - // linked list can remove elements from the beginning faster than - // array.shift() - - this.buffer = new BufferList(); - this.length = 0; - this.pipes = null; - this.pipesCount = 0; - this.flowing = null; - this.ended = false; - this.endEmitted = false; - this.reading = false; // a flag to be able to tell if the event 'readable'/'data' is emitted - // immediately, or on a later tick. We set this to true at first, because - // any actions that shouldn't happen until "later" should generally also - // not happen before the first read call. - - this.sync = true; // whenever we return null, then we set a flag to say - // that we're awaiting a 'readable' event emission. - - this.needReadable = false; - this.emittedReadable = false; - this.readableListening = false; - this.resumeScheduled = false; - this.paused = true; // Should close be emitted on destroy. Defaults to true. - - this.emitClose = options.emitClose !== false; // Should .destroy() be called after 'end' (and potentially 'finish') - - this.autoDestroy = !!options.autoDestroy; // has it been destroyed - - this.destroyed = false; // Crypto is kind of old and crusty. Historically, its default string - // encoding is 'binary' so we have to make this configurable. - // Everything else in the universe uses 'utf8', though. - - this.defaultEncoding = options.defaultEncoding || 'utf8'; // the number of writers that are awaiting a drain event in .pipe()s - - this.awaitDrain = 0; // if true, a maybeReadMore has been scheduled - - this.readingMore = false; - this.decoder = null; - this.encoding = null; - - if (options.encoding) { - if (!StringDecoder) StringDecoder = __webpack_require__(84882)/* .StringDecoder */ .s; - this.decoder = new StringDecoder(options.encoding); - this.encoding = options.encoding; - } -} - -function Readable(options) { - Duplex = Duplex || __webpack_require__(18084); - if (!(this instanceof Readable)) return new Readable(options); // Checking for a Stream.Duplex instance is faster here instead of inside - // the ReadableState constructor, at least with V8 6.5 - - var isDuplex = this instanceof Duplex; - this._readableState = new ReadableState(options, this, isDuplex); // legacy - - this.readable = true; - - if (options) { - if (typeof options.read === 'function') this._read = options.read; - if (typeof options.destroy === 'function') this._destroy = options.destroy; - } - - Stream.call(this); -} - -Object.defineProperty(Readable.prototype, 'destroyed', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - if (this._readableState === undefined) { - return false; - } - - return this._readableState.destroyed; - }, - set: function set(value) { - // we ignore the value if the stream - // has not been initialized yet - if (!this._readableState) { - return; - } // backward compatibility, the user is explicitly - // managing destroyed - - - this._readableState.destroyed = value; - } -}); -Readable.prototype.destroy = destroyImpl.destroy; -Readable.prototype._undestroy = destroyImpl.undestroy; - -Readable.prototype._destroy = function (err, cb) { - cb(err); -}; // Manually shove something into the read() buffer. -// This returns true if the highWaterMark has not been hit yet, -// similar to how Writable.write() returns true if you should -// write() some more. - - -Readable.prototype.push = function (chunk, encoding) { - var state = this._readableState; - var skipChunkCheck; - - if (!state.objectMode) { - if (typeof chunk === 'string') { - encoding = encoding || state.defaultEncoding; - - if (encoding !== state.encoding) { - chunk = Buffer.from(chunk, encoding); - encoding = ''; - } - - skipChunkCheck = true; - } - } else { - skipChunkCheck = true; - } - - return readableAddChunk(this, chunk, encoding, false, skipChunkCheck); -}; // Unshift should *always* be something directly out of read() - - -Readable.prototype.unshift = function (chunk) { - return readableAddChunk(this, chunk, null, true, false); -}; - -function readableAddChunk(stream, chunk, encoding, addToFront, skipChunkCheck) { - debug('readableAddChunk', chunk); - var state = stream._readableState; - - if (chunk === null) { - state.reading = false; - onEofChunk(stream, state); - } else { - var er; - if (!skipChunkCheck) er = chunkInvalid(state, chunk); - - if (er) { - errorOrDestroy(stream, er); - } else if (state.objectMode || chunk && chunk.length > 0) { - if (typeof chunk !== 'string' && !state.objectMode && Object.getPrototypeOf(chunk) !== Buffer.prototype) { - chunk = _uint8ArrayToBuffer(chunk); - } - - if (addToFront) { - if (state.endEmitted) errorOrDestroy(stream, new ERR_STREAM_UNSHIFT_AFTER_END_EVENT());else addChunk(stream, state, chunk, true); - } else if (state.ended) { - errorOrDestroy(stream, new ERR_STREAM_PUSH_AFTER_EOF()); - } else if (state.destroyed) { - return false; - } else { - state.reading = false; - - if (state.decoder && !encoding) { - chunk = state.decoder.write(chunk); - if (state.objectMode || chunk.length !== 0) addChunk(stream, state, chunk, false);else maybeReadMore(stream, state); - } else { - addChunk(stream, state, chunk, false); - } - } - } else if (!addToFront) { - state.reading = false; - maybeReadMore(stream, state); - } - } // We can push more data if we are below the highWaterMark. - // Also, if we have no data yet, we can stand some more bytes. - // This is to work around cases where hwm=0, such as the repl. - - - return !state.ended && (state.length < state.highWaterMark || state.length === 0); -} - -function addChunk(stream, state, chunk, addToFront) { - if (state.flowing && state.length === 0 && !state.sync) { - state.awaitDrain = 0; - stream.emit('data', chunk); - } else { - // update the buffer info. - state.length += state.objectMode ? 1 : chunk.length; - if (addToFront) state.buffer.unshift(chunk);else state.buffer.push(chunk); - if (state.needReadable) emitReadable(stream); - } - - maybeReadMore(stream, state); -} - -function chunkInvalid(state, chunk) { - var er; - - if (!_isUint8Array(chunk) && typeof chunk !== 'string' && chunk !== undefined && !state.objectMode) { - er = new ERR_INVALID_ARG_TYPE('chunk', ['string', 'Buffer', 'Uint8Array'], chunk); - } - - return er; -} - -Readable.prototype.isPaused = function () { - return this._readableState.flowing === false; -}; // backwards compatibility. - - -Readable.prototype.setEncoding = function (enc) { - if (!StringDecoder) StringDecoder = __webpack_require__(84882)/* .StringDecoder */ .s; - var decoder = new StringDecoder(enc); - this._readableState.decoder = decoder; // If setEncoding(null), decoder.encoding equals utf8 - - this._readableState.encoding = this._readableState.decoder.encoding; // Iterate over current buffer to convert already stored Buffers: - - var p = this._readableState.buffer.head; - var content = ''; - - while (p !== null) { - content += decoder.write(p.data); - p = p.next; - } - - this._readableState.buffer.clear(); - - if (content !== '') this._readableState.buffer.push(content); - this._readableState.length = content.length; - return this; -}; // Don't raise the hwm > 1GB - - -var MAX_HWM = 0x40000000; - -function computeNewHighWaterMark(n) { - if (n >= MAX_HWM) { - // TODO(ronag): Throw ERR_VALUE_OUT_OF_RANGE. - n = MAX_HWM; - } else { - // Get the next highest power of 2 to prevent increasing hwm excessively in - // tiny amounts - n--; - n |= n >>> 1; - n |= n >>> 2; - n |= n >>> 4; - n |= n >>> 8; - n |= n >>> 16; - n++; - } - - return n; -} // This function is designed to be inlinable, so please take care when making -// changes to the function body. - - -function howMuchToRead(n, state) { - if (n <= 0 || state.length === 0 && state.ended) return 0; - if (state.objectMode) return 1; - - if (n !== n) { - // Only flow one buffer at a time - if (state.flowing && state.length) return state.buffer.head.data.length;else return state.length; - } // If we're asking for more than the current hwm, then raise the hwm. - - - if (n > state.highWaterMark) state.highWaterMark = computeNewHighWaterMark(n); - if (n <= state.length) return n; // Don't have enough - - if (!state.ended) { - state.needReadable = true; - return 0; - } - - return state.length; -} // you can override either this method, or the async _read(n) below. - - -Readable.prototype.read = function (n) { - debug('read', n); - n = parseInt(n, 10); - var state = this._readableState; - var nOrig = n; - if (n !== 0) state.emittedReadable = false; // if we're doing read(0) to trigger a readable event, but we - // already have a bunch of data in the buffer, then just trigger - // the 'readable' event and move on. - - if (n === 0 && state.needReadable && ((state.highWaterMark !== 0 ? state.length >= state.highWaterMark : state.length > 0) || state.ended)) { - debug('read: emitReadable', state.length, state.ended); - if (state.length === 0 && state.ended) endReadable(this);else emitReadable(this); - return null; - } - - n = howMuchToRead(n, state); // if we've ended, and we're now clear, then finish it up. - - if (n === 0 && state.ended) { - if (state.length === 0) endReadable(this); - return null; - } // All the actual chunk generation logic needs to be - // *below* the call to _read. The reason is that in certain - // synthetic stream cases, such as passthrough streams, _read - // may be a completely synchronous operation which may change - // the state of the read buffer, providing enough data when - // before there was *not* enough. - // - // So, the steps are: - // 1. Figure out what the state of things will be after we do - // a read from the buffer. - // - // 2. If that resulting state will trigger a _read, then call _read. - // Note that this may be asynchronous, or synchronous. Yes, it is - // deeply ugly to write APIs this way, but that still doesn't mean - // that the Readable class should behave improperly, as streams are - // designed to be sync/async agnostic. - // Take note if the _read call is sync or async (ie, if the read call - // has returned yet), so that we know whether or not it's safe to emit - // 'readable' etc. - // - // 3. Actually pull the requested chunks out of the buffer and return. - // if we need a readable event, then we need to do some reading. - - - var doRead = state.needReadable; - debug('need readable', doRead); // if we currently have less than the highWaterMark, then also read some - - if (state.length === 0 || state.length - n < state.highWaterMark) { - doRead = true; - debug('length less than watermark', doRead); - } // however, if we've ended, then there's no point, and if we're already - // reading, then it's unnecessary. - - - if (state.ended || state.reading) { - doRead = false; - debug('reading or ended', doRead); - } else if (doRead) { - debug('do read'); - state.reading = true; - state.sync = true; // if the length is currently zero, then we *need* a readable event. - - if (state.length === 0) state.needReadable = true; // call internal read method - - this._read(state.highWaterMark); - - state.sync = false; // If _read pushed data synchronously, then `reading` will be false, - // and we need to re-evaluate how much data we can return to the user. - - if (!state.reading) n = howMuchToRead(nOrig, state); - } - - var ret; - if (n > 0) ret = fromList(n, state);else ret = null; - - if (ret === null) { - state.needReadable = state.length <= state.highWaterMark; - n = 0; - } else { - state.length -= n; - state.awaitDrain = 0; - } - - if (state.length === 0) { - // If we have nothing in the buffer, then we want to know - // as soon as we *do* get something into the buffer. - if (!state.ended) state.needReadable = true; // If we tried to read() past the EOF, then emit end on the next tick. - - if (nOrig !== n && state.ended) endReadable(this); - } - - if (ret !== null) this.emit('data', ret); - return ret; -}; - -function onEofChunk(stream, state) { - debug('onEofChunk'); - if (state.ended) return; - - if (state.decoder) { - var chunk = state.decoder.end(); - - if (chunk && chunk.length) { - state.buffer.push(chunk); - state.length += state.objectMode ? 1 : chunk.length; - } - } - - state.ended = true; - - if (state.sync) { - // if we are sync, wait until next tick to emit the data. - // Otherwise we risk emitting data in the flow() - // the readable code triggers during a read() call - emitReadable(stream); - } else { - // emit 'readable' now to make sure it gets picked up. - state.needReadable = false; - - if (!state.emittedReadable) { - state.emittedReadable = true; - emitReadable_(stream); - } - } -} // Don't emit readable right away in sync mode, because this can trigger -// another read() call => stack overflow. This way, it might trigger -// a nextTick recursion warning, but that's not so bad. - - -function emitReadable(stream) { - var state = stream._readableState; - debug('emitReadable', state.needReadable, state.emittedReadable); - state.needReadable = false; - - if (!state.emittedReadable) { - debug('emitReadable', state.flowing); - state.emittedReadable = true; - process.nextTick(emitReadable_, stream); - } -} - -function emitReadable_(stream) { - var state = stream._readableState; - debug('emitReadable_', state.destroyed, state.length, state.ended); - - if (!state.destroyed && (state.length || state.ended)) { - stream.emit('readable'); - state.emittedReadable = false; - } // The stream needs another readable event if - // 1. It is not flowing, as the flow mechanism will take - // care of it. - // 2. It is not ended. - // 3. It is below the highWaterMark, so we can schedule - // another readable later. - - - state.needReadable = !state.flowing && !state.ended && state.length <= state.highWaterMark; - flow(stream); -} // at this point, the user has presumably seen the 'readable' event, -// and called read() to consume some data. that may have triggered -// in turn another _read(n) call, in which case reading = true if -// it's in progress. -// However, if we're not ended, or reading, and the length < hwm, -// then go ahead and try to read some more preemptively. - - -function maybeReadMore(stream, state) { - if (!state.readingMore) { - state.readingMore = true; - process.nextTick(maybeReadMore_, stream, state); - } -} - -function maybeReadMore_(stream, state) { - // Attempt to read more data if we should. - // - // The conditions for reading more data are (one of): - // - Not enough data buffered (state.length < state.highWaterMark). The loop - // is responsible for filling the buffer with enough data if such data - // is available. If highWaterMark is 0 and we are not in the flowing mode - // we should _not_ attempt to buffer any extra data. We'll get more data - // when the stream consumer calls read() instead. - // - No data in the buffer, and the stream is in flowing mode. In this mode - // the loop below is responsible for ensuring read() is called. Failing to - // call read here would abort the flow and there's no other mechanism for - // continuing the flow if the stream consumer has just subscribed to the - // 'data' event. - // - // In addition to the above conditions to keep reading data, the following - // conditions prevent the data from being read: - // - The stream has ended (state.ended). - // - There is already a pending 'read' operation (state.reading). This is a - // case where the the stream has called the implementation defined _read() - // method, but they are processing the call asynchronously and have _not_ - // called push() with new data. In this case we skip performing more - // read()s. The execution ends in this method again after the _read() ends - // up calling push() with more data. - while (!state.reading && !state.ended && (state.length < state.highWaterMark || state.flowing && state.length === 0)) { - var len = state.length; - debug('maybeReadMore read 0'); - stream.read(0); - if (len === state.length) // didn't get any data, stop spinning. - break; - } - - state.readingMore = false; -} // abstract method. to be overridden in specific implementation classes. -// call cb(er, data) where data is <= n in length. -// for virtual (non-string, non-buffer) streams, "length" is somewhat -// arbitrary, and perhaps not very meaningful. - - -Readable.prototype._read = function (n) { - errorOrDestroy(this, new ERR_METHOD_NOT_IMPLEMENTED('_read()')); -}; - -Readable.prototype.pipe = function (dest, pipeOpts) { - var src = this; - var state = this._readableState; - - switch (state.pipesCount) { - case 0: - state.pipes = dest; - break; - - case 1: - state.pipes = [state.pipes, dest]; - break; - - default: - state.pipes.push(dest); - break; - } - - state.pipesCount += 1; - debug('pipe count=%d opts=%j', state.pipesCount, pipeOpts); - var doEnd = (!pipeOpts || pipeOpts.end !== false) && dest !== process.stdout && dest !== process.stderr; - var endFn = doEnd ? onend : unpipe; - if (state.endEmitted) process.nextTick(endFn);else src.once('end', endFn); - dest.on('unpipe', onunpipe); - - function onunpipe(readable, unpipeInfo) { - debug('onunpipe'); - - if (readable === src) { - if (unpipeInfo && unpipeInfo.hasUnpiped === false) { - unpipeInfo.hasUnpiped = true; - cleanup(); - } - } - } - - function onend() { - debug('onend'); - dest.end(); - } // when the dest drains, it reduces the awaitDrain counter - // on the source. This would be more elegant with a .once() - // handler in flow(), but adding and removing repeatedly is - // too slow. - - - var ondrain = pipeOnDrain(src); - dest.on('drain', ondrain); - var cleanedUp = false; - - function cleanup() { - debug('cleanup'); // cleanup event handlers once the pipe is broken - - dest.removeListener('close', onclose); - dest.removeListener('finish', onfinish); - dest.removeListener('drain', ondrain); - dest.removeListener('error', onerror); - dest.removeListener('unpipe', onunpipe); - src.removeListener('end', onend); - src.removeListener('end', unpipe); - src.removeListener('data', ondata); - cleanedUp = true; // if the reader is waiting for a drain event from this - // specific writer, then it would cause it to never start - // flowing again. - // So, if this is awaiting a drain, then we just call it now. - // If we don't know, then assume that we are waiting for one. - - if (state.awaitDrain && (!dest._writableState || dest._writableState.needDrain)) ondrain(); - } - - src.on('data', ondata); - - function ondata(chunk) { - debug('ondata'); - var ret = dest.write(chunk); - debug('dest.write', ret); - - if (ret === false) { - // If the user unpiped during `dest.write()`, it is possible - // to get stuck in a permanently paused state if that write - // also returned false. - // => Check whether `dest` is still a piping destination. - if ((state.pipesCount === 1 && state.pipes === dest || state.pipesCount > 1 && indexOf(state.pipes, dest) !== -1) && !cleanedUp) { - debug('false write response, pause', state.awaitDrain); - state.awaitDrain++; - } - - src.pause(); - } - } // if the dest has an error, then stop piping into it. - // however, don't suppress the throwing behavior for this. - - - function onerror(er) { - debug('onerror', er); - unpipe(); - dest.removeListener('error', onerror); - if (EElistenerCount(dest, 'error') === 0) errorOrDestroy(dest, er); - } // Make sure our error handler is attached before userland ones. - - - prependListener(dest, 'error', onerror); // Both close and finish should trigger unpipe, but only once. - - function onclose() { - dest.removeListener('finish', onfinish); - unpipe(); - } - - dest.once('close', onclose); - - function onfinish() { - debug('onfinish'); - dest.removeListener('close', onclose); - unpipe(); - } - - dest.once('finish', onfinish); - - function unpipe() { - debug('unpipe'); - src.unpipe(dest); - } // tell the dest that it's being piped to - - - dest.emit('pipe', src); // start the flow if it hasn't been started already. - - if (!state.flowing) { - debug('pipe resume'); - src.resume(); - } - - return dest; -}; - -function pipeOnDrain(src) { - return function pipeOnDrainFunctionResult() { - var state = src._readableState; - debug('pipeOnDrain', state.awaitDrain); - if (state.awaitDrain) state.awaitDrain--; - - if (state.awaitDrain === 0 && EElistenerCount(src, 'data')) { - state.flowing = true; - flow(src); - } - }; -} - -Readable.prototype.unpipe = function (dest) { - var state = this._readableState; - var unpipeInfo = { - hasUnpiped: false - }; // if we're not piping anywhere, then do nothing. - - if (state.pipesCount === 0) return this; // just one destination. most common case. - - if (state.pipesCount === 1) { - // passed in one, but it's not the right one. - if (dest && dest !== state.pipes) return this; - if (!dest) dest = state.pipes; // got a match. - - state.pipes = null; - state.pipesCount = 0; - state.flowing = false; - if (dest) dest.emit('unpipe', this, unpipeInfo); - return this; - } // slow case. multiple pipe destinations. - - - if (!dest) { - // remove all. - var dests = state.pipes; - var len = state.pipesCount; - state.pipes = null; - state.pipesCount = 0; - state.flowing = false; - - for (var i = 0; i < len; i++) { - dests[i].emit('unpipe', this, { - hasUnpiped: false - }); - } - - return this; - } // try to find the right one. - - - var index = indexOf(state.pipes, dest); - if (index === -1) return this; - state.pipes.splice(index, 1); - state.pipesCount -= 1; - if (state.pipesCount === 1) state.pipes = state.pipes[0]; - dest.emit('unpipe', this, unpipeInfo); - return this; -}; // set up data events if they are asked for -// Ensure readable listeners eventually get something - - -Readable.prototype.on = function (ev, fn) { - var res = Stream.prototype.on.call(this, ev, fn); - var state = this._readableState; - - if (ev === 'data') { - // update readableListening so that resume() may be a no-op - // a few lines down. This is needed to support once('readable'). - state.readableListening = this.listenerCount('readable') > 0; // Try start flowing on next tick if stream isn't explicitly paused - - if (state.flowing !== false) this.resume(); - } else if (ev === 'readable') { - if (!state.endEmitted && !state.readableListening) { - state.readableListening = state.needReadable = true; - state.flowing = false; - state.emittedReadable = false; - debug('on readable', state.length, state.reading); - - if (state.length) { - emitReadable(this); - } else if (!state.reading) { - process.nextTick(nReadingNextTick, this); - } - } - } - - return res; -}; - -Readable.prototype.addListener = Readable.prototype.on; - -Readable.prototype.removeListener = function (ev, fn) { - var res = Stream.prototype.removeListener.call(this, ev, fn); - - if (ev === 'readable') { - // We need to check if there is someone still listening to - // readable and reset the state. However this needs to happen - // after readable has been emitted but before I/O (nextTick) to - // support once('readable', fn) cycles. This means that calling - // resume within the same tick will have no - // effect. - process.nextTick(updateReadableListening, this); - } - - return res; -}; - -Readable.prototype.removeAllListeners = function (ev) { - var res = Stream.prototype.removeAllListeners.apply(this, arguments); - - if (ev === 'readable' || ev === undefined) { - // We need to check if there is someone still listening to - // readable and reset the state. However this needs to happen - // after readable has been emitted but before I/O (nextTick) to - // support once('readable', fn) cycles. This means that calling - // resume within the same tick will have no - // effect. - process.nextTick(updateReadableListening, this); - } - - return res; -}; - -function updateReadableListening(self) { - var state = self._readableState; - state.readableListening = self.listenerCount('readable') > 0; - - if (state.resumeScheduled && !state.paused) { - // flowing needs to be set to true now, otherwise - // the upcoming resume will not flow. - state.flowing = true; // crude way to check if we should resume - } else if (self.listenerCount('data') > 0) { - self.resume(); - } -} - -function nReadingNextTick(self) { - debug('readable nexttick read 0'); - self.read(0); -} // pause() and resume() are remnants of the legacy readable stream API -// If the user uses them, then switch into old mode. - - -Readable.prototype.resume = function () { - var state = this._readableState; - - if (!state.flowing) { - debug('resume'); // we flow only if there is no one listening - // for readable, but we still have to call - // resume() - - state.flowing = !state.readableListening; - resume(this, state); - } - - state.paused = false; - return this; -}; - -function resume(stream, state) { - if (!state.resumeScheduled) { - state.resumeScheduled = true; - process.nextTick(resume_, stream, state); - } -} - -function resume_(stream, state) { - debug('resume', state.reading); - - if (!state.reading) { - stream.read(0); - } - - state.resumeScheduled = false; - stream.emit('resume'); - flow(stream); - if (state.flowing && !state.reading) stream.read(0); -} - -Readable.prototype.pause = function () { - debug('call pause flowing=%j', this._readableState.flowing); - - if (this._readableState.flowing !== false) { - debug('pause'); - this._readableState.flowing = false; - this.emit('pause'); - } - - this._readableState.paused = true; - return this; -}; - -function flow(stream) { - var state = stream._readableState; - debug('flow', state.flowing); - - while (state.flowing && stream.read() !== null) { - ; - } -} // wrap an old-style stream as the async data source. -// This is *not* part of the readable stream interface. -// It is an ugly unfortunate mess of history. - - -Readable.prototype.wrap = function (stream) { - var _this = this; - - var state = this._readableState; - var paused = false; - stream.on('end', function () { - debug('wrapped end'); - - if (state.decoder && !state.ended) { - var chunk = state.decoder.end(); - if (chunk && chunk.length) _this.push(chunk); - } - - _this.push(null); - }); - stream.on('data', function (chunk) { - debug('wrapped data'); - if (state.decoder) chunk = state.decoder.write(chunk); // don't skip over falsy values in objectMode - - if (state.objectMode && (chunk === null || chunk === undefined)) return;else if (!state.objectMode && (!chunk || !chunk.length)) return; - - var ret = _this.push(chunk); - - if (!ret) { - paused = true; - stream.pause(); - } - }); // proxy all the other methods. - // important when wrapping filters and duplexes. - - for (var i in stream) { - if (this[i] === undefined && typeof stream[i] === 'function') { - this[i] = function methodWrap(method) { - return function methodWrapReturnFunction() { - return stream[method].apply(stream, arguments); - }; - }(i); - } - } // proxy certain important events. - - - for (var n = 0; n < kProxyEvents.length; n++) { - stream.on(kProxyEvents[n], this.emit.bind(this, kProxyEvents[n])); - } // when we try to consume some more bytes, simply unpause the - // underlying stream. - - - this._read = function (n) { - debug('wrapped _read', n); - - if (paused) { - paused = false; - stream.resume(); - } - }; - - return this; -}; - -if (typeof Symbol === 'function') { - Readable.prototype[Symbol.asyncIterator] = function () { - if (createReadableStreamAsyncIterator === undefined) { - createReadableStreamAsyncIterator = __webpack_require__(37090); - } - - return createReadableStreamAsyncIterator(this); - }; -} - -Object.defineProperty(Readable.prototype, 'readableHighWaterMark', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._readableState.highWaterMark; - } -}); -Object.defineProperty(Readable.prototype, 'readableBuffer', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._readableState && this._readableState.buffer; - } -}); -Object.defineProperty(Readable.prototype, 'readableFlowing', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._readableState.flowing; - }, - set: function set(state) { - if (this._readableState) { - this._readableState.flowing = state; - } - } -}); // exposed for testing purposes only. - -Readable._fromList = fromList; -Object.defineProperty(Readable.prototype, 'readableLength', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._readableState.length; - } -}); // Pluck off n bytes from an array of buffers. -// Length is the combined lengths of all the buffers in the list. -// This function is designed to be inlinable, so please take care when making -// changes to the function body. - -function fromList(n, state) { - // nothing buffered - if (state.length === 0) return null; - var ret; - if (state.objectMode) ret = state.buffer.shift();else if (!n || n >= state.length) { - // read it all, truncate the list - if (state.decoder) ret = state.buffer.join('');else if (state.buffer.length === 1) ret = state.buffer.first();else ret = state.buffer.concat(state.length); - state.buffer.clear(); - } else { - // read part of list - ret = state.buffer.consume(n, state.decoder); - } - return ret; -} - -function endReadable(stream) { - var state = stream._readableState; - debug('endReadable', state.endEmitted); - - if (!state.endEmitted) { - state.ended = true; - process.nextTick(endReadableNT, state, stream); - } -} - -function endReadableNT(state, stream) { - debug('endReadableNT', state.endEmitted, state.length); // Check that we didn't get one last unshift. - - if (!state.endEmitted && state.length === 0) { - state.endEmitted = true; - stream.readable = false; - stream.emit('end'); - - if (state.autoDestroy) { - // In case of duplex streams we need a way to detect - // if the writable side is ready for autoDestroy as well - var wState = stream._writableState; - - if (!wState || wState.autoDestroy && wState.finished) { - stream.destroy(); - } - } - } -} - -if (typeof Symbol === 'function') { - Readable.from = function (iterable, opts) { - if (from === undefined) { - from = __webpack_require__(97754); - } - - return from(Readable, iterable, opts); - }; -} - -function indexOf(xs, x) { - for (var i = 0, l = xs.length; i < l; i++) { - if (xs[i] === x) return i; - } - - return -1; -} - -/***/ }), - -/***/ 57173: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. -// a transform stream is a readable/writable stream where you do -// something with the data. Sometimes it's called a "filter", -// but that's not a great name for it, since that implies a thing where -// some bits pass through, and others are simply ignored. (That would -// be a valid example of a transform, of course.) -// -// While the output is causally related to the input, it's not a -// necessarily symmetric or synchronous transformation. For example, -// a zlib stream might take multiple plain-text writes(), and then -// emit a single compressed chunk some time in the future. -// -// Here's how this works: -// -// The Transform stream has all the aspects of the readable and writable -// stream classes. When you write(chunk), that calls _write(chunk,cb) -// internally, and returns false if there's a lot of pending writes -// buffered up. When you call read(), that calls _read(n) until -// there's enough pending readable data buffered up. -// -// In a transform stream, the written data is placed in a buffer. When -// _read(n) is called, it transforms the queued up data, calling the -// buffered _write cb's as it consumes chunks. If consuming a single -// written chunk would result in multiple output chunks, then the first -// outputted bit calls the readcb, and subsequent chunks just go into -// the read buffer, and will cause it to emit 'readable' if necessary. -// -// This way, back-pressure is actually determined by the reading side, -// since _read has to be called to start processing a new chunk. However, -// a pathological inflate type of transform can cause excessive buffering -// here. For example, imagine a stream where every byte of input is -// interpreted as an integer from 0-255, and then results in that many -// bytes of output. Writing the 4 bytes {ff,ff,ff,ff} would result in -// 1kb of data being output. In this case, you could write a very small -// amount of input, and end up with a very large amount of output. In -// such a pathological inflating mechanism, there'd be no way to tell -// the system to stop doing the transform. A single 4MB write could -// cause the system to run out of memory. -// -// However, even in such a pathological case, only a single written chunk -// would be consumed, and then the rest would wait (un-transformed) until -// the results of the previous transformed chunk were consumed. - - -module.exports = Transform; - -var _require$codes = __webpack_require__(71947)/* .codes */ .q, - ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED, - ERR_MULTIPLE_CALLBACK = _require$codes.ERR_MULTIPLE_CALLBACK, - ERR_TRANSFORM_ALREADY_TRANSFORMING = _require$codes.ERR_TRANSFORM_ALREADY_TRANSFORMING, - ERR_TRANSFORM_WITH_LENGTH_0 = _require$codes.ERR_TRANSFORM_WITH_LENGTH_0; - -var Duplex = __webpack_require__(18084); - -__webpack_require__(94835)(Transform, Duplex); - -function afterTransform(er, data) { - var ts = this._transformState; - ts.transforming = false; - var cb = ts.writecb; - - if (cb === null) { - return this.emit('error', new ERR_MULTIPLE_CALLBACK()); - } - - ts.writechunk = null; - ts.writecb = null; - if (data != null) // single equals check for both `null` and `undefined` - this.push(data); - cb(er); - var rs = this._readableState; - rs.reading = false; - - if (rs.needReadable || rs.length < rs.highWaterMark) { - this._read(rs.highWaterMark); - } -} - -function Transform(options) { - if (!(this instanceof Transform)) return new Transform(options); - Duplex.call(this, options); - this._transformState = { - afterTransform: afterTransform.bind(this), - needTransform: false, - transforming: false, - writecb: null, - writechunk: null, - writeencoding: null - }; // start out asking for a readable event once data is transformed. - - this._readableState.needReadable = true; // we have implemented the _read method, and done the other things - // that Readable wants before the first _read call, so unset the - // sync guard flag. - - this._readableState.sync = false; - - if (options) { - if (typeof options.transform === 'function') this._transform = options.transform; - if (typeof options.flush === 'function') this._flush = options.flush; - } // When the writable side finishes, then flush out anything remaining. - - - this.on('prefinish', prefinish); -} - -function prefinish() { - var _this = this; - - if (typeof this._flush === 'function' && !this._readableState.destroyed) { - this._flush(function (er, data) { - done(_this, er, data); - }); - } else { - done(this, null, null); - } -} - -Transform.prototype.push = function (chunk, encoding) { - this._transformState.needTransform = false; - return Duplex.prototype.push.call(this, chunk, encoding); -}; // This is the part where you do stuff! -// override this function in implementation classes. -// 'chunk' is an input chunk. -// -// Call `push(newChunk)` to pass along transformed output -// to the readable side. You may call 'push' zero or more times. -// -// Call `cb(err)` when you are done with this chunk. If you pass -// an error, then that'll put the hurt on the whole operation. If you -// never call cb(), then you'll never get another chunk. - - -Transform.prototype._transform = function (chunk, encoding, cb) { - cb(new ERR_METHOD_NOT_IMPLEMENTED('_transform()')); -}; - -Transform.prototype._write = function (chunk, encoding, cb) { - var ts = this._transformState; - ts.writecb = cb; - ts.writechunk = chunk; - ts.writeencoding = encoding; - - if (!ts.transforming) { - var rs = this._readableState; - if (ts.needTransform || rs.needReadable || rs.length < rs.highWaterMark) this._read(rs.highWaterMark); - } -}; // Doesn't matter what the args are here. -// _transform does all the work. -// That we got here means that the readable side wants more data. - - -Transform.prototype._read = function (n) { - var ts = this._transformState; - - if (ts.writechunk !== null && !ts.transforming) { - ts.transforming = true; - - this._transform(ts.writechunk, ts.writeencoding, ts.afterTransform); - } else { - // mark that we need a transform, so that any data that comes in - // will get processed, now that we've asked for it. - ts.needTransform = true; - } -}; - -Transform.prototype._destroy = function (err, cb) { - Duplex.prototype._destroy.call(this, err, function (err2) { - cb(err2); - }); -}; - -function done(stream, er, data) { - if (er) return stream.emit('error', er); - if (data != null) // single equals check for both `null` and `undefined` - stream.push(data); // TODO(BridgeAR): Write a test for these two error cases - // if there's nothing in the write buffer, then that means - // that nothing more will ever be provided - - if (stream._writableState.length) throw new ERR_TRANSFORM_WITH_LENGTH_0(); - if (stream._transformState.transforming) throw new ERR_TRANSFORM_ALREADY_TRANSFORMING(); - return stream.push(null); -} - -/***/ }), - -/***/ 92042: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Copyright Joyent, Inc. and other Node contributors. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to permit -// persons to whom the Software is furnished to do so, subject to the -// following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN -// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR -// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE -// USE OR OTHER DEALINGS IN THE SOFTWARE. -// A bit simpler than readable streams. -// Implement an async ._write(chunk, encoding, cb), and it'll handle all -// the drain event emission and buffering. - - -module.exports = Writable; -/* */ - -function WriteReq(chunk, encoding, cb) { - this.chunk = chunk; - this.encoding = encoding; - this.callback = cb; - this.next = null; -} // It seems a linked list but it is not -// there will be only 2 of these for each stream - - -function CorkedRequest(state) { - var _this = this; - - this.next = null; - this.entry = null; - - this.finish = function () { - onCorkedFinish(_this, state); - }; -} -/* */ - -/**/ - - -var Duplex; -/**/ - -Writable.WritableState = WritableState; -/**/ - -var internalUtil = { - deprecate: __webpack_require__(65941) -}; -/**/ - -/**/ - -var Stream = __webpack_require__(47640); -/**/ - - -var Buffer = __webpack_require__(64293).Buffer; - -var OurUint8Array = global.Uint8Array || function () {}; - -function _uint8ArrayToBuffer(chunk) { - return Buffer.from(chunk); -} - -function _isUint8Array(obj) { - return Buffer.isBuffer(obj) || obj instanceof OurUint8Array; -} - -var destroyImpl = __webpack_require__(22126); - -var _require = __webpack_require__(14286), - getHighWaterMark = _require.getHighWaterMark; - -var _require$codes = __webpack_require__(71947)/* .codes */ .q, - ERR_INVALID_ARG_TYPE = _require$codes.ERR_INVALID_ARG_TYPE, - ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED, - ERR_MULTIPLE_CALLBACK = _require$codes.ERR_MULTIPLE_CALLBACK, - ERR_STREAM_CANNOT_PIPE = _require$codes.ERR_STREAM_CANNOT_PIPE, - ERR_STREAM_DESTROYED = _require$codes.ERR_STREAM_DESTROYED, - ERR_STREAM_NULL_VALUES = _require$codes.ERR_STREAM_NULL_VALUES, - ERR_STREAM_WRITE_AFTER_END = _require$codes.ERR_STREAM_WRITE_AFTER_END, - ERR_UNKNOWN_ENCODING = _require$codes.ERR_UNKNOWN_ENCODING; - -var errorOrDestroy = destroyImpl.errorOrDestroy; - -__webpack_require__(94835)(Writable, Stream); - -function nop() {} - -function WritableState(options, stream, isDuplex) { - Duplex = Duplex || __webpack_require__(18084); - options = options || {}; // Duplex streams are both readable and writable, but share - // the same options object. - // However, some cases require setting options to different - // values for the readable and the writable sides of the duplex stream, - // e.g. options.readableObjectMode vs. options.writableObjectMode, etc. - - if (typeof isDuplex !== 'boolean') isDuplex = stream instanceof Duplex; // object stream flag to indicate whether or not this stream - // contains buffers or objects. - - this.objectMode = !!options.objectMode; - if (isDuplex) this.objectMode = this.objectMode || !!options.writableObjectMode; // the point at which write() starts returning false - // Note: 0 is a valid value, means that we always return false if - // the entire buffer is not flushed immediately on write() - - this.highWaterMark = getHighWaterMark(this, options, 'writableHighWaterMark', isDuplex); // if _final has been called - - this.finalCalled = false; // drain event flag. - - this.needDrain = false; // at the start of calling end() - - this.ending = false; // when end() has been called, and returned - - this.ended = false; // when 'finish' is emitted - - this.finished = false; // has it been destroyed - - this.destroyed = false; // should we decode strings into buffers before passing to _write? - // this is here so that some node-core streams can optimize string - // handling at a lower level. - - var noDecode = options.decodeStrings === false; - this.decodeStrings = !noDecode; // Crypto is kind of old and crusty. Historically, its default string - // encoding is 'binary' so we have to make this configurable. - // Everything else in the universe uses 'utf8', though. - - this.defaultEncoding = options.defaultEncoding || 'utf8'; // not an actual buffer we keep track of, but a measurement - // of how much we're waiting to get pushed to some underlying - // socket or file. - - this.length = 0; // a flag to see when we're in the middle of a write. - - this.writing = false; // when true all writes will be buffered until .uncork() call - - this.corked = 0; // a flag to be able to tell if the onwrite cb is called immediately, - // or on a later tick. We set this to true at first, because any - // actions that shouldn't happen until "later" should generally also - // not happen before the first write call. - - this.sync = true; // a flag to know if we're processing previously buffered items, which - // may call the _write() callback in the same tick, so that we don't - // end up in an overlapped onwrite situation. - - this.bufferProcessing = false; // the callback that's passed to _write(chunk,cb) - - this.onwrite = function (er) { - onwrite(stream, er); - }; // the callback that the user supplies to write(chunk,encoding,cb) - - - this.writecb = null; // the amount that is being written when _write is called. - - this.writelen = 0; - this.bufferedRequest = null; - this.lastBufferedRequest = null; // number of pending user-supplied write callbacks - // this must be 0 before 'finish' can be emitted - - this.pendingcb = 0; // emit prefinish if the only thing we're waiting for is _write cbs - // This is relevant for synchronous Transform streams - - this.prefinished = false; // True if the error was already emitted and should not be thrown again - - this.errorEmitted = false; // Should close be emitted on destroy. Defaults to true. - - this.emitClose = options.emitClose !== false; // Should .destroy() be called after 'finish' (and potentially 'end') - - this.autoDestroy = !!options.autoDestroy; // count buffered requests - - this.bufferedRequestCount = 0; // allocate the first CorkedRequest, there is always - // one allocated and free to use, and we maintain at most two - - this.corkedRequestsFree = new CorkedRequest(this); -} - -WritableState.prototype.getBuffer = function getBuffer() { - var current = this.bufferedRequest; - var out = []; - - while (current) { - out.push(current); - current = current.next; - } - - return out; -}; - -(function () { - try { - Object.defineProperty(WritableState.prototype, 'buffer', { - get: internalUtil.deprecate(function writableStateBufferGetter() { - return this.getBuffer(); - }, '_writableState.buffer is deprecated. Use _writableState.getBuffer ' + 'instead.', 'DEP0003') - }); - } catch (_) {} -})(); // Test _writableState for inheritance to account for Duplex streams, -// whose prototype chain only points to Readable. - - -var realHasInstance; - -if (typeof Symbol === 'function' && Symbol.hasInstance && typeof Function.prototype[Symbol.hasInstance] === 'function') { - realHasInstance = Function.prototype[Symbol.hasInstance]; - Object.defineProperty(Writable, Symbol.hasInstance, { - value: function value(object) { - if (realHasInstance.call(this, object)) return true; - if (this !== Writable) return false; - return object && object._writableState instanceof WritableState; - } - }); -} else { - realHasInstance = function realHasInstance(object) { - return object instanceof this; - }; -} - -function Writable(options) { - Duplex = Duplex || __webpack_require__(18084); // Writable ctor is applied to Duplexes, too. - // `realHasInstance` is necessary because using plain `instanceof` - // would return false, as no `_writableState` property is attached. - // Trying to use the custom `instanceof` for Writable here will also break the - // Node.js LazyTransform implementation, which has a non-trivial getter for - // `_writableState` that would lead to infinite recursion. - // Checking for a Stream.Duplex instance is faster here instead of inside - // the WritableState constructor, at least with V8 6.5 - - var isDuplex = this instanceof Duplex; - if (!isDuplex && !realHasInstance.call(Writable, this)) return new Writable(options); - this._writableState = new WritableState(options, this, isDuplex); // legacy. - - this.writable = true; - - if (options) { - if (typeof options.write === 'function') this._write = options.write; - if (typeof options.writev === 'function') this._writev = options.writev; - if (typeof options.destroy === 'function') this._destroy = options.destroy; - if (typeof options.final === 'function') this._final = options.final; - } - - Stream.call(this); -} // Otherwise people can pipe Writable streams, which is just wrong. - - -Writable.prototype.pipe = function () { - errorOrDestroy(this, new ERR_STREAM_CANNOT_PIPE()); -}; - -function writeAfterEnd(stream, cb) { - var er = new ERR_STREAM_WRITE_AFTER_END(); // TODO: defer error events consistently everywhere, not just the cb - - errorOrDestroy(stream, er); - process.nextTick(cb, er); -} // Checks that a user-supplied chunk is valid, especially for the particular -// mode the stream is in. Currently this means that `null` is never accepted -// and undefined/non-string values are only allowed in object mode. - - -function validChunk(stream, state, chunk, cb) { - var er; - - if (chunk === null) { - er = new ERR_STREAM_NULL_VALUES(); - } else if (typeof chunk !== 'string' && !state.objectMode) { - er = new ERR_INVALID_ARG_TYPE('chunk', ['string', 'Buffer'], chunk); - } - - if (er) { - errorOrDestroy(stream, er); - process.nextTick(cb, er); - return false; - } - - return true; -} - -Writable.prototype.write = function (chunk, encoding, cb) { - var state = this._writableState; - var ret = false; - - var isBuf = !state.objectMode && _isUint8Array(chunk); - - if (isBuf && !Buffer.isBuffer(chunk)) { - chunk = _uint8ArrayToBuffer(chunk); - } - - if (typeof encoding === 'function') { - cb = encoding; - encoding = null; - } - - if (isBuf) encoding = 'buffer';else if (!encoding) encoding = state.defaultEncoding; - if (typeof cb !== 'function') cb = nop; - if (state.ending) writeAfterEnd(this, cb);else if (isBuf || validChunk(this, state, chunk, cb)) { - state.pendingcb++; - ret = writeOrBuffer(this, state, isBuf, chunk, encoding, cb); - } - return ret; -}; - -Writable.prototype.cork = function () { - this._writableState.corked++; -}; - -Writable.prototype.uncork = function () { - var state = this._writableState; - - if (state.corked) { - state.corked--; - if (!state.writing && !state.corked && !state.bufferProcessing && state.bufferedRequest) clearBuffer(this, state); - } -}; - -Writable.prototype.setDefaultEncoding = function setDefaultEncoding(encoding) { - // node::ParseEncoding() requires lower case. - if (typeof encoding === 'string') encoding = encoding.toLowerCase(); - if (!(['hex', 'utf8', 'utf-8', 'ascii', 'binary', 'base64', 'ucs2', 'ucs-2', 'utf16le', 'utf-16le', 'raw'].indexOf((encoding + '').toLowerCase()) > -1)) throw new ERR_UNKNOWN_ENCODING(encoding); - this._writableState.defaultEncoding = encoding; - return this; -}; - -Object.defineProperty(Writable.prototype, 'writableBuffer', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState && this._writableState.getBuffer(); - } -}); - -function decodeChunk(state, chunk, encoding) { - if (!state.objectMode && state.decodeStrings !== false && typeof chunk === 'string') { - chunk = Buffer.from(chunk, encoding); - } - - return chunk; -} - -Object.defineProperty(Writable.prototype, 'writableHighWaterMark', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState.highWaterMark; - } -}); // if we're already writing something, then just put this -// in the queue, and wait our turn. Otherwise, call _write -// If we return false, then we need a drain event, so set that flag. - -function writeOrBuffer(stream, state, isBuf, chunk, encoding, cb) { - if (!isBuf) { - var newChunk = decodeChunk(state, chunk, encoding); - - if (chunk !== newChunk) { - isBuf = true; - encoding = 'buffer'; - chunk = newChunk; - } - } - - var len = state.objectMode ? 1 : chunk.length; - state.length += len; - var ret = state.length < state.highWaterMark; // we must ensure that previous needDrain will not be reset to false. - - if (!ret) state.needDrain = true; - - if (state.writing || state.corked) { - var last = state.lastBufferedRequest; - state.lastBufferedRequest = { - chunk: chunk, - encoding: encoding, - isBuf: isBuf, - callback: cb, - next: null - }; - - if (last) { - last.next = state.lastBufferedRequest; - } else { - state.bufferedRequest = state.lastBufferedRequest; - } - - state.bufferedRequestCount += 1; - } else { - doWrite(stream, state, false, len, chunk, encoding, cb); - } - - return ret; -} - -function doWrite(stream, state, writev, len, chunk, encoding, cb) { - state.writelen = len; - state.writecb = cb; - state.writing = true; - state.sync = true; - if (state.destroyed) state.onwrite(new ERR_STREAM_DESTROYED('write'));else if (writev) stream._writev(chunk, state.onwrite);else stream._write(chunk, encoding, state.onwrite); - state.sync = false; -} - -function onwriteError(stream, state, sync, er, cb) { - --state.pendingcb; - - if (sync) { - // defer the callback if we are being called synchronously - // to avoid piling up things on the stack - process.nextTick(cb, er); // this can emit finish, and it will always happen - // after error - - process.nextTick(finishMaybe, stream, state); - stream._writableState.errorEmitted = true; - errorOrDestroy(stream, er); - } else { - // the caller expect this to happen before if - // it is async - cb(er); - stream._writableState.errorEmitted = true; - errorOrDestroy(stream, er); // this can emit finish, but finish must - // always follow error - - finishMaybe(stream, state); - } -} - -function onwriteStateUpdate(state) { - state.writing = false; - state.writecb = null; - state.length -= state.writelen; - state.writelen = 0; -} - -function onwrite(stream, er) { - var state = stream._writableState; - var sync = state.sync; - var cb = state.writecb; - if (typeof cb !== 'function') throw new ERR_MULTIPLE_CALLBACK(); - onwriteStateUpdate(state); - if (er) onwriteError(stream, state, sync, er, cb);else { - // Check if we're actually ready to finish, but don't emit yet - var finished = needFinish(state) || stream.destroyed; - - if (!finished && !state.corked && !state.bufferProcessing && state.bufferedRequest) { - clearBuffer(stream, state); - } - - if (sync) { - process.nextTick(afterWrite, stream, state, finished, cb); - } else { - afterWrite(stream, state, finished, cb); - } - } -} - -function afterWrite(stream, state, finished, cb) { - if (!finished) onwriteDrain(stream, state); - state.pendingcb--; - cb(); - finishMaybe(stream, state); -} // Must force callback to be called on nextTick, so that we don't -// emit 'drain' before the write() consumer gets the 'false' return -// value, and has a chance to attach a 'drain' listener. - - -function onwriteDrain(stream, state) { - if (state.length === 0 && state.needDrain) { - state.needDrain = false; - stream.emit('drain'); - } -} // if there's something in the buffer waiting, then process it - - -function clearBuffer(stream, state) { - state.bufferProcessing = true; - var entry = state.bufferedRequest; - - if (stream._writev && entry && entry.next) { - // Fast case, write everything using _writev() - var l = state.bufferedRequestCount; - var buffer = new Array(l); - var holder = state.corkedRequestsFree; - holder.entry = entry; - var count = 0; - var allBuffers = true; - - while (entry) { - buffer[count] = entry; - if (!entry.isBuf) allBuffers = false; - entry = entry.next; - count += 1; - } - - buffer.allBuffers = allBuffers; - doWrite(stream, state, true, state.length, buffer, '', holder.finish); // doWrite is almost always async, defer these to save a bit of time - // as the hot path ends with doWrite - - state.pendingcb++; - state.lastBufferedRequest = null; - - if (holder.next) { - state.corkedRequestsFree = holder.next; - holder.next = null; - } else { - state.corkedRequestsFree = new CorkedRequest(state); - } - - state.bufferedRequestCount = 0; - } else { - // Slow case, write chunks one-by-one - while (entry) { - var chunk = entry.chunk; - var encoding = entry.encoding; - var cb = entry.callback; - var len = state.objectMode ? 1 : chunk.length; - doWrite(stream, state, false, len, chunk, encoding, cb); - entry = entry.next; - state.bufferedRequestCount--; // if we didn't call the onwrite immediately, then - // it means that we need to wait until it does. - // also, that means that the chunk and cb are currently - // being processed, so move the buffer counter past them. - - if (state.writing) { - break; - } - } - - if (entry === null) state.lastBufferedRequest = null; - } - - state.bufferedRequest = entry; - state.bufferProcessing = false; -} - -Writable.prototype._write = function (chunk, encoding, cb) { - cb(new ERR_METHOD_NOT_IMPLEMENTED('_write()')); -}; - -Writable.prototype._writev = null; - -Writable.prototype.end = function (chunk, encoding, cb) { - var state = this._writableState; - - if (typeof chunk === 'function') { - cb = chunk; - chunk = null; - encoding = null; - } else if (typeof encoding === 'function') { - cb = encoding; - encoding = null; - } - - if (chunk !== null && chunk !== undefined) this.write(chunk, encoding); // .end() fully uncorks - - if (state.corked) { - state.corked = 1; - this.uncork(); - } // ignore unnecessary end() calls. - - - if (!state.ending) endWritable(this, state, cb); - return this; -}; - -Object.defineProperty(Writable.prototype, 'writableLength', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - return this._writableState.length; - } -}); - -function needFinish(state) { - return state.ending && state.length === 0 && state.bufferedRequest === null && !state.finished && !state.writing; -} - -function callFinal(stream, state) { - stream._final(function (err) { - state.pendingcb--; - - if (err) { - errorOrDestroy(stream, err); - } - - state.prefinished = true; - stream.emit('prefinish'); - finishMaybe(stream, state); - }); -} - -function prefinish(stream, state) { - if (!state.prefinished && !state.finalCalled) { - if (typeof stream._final === 'function' && !state.destroyed) { - state.pendingcb++; - state.finalCalled = true; - process.nextTick(callFinal, stream, state); - } else { - state.prefinished = true; - stream.emit('prefinish'); - } - } -} - -function finishMaybe(stream, state) { - var need = needFinish(state); - - if (need) { - prefinish(stream, state); - - if (state.pendingcb === 0) { - state.finished = true; - stream.emit('finish'); - - if (state.autoDestroy) { - // In case of duplex streams we need a way to detect - // if the readable side is ready for autoDestroy as well - var rState = stream._readableState; - - if (!rState || rState.autoDestroy && rState.endEmitted) { - stream.destroy(); - } - } - } - } - - return need; -} - -function endWritable(stream, state, cb) { - state.ending = true; - finishMaybe(stream, state); - - if (cb) { - if (state.finished) process.nextTick(cb);else stream.once('finish', cb); - } - - state.ended = true; - stream.writable = false; -} - -function onCorkedFinish(corkReq, state, err) { - var entry = corkReq.entry; - corkReq.entry = null; - - while (entry) { - var cb = entry.callback; - state.pendingcb--; - cb(err); - entry = entry.next; - } // reuse the free corkReq. - - - state.corkedRequestsFree.next = corkReq; -} - -Object.defineProperty(Writable.prototype, 'destroyed', { - // making it explicit this property is not enumerable - // because otherwise some prototype manipulation in - // userland will fail - enumerable: false, - get: function get() { - if (this._writableState === undefined) { - return false; - } - - return this._writableState.destroyed; - }, - set: function set(value) { - // we ignore the value if the stream - // has not been initialized yet - if (!this._writableState) { - return; - } // backward compatibility, the user is explicitly - // managing destroyed - - - this._writableState.destroyed = value; - } -}); -Writable.prototype.destroy = destroyImpl.destroy; -Writable.prototype._undestroy = destroyImpl.undestroy; - -Writable.prototype._destroy = function (err, cb) { - cb(err); -}; - -/***/ }), - -/***/ 37090: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var _Object$setPrototypeO; - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -var finished = __webpack_require__(26052); - -var kLastResolve = Symbol('lastResolve'); -var kLastReject = Symbol('lastReject'); -var kError = Symbol('error'); -var kEnded = Symbol('ended'); -var kLastPromise = Symbol('lastPromise'); -var kHandlePromise = Symbol('handlePromise'); -var kStream = Symbol('stream'); - -function createIterResult(value, done) { - return { - value: value, - done: done - }; -} - -function readAndResolve(iter) { - var resolve = iter[kLastResolve]; - - if (resolve !== null) { - var data = iter[kStream].read(); // we defer if data is null - // we can be expecting either 'end' or - // 'error' - - if (data !== null) { - iter[kLastPromise] = null; - iter[kLastResolve] = null; - iter[kLastReject] = null; - resolve(createIterResult(data, false)); - } - } -} - -function onReadable(iter) { - // we wait for the next tick, because it might - // emit an error with process.nextTick - process.nextTick(readAndResolve, iter); -} - -function wrapForNext(lastPromise, iter) { - return function (resolve, reject) { - lastPromise.then(function () { - if (iter[kEnded]) { - resolve(createIterResult(undefined, true)); - return; - } - - iter[kHandlePromise](resolve, reject); - }, reject); - }; -} - -var AsyncIteratorPrototype = Object.getPrototypeOf(function () {}); -var ReadableStreamAsyncIteratorPrototype = Object.setPrototypeOf((_Object$setPrototypeO = { - get stream() { - return this[kStream]; - }, - - next: function next() { - var _this = this; - - // if we have detected an error in the meanwhile - // reject straight away - var error = this[kError]; - - if (error !== null) { - return Promise.reject(error); - } - - if (this[kEnded]) { - return Promise.resolve(createIterResult(undefined, true)); - } - - if (this[kStream].destroyed) { - // We need to defer via nextTick because if .destroy(err) is - // called, the error will be emitted via nextTick, and - // we cannot guarantee that there is no error lingering around - // waiting to be emitted. - return new Promise(function (resolve, reject) { - process.nextTick(function () { - if (_this[kError]) { - reject(_this[kError]); - } else { - resolve(createIterResult(undefined, true)); - } - }); - }); - } // if we have multiple next() calls - // we will wait for the previous Promise to finish - // this logic is optimized to support for await loops, - // where next() is only called once at a time - - - var lastPromise = this[kLastPromise]; - var promise; - - if (lastPromise) { - promise = new Promise(wrapForNext(lastPromise, this)); - } else { - // fast path needed to support multiple this.push() - // without triggering the next() queue - var data = this[kStream].read(); - - if (data !== null) { - return Promise.resolve(createIterResult(data, false)); - } - - promise = new Promise(this[kHandlePromise]); - } - - this[kLastPromise] = promise; - return promise; - } -}, _defineProperty(_Object$setPrototypeO, Symbol.asyncIterator, function () { - return this; -}), _defineProperty(_Object$setPrototypeO, "return", function _return() { - var _this2 = this; - - // destroy(err, cb) is a private API - // we can guarantee we have that here, because we control the - // Readable class this is attached to - return new Promise(function (resolve, reject) { - _this2[kStream].destroy(null, function (err) { - if (err) { - reject(err); - return; - } - - resolve(createIterResult(undefined, true)); - }); - }); -}), _Object$setPrototypeO), AsyncIteratorPrototype); - -var createReadableStreamAsyncIterator = function createReadableStreamAsyncIterator(stream) { - var _Object$create; - - var iterator = Object.create(ReadableStreamAsyncIteratorPrototype, (_Object$create = {}, _defineProperty(_Object$create, kStream, { - value: stream, - writable: true - }), _defineProperty(_Object$create, kLastResolve, { - value: null, - writable: true - }), _defineProperty(_Object$create, kLastReject, { - value: null, - writable: true - }), _defineProperty(_Object$create, kError, { - value: null, - writable: true - }), _defineProperty(_Object$create, kEnded, { - value: stream._readableState.endEmitted, - writable: true - }), _defineProperty(_Object$create, kHandlePromise, { - value: function value(resolve, reject) { - var data = iterator[kStream].read(); - - if (data) { - iterator[kLastPromise] = null; - iterator[kLastResolve] = null; - iterator[kLastReject] = null; - resolve(createIterResult(data, false)); - } else { - iterator[kLastResolve] = resolve; - iterator[kLastReject] = reject; - } - }, - writable: true - }), _Object$create)); - iterator[kLastPromise] = null; - finished(stream, function (err) { - if (err && err.code !== 'ERR_STREAM_PREMATURE_CLOSE') { - var reject = iterator[kLastReject]; // reject if we are waiting for data in the Promise - // returned by next() and store the error - - if (reject !== null) { - iterator[kLastPromise] = null; - iterator[kLastResolve] = null; - iterator[kLastReject] = null; - reject(err); - } - - iterator[kError] = err; - return; - } - - var resolve = iterator[kLastResolve]; - - if (resolve !== null) { - iterator[kLastPromise] = null; - iterator[kLastResolve] = null; - iterator[kLastReject] = null; - resolve(createIterResult(undefined, true)); - } - - iterator[kEnded] = true; - }); - stream.on('readable', onReadable.bind(null, iterator)); - return iterator; -}; - -module.exports = createReadableStreamAsyncIterator; - -/***/ }), - -/***/ 38568: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } - -function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } - -function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; } - -var _require = __webpack_require__(64293), - Buffer = _require.Buffer; - -var _require2 = __webpack_require__(31669), - inspect = _require2.inspect; - -var custom = inspect && inspect.custom || 'inspect'; - -function copyBuffer(src, target, offset) { - Buffer.prototype.copy.call(src, target, offset); -} - -module.exports = -/*#__PURE__*/ -function () { - function BufferList() { - _classCallCheck(this, BufferList); - - this.head = null; - this.tail = null; - this.length = 0; - } - - _createClass(BufferList, [{ - key: "push", - value: function push(v) { - var entry = { - data: v, - next: null - }; - if (this.length > 0) this.tail.next = entry;else this.head = entry; - this.tail = entry; - ++this.length; - } - }, { - key: "unshift", - value: function unshift(v) { - var entry = { - data: v, - next: this.head - }; - if (this.length === 0) this.tail = entry; - this.head = entry; - ++this.length; - } - }, { - key: "shift", - value: function shift() { - if (this.length === 0) return; - var ret = this.head.data; - if (this.length === 1) this.head = this.tail = null;else this.head = this.head.next; - --this.length; - return ret; - } - }, { - key: "clear", - value: function clear() { - this.head = this.tail = null; - this.length = 0; - } - }, { - key: "join", - value: function join(s) { - if (this.length === 0) return ''; - var p = this.head; - var ret = '' + p.data; - - while (p = p.next) { - ret += s + p.data; - } - - return ret; - } - }, { - key: "concat", - value: function concat(n) { - if (this.length === 0) return Buffer.alloc(0); - var ret = Buffer.allocUnsafe(n >>> 0); - var p = this.head; - var i = 0; - - while (p) { - copyBuffer(p.data, ret, i); - i += p.data.length; - p = p.next; - } - - return ret; - } // Consumes a specified amount of bytes or characters from the buffered data. - - }, { - key: "consume", - value: function consume(n, hasStrings) { - var ret; - - if (n < this.head.data.length) { - // `slice` is the same for buffers and strings. - ret = this.head.data.slice(0, n); - this.head.data = this.head.data.slice(n); - } else if (n === this.head.data.length) { - // First chunk is a perfect match. - ret = this.shift(); - } else { - // Result spans more than one buffer. - ret = hasStrings ? this._getString(n) : this._getBuffer(n); - } - - return ret; - } - }, { - key: "first", - value: function first() { - return this.head.data; - } // Consumes a specified amount of characters from the buffered data. - - }, { - key: "_getString", - value: function _getString(n) { - var p = this.head; - var c = 1; - var ret = p.data; - n -= ret.length; - - while (p = p.next) { - var str = p.data; - var nb = n > str.length ? str.length : n; - if (nb === str.length) ret += str;else ret += str.slice(0, n); - n -= nb; - - if (n === 0) { - if (nb === str.length) { - ++c; - if (p.next) this.head = p.next;else this.head = this.tail = null; - } else { - this.head = p; - p.data = str.slice(nb); - } - - break; - } - - ++c; - } - - this.length -= c; - return ret; - } // Consumes a specified amount of bytes from the buffered data. - - }, { - key: "_getBuffer", - value: function _getBuffer(n) { - var ret = Buffer.allocUnsafe(n); - var p = this.head; - var c = 1; - p.data.copy(ret); - n -= p.data.length; - - while (p = p.next) { - var buf = p.data; - var nb = n > buf.length ? buf.length : n; - buf.copy(ret, ret.length - n, 0, nb); - n -= nb; - - if (n === 0) { - if (nb === buf.length) { - ++c; - if (p.next) this.head = p.next;else this.head = this.tail = null; - } else { - this.head = p; - p.data = buf.slice(nb); - } - - break; - } - - ++c; - } - - this.length -= c; - return ret; - } // Make sure the linked list only shows the minimal necessary information. - - }, { - key: custom, - value: function value(_, options) { - return inspect(this, _objectSpread({}, options, { - // Only inspect one level. - depth: 0, - // It should not recurse. - customInspect: false - })); - } - }]); - - return BufferList; -}(); - -/***/ }), - -/***/ 22126: -/***/ ((module) => { - -"use strict"; - // undocumented cb() API, needed for core, not for public API - -function destroy(err, cb) { - var _this = this; - - var readableDestroyed = this._readableState && this._readableState.destroyed; - var writableDestroyed = this._writableState && this._writableState.destroyed; - - if (readableDestroyed || writableDestroyed) { - if (cb) { - cb(err); - } else if (err) { - if (!this._writableState) { - process.nextTick(emitErrorNT, this, err); - } else if (!this._writableState.errorEmitted) { - this._writableState.errorEmitted = true; - process.nextTick(emitErrorNT, this, err); - } - } - - return this; - } // we set destroyed to true before firing error callbacks in order - // to make it re-entrance safe in case destroy() is called within callbacks - - - if (this._readableState) { - this._readableState.destroyed = true; - } // if this is a duplex stream mark the writable part as destroyed as well - - - if (this._writableState) { - this._writableState.destroyed = true; - } - - this._destroy(err || null, function (err) { - if (!cb && err) { - if (!_this._writableState) { - process.nextTick(emitErrorAndCloseNT, _this, err); - } else if (!_this._writableState.errorEmitted) { - _this._writableState.errorEmitted = true; - process.nextTick(emitErrorAndCloseNT, _this, err); - } else { - process.nextTick(emitCloseNT, _this); - } - } else if (cb) { - process.nextTick(emitCloseNT, _this); - cb(err); - } else { - process.nextTick(emitCloseNT, _this); - } - }); - - return this; -} - -function emitErrorAndCloseNT(self, err) { - emitErrorNT(self, err); - emitCloseNT(self); -} - -function emitCloseNT(self) { - if (self._writableState && !self._writableState.emitClose) return; - if (self._readableState && !self._readableState.emitClose) return; - self.emit('close'); -} - -function undestroy() { - if (this._readableState) { - this._readableState.destroyed = false; - this._readableState.reading = false; - this._readableState.ended = false; - this._readableState.endEmitted = false; - } - - if (this._writableState) { - this._writableState.destroyed = false; - this._writableState.ended = false; - this._writableState.ending = false; - this._writableState.finalCalled = false; - this._writableState.prefinished = false; - this._writableState.finished = false; - this._writableState.errorEmitted = false; - } -} - -function emitErrorNT(self, err) { - self.emit('error', err); -} - -function errorOrDestroy(stream, err) { - // We have tests that rely on errors being emitted - // in the same tick, so changing this is semver major. - // For now when you opt-in to autoDestroy we allow - // the error to be emitted nextTick. In a future - // semver major update we should change the default to this. - var rState = stream._readableState; - var wState = stream._writableState; - if (rState && rState.autoDestroy || wState && wState.autoDestroy) stream.destroy(err);else stream.emit('error', err); -} - -module.exports = { - destroy: destroy, - undestroy: undestroy, - errorOrDestroy: errorOrDestroy -}; - -/***/ }), - -/***/ 26052: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Ported from https://github.com/mafintosh/end-of-stream with -// permission from the author, Mathias Buus (@mafintosh). - - -var ERR_STREAM_PREMATURE_CLOSE = __webpack_require__(71947)/* .codes.ERR_STREAM_PREMATURE_CLOSE */ .q.ERR_STREAM_PREMATURE_CLOSE; - -function once(callback) { - var called = false; - return function () { - if (called) return; - called = true; - - for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) { - args[_key] = arguments[_key]; - } - - callback.apply(this, args); - }; -} - -function noop() {} - -function isRequest(stream) { - return stream.setHeader && typeof stream.abort === 'function'; -} - -function eos(stream, opts, callback) { - if (typeof opts === 'function') return eos(stream, null, opts); - if (!opts) opts = {}; - callback = once(callback || noop); - var readable = opts.readable || opts.readable !== false && stream.readable; - var writable = opts.writable || opts.writable !== false && stream.writable; - - var onlegacyfinish = function onlegacyfinish() { - if (!stream.writable) onfinish(); - }; - - var writableEnded = stream._writableState && stream._writableState.finished; - - var onfinish = function onfinish() { - writable = false; - writableEnded = true; - if (!readable) callback.call(stream); - }; - - var readableEnded = stream._readableState && stream._readableState.endEmitted; - - var onend = function onend() { - readable = false; - readableEnded = true; - if (!writable) callback.call(stream); - }; - - var onerror = function onerror(err) { - callback.call(stream, err); - }; - - var onclose = function onclose() { - var err; - - if (readable && !readableEnded) { - if (!stream._readableState || !stream._readableState.ended) err = new ERR_STREAM_PREMATURE_CLOSE(); - return callback.call(stream, err); - } - - if (writable && !writableEnded) { - if (!stream._writableState || !stream._writableState.ended) err = new ERR_STREAM_PREMATURE_CLOSE(); - return callback.call(stream, err); - } - }; - - var onrequest = function onrequest() { - stream.req.on('finish', onfinish); - }; - - if (isRequest(stream)) { - stream.on('complete', onfinish); - stream.on('abort', onclose); - if (stream.req) onrequest();else stream.on('request', onrequest); - } else if (writable && !stream._writableState) { - // legacy streams - stream.on('end', onlegacyfinish); - stream.on('close', onlegacyfinish); - } - - stream.on('end', onend); - stream.on('finish', onfinish); - if (opts.error !== false) stream.on('error', onerror); - stream.on('close', onclose); - return function () { - stream.removeListener('complete', onfinish); - stream.removeListener('abort', onclose); - stream.removeListener('request', onrequest); - if (stream.req) stream.req.removeListener('finish', onfinish); - stream.removeListener('end', onlegacyfinish); - stream.removeListener('close', onlegacyfinish); - stream.removeListener('finish', onfinish); - stream.removeListener('end', onend); - stream.removeListener('error', onerror); - stream.removeListener('close', onclose); - }; -} - -module.exports = eos; - -/***/ }), - -/***/ 97754: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { Promise.resolve(value).then(_next, _throw); } } - -function _asyncToGenerator(fn) { return function () { var self = this, args = arguments; return new Promise(function (resolve, reject) { var gen = fn.apply(self, args); function _next(value) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value); } function _throw(err) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err); } _next(undefined); }); }; } - -function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; } - -function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; } - -function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } - -var ERR_INVALID_ARG_TYPE = __webpack_require__(71947)/* .codes.ERR_INVALID_ARG_TYPE */ .q.ERR_INVALID_ARG_TYPE; - -function from(Readable, iterable, opts) { - var iterator; - - if (iterable && typeof iterable.next === 'function') { - iterator = iterable; - } else if (iterable && iterable[Symbol.asyncIterator]) iterator = iterable[Symbol.asyncIterator]();else if (iterable && iterable[Symbol.iterator]) iterator = iterable[Symbol.iterator]();else throw new ERR_INVALID_ARG_TYPE('iterable', ['Iterable'], iterable); - - var readable = new Readable(_objectSpread({ - objectMode: true - }, opts)); // Reading boolean to protect against _read - // being called before last iteration completion. - - var reading = false; - - readable._read = function () { - if (!reading) { - reading = true; - next(); - } - }; - - function next() { - return _next2.apply(this, arguments); - } - - function _next2() { - _next2 = _asyncToGenerator(function* () { - try { - var _ref = yield iterator.next(), - value = _ref.value, - done = _ref.done; - - if (done) { - readable.push(null); - } else if (readable.push((yield value))) { - next(); - } else { - reading = false; - } - } catch (err) { - readable.destroy(err); - } - }); - return _next2.apply(this, arguments); - } - - return readable; -} - -module.exports = from; - -/***/ }), - -/***/ 14705: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; -// Ported from https://github.com/mafintosh/pump with -// permission from the author, Mathias Buus (@mafintosh). - - -var eos; - -function once(callback) { - var called = false; - return function () { - if (called) return; - called = true; - callback.apply(void 0, arguments); - }; -} - -var _require$codes = __webpack_require__(71947)/* .codes */ .q, - ERR_MISSING_ARGS = _require$codes.ERR_MISSING_ARGS, - ERR_STREAM_DESTROYED = _require$codes.ERR_STREAM_DESTROYED; - -function noop(err) { - // Rethrow the error if it exists to avoid swallowing it - if (err) throw err; -} - -function isRequest(stream) { - return stream.setHeader && typeof stream.abort === 'function'; -} - -function destroyer(stream, reading, writing, callback) { - callback = once(callback); - var closed = false; - stream.on('close', function () { - closed = true; - }); - if (eos === undefined) eos = __webpack_require__(26052); - eos(stream, { - readable: reading, - writable: writing - }, function (err) { - if (err) return callback(err); - closed = true; - callback(); - }); - var destroyed = false; - return function (err) { - if (closed) return; - if (destroyed) return; - destroyed = true; // request.destroy just do .end - .abort is what we want - - if (isRequest(stream)) return stream.abort(); - if (typeof stream.destroy === 'function') return stream.destroy(); - callback(err || new ERR_STREAM_DESTROYED('pipe')); - }; -} - -function call(fn) { - fn(); -} - -function pipe(from, to) { - return from.pipe(to); -} - -function popCallback(streams) { - if (!streams.length) return noop; - if (typeof streams[streams.length - 1] !== 'function') return noop; - return streams.pop(); -} - -function pipeline() { - for (var _len = arguments.length, streams = new Array(_len), _key = 0; _key < _len; _key++) { - streams[_key] = arguments[_key]; - } - - var callback = popCallback(streams); - if (Array.isArray(streams[0])) streams = streams[0]; - - if (streams.length < 2) { - throw new ERR_MISSING_ARGS('streams'); - } - - var error; - var destroys = streams.map(function (stream, i) { - var reading = i < streams.length - 1; - var writing = i > 0; - return destroyer(stream, reading, writing, function (err) { - if (!error) error = err; - if (err) destroys.forEach(call); - if (reading) return; - destroys.forEach(call); - callback(error); - }); - }); - return streams.reduce(pipe); -} - -module.exports = pipeline; - -/***/ }), - -/***/ 14286: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -var ERR_INVALID_OPT_VALUE = __webpack_require__(71947)/* .codes.ERR_INVALID_OPT_VALUE */ .q.ERR_INVALID_OPT_VALUE; - -function highWaterMarkFrom(options, isDuplex, duplexKey) { - return options.highWaterMark != null ? options.highWaterMark : isDuplex ? options[duplexKey] : null; -} - -function getHighWaterMark(state, options, duplexKey, isDuplex) { - var hwm = highWaterMarkFrom(options, isDuplex, duplexKey); - - if (hwm != null) { - if (!(isFinite(hwm) && Math.floor(hwm) === hwm) || hwm < 0) { - var name = isDuplex ? duplexKey : 'highWaterMark'; - throw new ERR_INVALID_OPT_VALUE(name, hwm); - } - - return Math.floor(hwm); - } // Default value - - - return state.objectMode ? 16 : 16 * 1024; -} - -module.exports = { - getHighWaterMark: getHighWaterMark -}; - -/***/ }), - -/***/ 47640: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -module.exports = __webpack_require__(92413); - - -/***/ }), - -/***/ 30009: -/***/ ((module, exports, __webpack_require__) => { - -var Stream = __webpack_require__(92413); -if (process.env.READABLE_STREAM === 'disable' && Stream) { - module.exports = Stream.Readable; - Object.assign(module.exports, Stream); - module.exports.Stream = Stream; -} else { - exports = module.exports = __webpack_require__(11864); - exports.Stream = Stream || exports; - exports.Readable = exports; - exports.Writable = __webpack_require__(92042); - exports.Duplex = __webpack_require__(18084); - exports.Transform = __webpack_require__(57173); - exports.PassThrough = __webpack_require__(11798); - exports.finished = __webpack_require__(26052); - exports.pipeline = __webpack_require__(14705); -} - - -/***/ }), - -/***/ 27510: -/***/ ((module) => { - -module.exports = { - trueFunc: function trueFunc(){ - return true; - }, - falseFunc: function falseFunc(){ - return false; - } -}; - -/***/ }), - -/***/ 63726: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -var concatMap = __webpack_require__(16755); -var balanced = __webpack_require__(15893); - -module.exports = expandTop; - -var escSlash = '\0SLASH'+Math.random()+'\0'; -var escOpen = '\0OPEN'+Math.random()+'\0'; -var escClose = '\0CLOSE'+Math.random()+'\0'; -var escComma = '\0COMMA'+Math.random()+'\0'; -var escPeriod = '\0PERIOD'+Math.random()+'\0'; - -function numeric(str) { - return parseInt(str, 10) == str - ? parseInt(str, 10) - : str.charCodeAt(0); -} - -function escapeBraces(str) { - return str.split('\\\\').join(escSlash) - .split('\\{').join(escOpen) - .split('\\}').join(escClose) - .split('\\,').join(escComma) - .split('\\.').join(escPeriod); -} - -function unescapeBraces(str) { - return str.split(escSlash).join('\\') - .split(escOpen).join('{') - .split(escClose).join('}') - .split(escComma).join(',') - .split(escPeriod).join('.'); -} - - -// Basically just str.split(","), but handling cases -// where we have nested braced sections, which should be -// treated as individual members, like {a,{b,c},d} -function parseCommaParts(str) { - if (!str) - return ['']; - - var parts = []; - var m = balanced('{', '}', str); - - if (!m) - return str.split(','); - - var pre = m.pre; - var body = m.body; - var post = m.post; - var p = pre.split(','); - - p[p.length-1] += '{' + body + '}'; - var postParts = parseCommaParts(post); - if (post.length) { - p[p.length-1] += postParts.shift(); - p.push.apply(p, postParts); - } - - parts.push.apply(parts, p); - - return parts; -} - -function expandTop(str) { - if (!str) - return []; - - // I don't know why Bash 4.3 does this, but it does. - // Anything starting with {} will have the first two bytes preserved - // but *only* at the top level, so {},a}b will not expand to anything, - // but a{},b}c will be expanded to [a}c,abc]. - // One could argue that this is a bug in Bash, but since the goal of - // this module is to match Bash's rules, we escape a leading {} - if (str.substr(0, 2) === '{}') { - str = '\\{\\}' + str.substr(2); - } - - return expand(escapeBraces(str), true).map(unescapeBraces); -} - -function identity(e) { - return e; -} - -function embrace(str) { - return '{' + str + '}'; -} -function isPadded(el) { - return /^-?0\d/.test(el); -} - -function lte(i, y) { - return i <= y; -} -function gte(i, y) { - return i >= y; -} - -function expand(str, isTop) { - var expansions = []; - - var m = balanced('{', '}', str); - if (!m || /\$$/.test(m.pre)) return [str]; - - var isNumericSequence = /^-?\d+\.\.-?\d+(?:\.\.-?\d+)?$/.test(m.body); - var isAlphaSequence = /^[a-zA-Z]\.\.[a-zA-Z](?:\.\.-?\d+)?$/.test(m.body); - var isSequence = isNumericSequence || isAlphaSequence; - var isOptions = m.body.indexOf(',') >= 0; - if (!isSequence && !isOptions) { - // {a},b} - if (m.post.match(/,.*\}/)) { - str = m.pre + '{' + m.body + escClose + m.post; - return expand(str); - } - return [str]; - } - - var n; - if (isSequence) { - n = m.body.split(/\.\./); - } else { - n = parseCommaParts(m.body); - if (n.length === 1) { - // x{{a,b}}y ==> x{a}y x{b}y - n = expand(n[0], false).map(embrace); - if (n.length === 1) { - var post = m.post.length - ? expand(m.post, false) - : ['']; - return post.map(function(p) { - return m.pre + n[0] + p; - }); - } - } - } - - // at this point, n is the parts, and we know it's not a comma set - // with a single entry. - - // no need to expand pre, since it is guaranteed to be free of brace-sets - var pre = m.pre; - var post = m.post.length - ? expand(m.post, false) - : ['']; - - var N; - - if (isSequence) { - var x = numeric(n[0]); - var y = numeric(n[1]); - var width = Math.max(n[0].length, n[1].length) - var incr = n.length == 3 - ? Math.abs(numeric(n[2])) - : 1; - var test = lte; - var reverse = y < x; - if (reverse) { - incr *= -1; - test = gte; - } - var pad = n.some(isPadded); - - N = []; - - for (var i = x; test(i, y); i += incr) { - var c; - if (isAlphaSequence) { - c = String.fromCharCode(i); - if (c === '\\') - c = ''; - } else { - c = String(i); - if (pad) { - var need = width - c.length; - if (need > 0) { - var z = new Array(need + 1).join('0'); - if (i < 0) - c = '-' + z + c.slice(1); - else - c = z + c; - } - } - } - N.push(c); - } - } else { - N = concatMap(n, function(el) { return expand(el, false) }); - } - - for (var j = 0; j < N.length; j++) { - for (var k = 0; k < post.length; k++) { - var expansion = pre + N[j] + post[k]; - if (!isTop || isSequence || expansion) - expansions.push(expansion); - } - } - - return expansions; -} - - - -/***/ }), - -/***/ 93514: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -var Buffer = __webpack_require__(64293).Buffer; - -var CRC_TABLE = [ - 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, - 0x706af48f, 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, - 0xe0d5e91e, 0x97d2d988, 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, - 0x90bf1d91, 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de, - 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7, 0x136c9856, - 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9, - 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, - 0xa2677172, 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, - 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, - 0x45df5c75, 0xdcd60dcf, 0xabd13d59, 0x26d930ac, 0x51de003a, - 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, 0xcfba9599, - 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, - 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, - 0x01db7106, 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, - 0x9fbfe4a5, 0xe8b8d433, 0x7807c9a2, 0x0f00f934, 0x9609a88e, - 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01, - 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, 0x6c0695ed, - 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950, - 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, - 0xfbd44c65, 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, - 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, - 0x346ed9fc, 0xad678846, 0xda60b8d0, 0x44042d73, 0x33031de5, - 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa, 0xbe0b1010, - 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f, - 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, - 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, - 0x03b6e20c, 0x74b1d29a, 0xead54739, 0x9dd277af, 0x04db2615, - 0x73dc1683, 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8, - 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1, 0xf00f9344, - 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb, - 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, - 0x67dd4acc, 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, - 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, - 0xa6bc5767, 0x3fb506dd, 0x48b2364b, 0xd80d2bda, 0xaf0a1b4c, - 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, 0x316e8eef, - 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, - 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, - 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, - 0x2cd99e8b, 0x5bdeae1d, 0x9b64c2b0, 0xec63f226, 0x756aa39c, - 0x026d930a, 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713, - 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, 0x92d28e9b, - 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242, - 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, - 0x18b74777, 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, - 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45, 0xa00ae278, - 0xd70dd2ee, 0x4e048354, 0x3903b3c2, 0xa7672661, 0xd06016f7, - 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc, 0x40df0b66, - 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9, - 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, - 0xcdd70693, 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, - 0x5d681b02, 0x2a6f2b94, 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, - 0x2d02ef8d -]; - -if (typeof Int32Array !== 'undefined') { - CRC_TABLE = new Int32Array(CRC_TABLE); -} - -function ensureBuffer(input) { - if (Buffer.isBuffer(input)) { - return input; - } - - var hasNewBufferAPI = - typeof Buffer.alloc === "function" && - typeof Buffer.from === "function"; - - if (typeof input === "number") { - return hasNewBufferAPI ? Buffer.alloc(input) : new Buffer(input); - } - else if (typeof input === "string") { - return hasNewBufferAPI ? Buffer.from(input) : new Buffer(input); - } - else { - throw new Error("input must be buffer, number, or string, received " + - typeof input); - } -} - -function bufferizeInt(num) { - var tmp = ensureBuffer(4); - tmp.writeInt32BE(num, 0); - return tmp; -} - -function _crc32(buf, previous) { - buf = ensureBuffer(buf); - if (Buffer.isBuffer(previous)) { - previous = previous.readUInt32BE(0); - } - var crc = ~~previous ^ -1; - for (var n = 0; n < buf.length; n++) { - crc = CRC_TABLE[(crc ^ buf[n]) & 0xff] ^ (crc >>> 8); - } - return (crc ^ -1); -} - -function crc32() { - return bufferizeInt(_crc32.apply(null, arguments)); -} -crc32.signed = function () { - return _crc32.apply(null, arguments); -}; -crc32.unsigned = function () { - return _crc32.apply(null, arguments) >>> 0; -}; - -module.exports = crc32; - - -/***/ }), - -/***/ 28729: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - -const fs = __webpack_require__(35747) -const path = __webpack_require__(85622) - -/* istanbul ignore next */ -const LCHOWN = fs.lchown ? 'lchown' : 'chown' -/* istanbul ignore next */ -const LCHOWNSYNC = fs.lchownSync ? 'lchownSync' : 'chownSync' - -/* istanbul ignore next */ -const needEISDIRHandled = fs.lchown && - !process.version.match(/v1[1-9]+\./) && - !process.version.match(/v10\.[6-9]/) - -const lchownSync = (path, uid, gid) => { - try { - return fs[LCHOWNSYNC](path, uid, gid) - } catch (er) { - if (er.code !== 'ENOENT') - throw er - } -} - -/* istanbul ignore next */ -const chownSync = (path, uid, gid) => { - try { - return fs.chownSync(path, uid, gid) - } catch (er) { - if (er.code !== 'ENOENT') - throw er - } -} - -/* istanbul ignore next */ -const handleEISDIR = - needEISDIRHandled ? (path, uid, gid, cb) => er => { - // Node prior to v10 had a very questionable implementation of - // fs.lchown, which would always try to call fs.open on a directory - // Fall back to fs.chown in those cases. - if (!er || er.code !== 'EISDIR') - cb(er) - else - fs.chown(path, uid, gid, cb) - } - : (_, __, ___, cb) => cb - -/* istanbul ignore next */ -const handleEISDirSync = - needEISDIRHandled ? (path, uid, gid) => { - try { - return lchownSync(path, uid, gid) - } catch (er) { - if (er.code !== 'EISDIR') - throw er - chownSync(path, uid, gid) - } - } - : (path, uid, gid) => lchownSync(path, uid, gid) - -// fs.readdir could only accept an options object as of node v6 -const nodeVersion = process.version -let readdir = (path, options, cb) => fs.readdir(path, options, cb) -let readdirSync = (path, options) => fs.readdirSync(path, options) -/* istanbul ignore next */ -if (/^v4\./.test(nodeVersion)) - readdir = (path, options, cb) => fs.readdir(path, cb) - -const chown = (cpath, uid, gid, cb) => { - fs[LCHOWN](cpath, uid, gid, handleEISDIR(cpath, uid, gid, er => { - // Skip ENOENT error - cb(er && er.code !== 'ENOENT' ? er : null) - })) -} - -const chownrKid = (p, child, uid, gid, cb) => { - if (typeof child === 'string') - return fs.lstat(path.resolve(p, child), (er, stats) => { - // Skip ENOENT error - if (er) - return cb(er.code !== 'ENOENT' ? er : null) - stats.name = child - chownrKid(p, stats, uid, gid, cb) - }) - - if (child.isDirectory()) { - chownr(path.resolve(p, child.name), uid, gid, er => { - if (er) - return cb(er) - const cpath = path.resolve(p, child.name) - chown(cpath, uid, gid, cb) - }) - } else { - const cpath = path.resolve(p, child.name) - chown(cpath, uid, gid, cb) - } -} - - -const chownr = (p, uid, gid, cb) => { - readdir(p, { withFileTypes: true }, (er, children) => { - // any error other than ENOTDIR or ENOTSUP means it's not readable, - // or doesn't exist. give up. - if (er) { - if (er.code === 'ENOENT') - return cb() - else if (er.code !== 'ENOTDIR' && er.code !== 'ENOTSUP') - return cb(er) - } - if (er || !children.length) - return chown(p, uid, gid, cb) - - let len = children.length - let errState = null - const then = er => { - if (errState) - return - if (er) - return cb(errState = er) - if (-- len === 0) - return chown(p, uid, gid, cb) - } - - children.forEach(child => chownrKid(p, child, uid, gid, then)) - }) -} - -const chownrKidSync = (p, child, uid, gid) => { - if (typeof child === 'string') { - try { - const stats = fs.lstatSync(path.resolve(p, child)) - stats.name = child - child = stats - } catch (er) { - if (er.code === 'ENOENT') - return - else - throw er - } - } - - if (child.isDirectory()) - chownrSync(path.resolve(p, child.name), uid, gid) - - handleEISDirSync(path.resolve(p, child.name), uid, gid) -} - -const chownrSync = (p, uid, gid) => { - let children - try { - children = readdirSync(p, { withFileTypes: true }) - } catch (er) { - if (er.code === 'ENOENT') - return - else if (er.code === 'ENOTDIR' || er.code === 'ENOTSUP') - return handleEISDirSync(p, uid, gid) - else - throw er - } - - if (children && children.length) - children.forEach(child => chownrKidSync(p, child, uid, gid)) - - return handleEISDirSync(p, uid, gid) -} - -module.exports = chownr -chownr.sync = chownrSync - - -/***/ }), - -/***/ 16755: -/***/ ((module) => { - -module.exports = function (xs, fn) { - var res = []; - for (var i = 0; i < xs.length; i++) { - var x = fn(xs[i], i); - if (isArray(x)) res.push.apply(res, x); - else res.push(x); - } - return res; -}; - -var isArray = Array.isArray || function (xs) { - return Object.prototype.toString.call(xs) === '[object Array]'; -}; - - -/***/ }), - -/***/ 89072: -/***/ ((module) => { - -"use strict"; - - -module.exports = adapterFactory; - -function adapterFactory(implementation){ - ensureImplementation(implementation); - - var adapter = {} - - var baseAdapter = { - removeSubsets: function (nodes){ - return removeSubsets(adapter, nodes); - }, - existsOne: function(test, elems){ - return existsOne(adapter, test, elems); - }, - getSiblings: function(elem){ - return getSiblings(adapter, elem); - }, - hasAttrib: function(elem, name){ - return hasAttrib(adapter, elem, name); - }, - findOne: function(test, arr){ - return findOne(adapter, test, arr); - }, - findAll: function(test, elems){ - return findAll(adapter, test, elems) - } - }; - - Object.assign(adapter, baseAdapter, implementation); - - return adapter; -} - -var expectImplemented = [ - "isTag", "getAttributeValue", "getChildren", "getName", "getParent", - "getText" -]; - -function ensureImplementation(implementation){ - if(!implementation) throw new TypeError("Expected implementation") - - var notImplemented = expectImplemented.filter(function(fname){ - return typeof implementation[fname] !== "function"; - }); - - if(notImplemented.length){ - var notList = "(" + notImplemented.join(", ") + ")"; - var message = "Expected functions " + notList + " to be implemented"; - throw new Error(message); - } -} - -function removeSubsets(adapter, nodes){ - var idx = nodes.length, node, ancestor, replace; - - // Check if each node (or one of its ancestors) is already contained in the - // array. - while(--idx > -1){ - node = ancestor = nodes[idx]; - - // Temporarily remove the node under consideration - nodes[idx] = null; - replace = true; - - while(ancestor){ - if(nodes.indexOf(ancestor) > -1){ - replace = false; - nodes.splice(idx, 1); - break; - } - ancestor = adapter.getParent(ancestor) - } - - // If the node has been found to be unique, re-insert it. - if(replace){ - nodes[idx] = node; - } - } - - return nodes; -} - -function existsOne(adapter, test, elems){ - return elems.some(function(elem){ - return adapter.isTag(elem) ? - test(elem) || adapter.existsOne(test, adapter.getChildren(elem)) : - false; - }); -} - -function getSiblings(adapter, elem){ - var parent = adapter.getParent(elem); - return parent && adapter.getChildren(parent); -} - - -function hasAttrib(adapter, elem, name){ - return adapter.getAttributeValue(elem,name) !== undefined -} - -function findOne(adapter, test, arr){ - var elem = null; - - for(var i = 0, l = arr.length; i < l && !elem; i++){ - if(test(arr[i])){ - elem = arr[i]; - } else { - var childs = adapter.getChildren(arr[i]); - if(childs && childs.length > 0){ - elem = adapter.findOne(test, childs); - } - } - } - - return elem; -} - -function findAll(adapter, test, elems){ - var result = []; - - for(var i = 0, j = elems.length; i < j; i++){ - if(!adapter.isTag(elems[i])) continue; - if(test(elems[i])) result.push(elems[i]); - var childs = adapter.getChildren(elems[i]); - if(childs) result = result.concat(adapter.findAll(test, childs)); - } - - return result; -} - - -/***/ }), - -/***/ 32825: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -"use strict"; - - -module.exports = CSSselect; - -var DomUtils = __webpack_require__(43370); -var falseFunc = __webpack_require__(27510).falseFunc; -var compileRaw = __webpack_require__(22365); - -function wrapCompile(func) { - return function addAdapter(selector, options, context) { - options = options || {}; - options.adapter = options.adapter || DomUtils; - - return func(selector, options, context); - }; -} - -var compile = wrapCompile(compileRaw); -var compileUnsafe = wrapCompile(compileRaw.compileUnsafe); - -function getSelectorFunc(searchFunc) { - return function select(query, elems, options) { - options = options || {}; - options.adapter = options.adapter || DomUtils; - - if (typeof query !== "function") { - query = compileUnsafe(query, options, elems); - } - if (query.shouldTestNextSiblings) { - elems = appendNextSiblings((options && options.context) || elems, options.adapter); - } - if (!Array.isArray(elems)) elems = options.adapter.getChildren(elems); - else elems = options.adapter.removeSubsets(elems); - return searchFunc(query, elems, options); - }; -} - -function getNextSiblings(elem, adapter) { - var siblings = adapter.getSiblings(elem); - if (!Array.isArray(siblings)) return []; - siblings = siblings.slice(0); - while (siblings.shift() !== elem); - return siblings; -} - -function appendNextSiblings(elems, adapter) { - // Order matters because jQuery seems to check the children before the siblings - if (!Array.isArray(elems)) elems = [elems]; - var newElems = elems.slice(0); - - for (var i = 0, len = elems.length; i < len; i++) { - var nextSiblings = getNextSiblings(newElems[i], adapter); - newElems.push.apply(newElems, nextSiblings); - } - return newElems; -} - -var selectAll = getSelectorFunc(function selectAll(query, elems, options) { - return query === falseFunc || !elems || elems.length === 0 ? [] : options.adapter.findAll(query, elems); -}); - -var selectOne = getSelectorFunc(function selectOne(query, elems, options) { - return query === falseFunc || !elems || elems.length === 0 ? null : options.adapter.findOne(query, elems); -}); - -function is(elem, query, options) { - options = options || {}; - options.adapter = options.adapter || DomUtils; - return (typeof query === "function" ? query : compile(query, options))(elem); -} - -/* - the exported interface -*/ -function CSSselect(query, elems, options) { - return selectAll(query, elems, options); -} - -CSSselect.compile = compile; -CSSselect.filters = compileRaw.Pseudos.filters; -CSSselect.pseudos = compileRaw.Pseudos.pseudos; - -CSSselect.selectAll = selectAll; -CSSselect.selectOne = selectOne; - -CSSselect.is = is; - -//legacy methods (might be removed) -CSSselect.parse = compile; -CSSselect.iterate = selectAll; - -//hooks -CSSselect._compileUnsafe = compileUnsafe; -CSSselect._compileToken = compileRaw.compileToken; - - -/***/ }), - -/***/ 91221: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -var falseFunc = __webpack_require__(27510).falseFunc; - -//https://github.com/slevithan/XRegExp/blob/master/src/xregexp.js#L469 -var reChars = /[-[\]{}()*+?.,\\^$|#\s]/g; - -/* - attribute selectors -*/ -var attributeRules = { - __proto__: null, - equals: function(next, data, options) { - var name = data.name; - var value = data.value; - var adapter = options.adapter; - - if (data.ignoreCase) { - value = value.toLowerCase(); - - return function equalsIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.toLowerCase() === value && next(elem); - }; - } - - return function equals(elem) { - return adapter.getAttributeValue(elem, name) === value && next(elem); - }; - }, - hyphen: function(next, data, options) { - var name = data.name; - var value = data.value; - var len = value.length; - var adapter = options.adapter; - - if (data.ignoreCase) { - value = value.toLowerCase(); - - return function hyphenIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return ( - attr != null && - (attr.length === len || attr.charAt(len) === "-") && - attr.substr(0, len).toLowerCase() === value && - next(elem) - ); - }; - } - - return function hyphen(elem) { - var attr = adapter.getAttributeValue(elem, name); - return ( - attr != null && - attr.substr(0, len) === value && - (attr.length === len || attr.charAt(len) === "-") && - next(elem) - ); - }; - }, - element: function(next, data, options) { - var name = data.name; - var value = data.value; - var adapter = options.adapter; - - if (/\s/.test(value)) { - return falseFunc; - } - - value = value.replace(reChars, "\\$&"); - - var pattern = "(?:^|\\s)" + value + "(?:$|\\s)", - flags = data.ignoreCase ? "i" : "", - regex = new RegExp(pattern, flags); - - return function element(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && regex.test(attr) && next(elem); - }; - }, - exists: function(next, data, options) { - var name = data.name; - var adapter = options.adapter; - - return function exists(elem) { - return adapter.hasAttrib(elem, name) && next(elem); - }; - }, - start: function(next, data, options) { - var name = data.name; - var value = data.value; - var len = value.length; - var adapter = options.adapter; - - if (len === 0) { - return falseFunc; - } - - if (data.ignoreCase) { - value = value.toLowerCase(); - - return function startIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.substr(0, len).toLowerCase() === value && next(elem); - }; - } - - return function start(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.substr(0, len) === value && next(elem); - }; - }, - end: function(next, data, options) { - var name = data.name; - var value = data.value; - var len = -value.length; - var adapter = options.adapter; - - if (len === 0) { - return falseFunc; - } - - if (data.ignoreCase) { - value = value.toLowerCase(); - - return function endIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.substr(len).toLowerCase() === value && next(elem); - }; - } - - return function end(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.substr(len) === value && next(elem); - }; - }, - any: function(next, data, options) { - var name = data.name; - var value = data.value; - var adapter = options.adapter; - - if (value === "") { - return falseFunc; - } - - if (data.ignoreCase) { - var regex = new RegExp(value.replace(reChars, "\\$&"), "i"); - - return function anyIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && regex.test(attr) && next(elem); - }; - } - - return function any(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.indexOf(value) >= 0 && next(elem); - }; - }, - not: function(next, data, options) { - var name = data.name; - var value = data.value; - var adapter = options.adapter; - - if (value === "") { - return function notEmpty(elem) { - return !!adapter.getAttributeValue(elem, name) && next(elem); - }; - } else if (data.ignoreCase) { - value = value.toLowerCase(); - - return function notIC(elem) { - var attr = adapter.getAttributeValue(elem, name); - return attr != null && attr.toLowerCase() !== value && next(elem); - }; - } - - return function not(elem) { - return adapter.getAttributeValue(elem, name) !== value && next(elem); - }; - } -}; - -module.exports = { - compile: function(next, data, options) { - if (options && options.strict && (data.ignoreCase || data.action === "not")) { - throw new Error("Unsupported attribute selector"); - } - return attributeRules[data.action](next, data, options); - }, - rules: attributeRules -}; - - -/***/ }), - -/***/ 22365: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -/* - compiles a selector to an executable function -*/ - -module.exports = compile; - -var parse = __webpack_require__(17525).parse; -var BaseFuncs = __webpack_require__(27510); -var sortRules = __webpack_require__(65426); -var procedure = __webpack_require__(86721); -var Rules = __webpack_require__(35890); -var Pseudos = __webpack_require__(65582); -var trueFunc = BaseFuncs.trueFunc; -var falseFunc = BaseFuncs.falseFunc; - -var filters = Pseudos.filters; - -function compile(selector, options, context) { - var next = compileUnsafe(selector, options, context); - return wrap(next, options); -} - -function wrap(next, options) { - var adapter = options.adapter; - - return function base(elem) { - return adapter.isTag(elem) && next(elem); - }; -} - -function compileUnsafe(selector, options, context) { - var token = parse(selector, options); - return compileToken(token, options, context); -} - -function includesScopePseudo(t) { - return ( - t.type === "pseudo" && - (t.name === "scope" || - (Array.isArray(t.data) && - t.data.some(function(data) { - return data.some(includesScopePseudo); - }))) - ); -} - -var DESCENDANT_TOKEN = { type: "descendant" }; -var FLEXIBLE_DESCENDANT_TOKEN = { type: "_flexibleDescendant" }; -var SCOPE_TOKEN = { type: "pseudo", name: "scope" }; -var PLACEHOLDER_ELEMENT = {}; - -//CSS 4 Spec (Draft): 3.3.1. Absolutizing a Scope-relative Selector -//http://www.w3.org/TR/selectors4/#absolutizing -function absolutize(token, options, context) { - var adapter = options.adapter; - - //TODO better check if context is document - var hasContext = - !!context && - !!context.length && - context.every(function(e) { - return e === PLACEHOLDER_ELEMENT || !!adapter.getParent(e); - }); - - token.forEach(function(t) { - if (t.length > 0 && isTraversal(t[0]) && t[0].type !== "descendant") { - //don't return in else branch - } else if (hasContext && !(Array.isArray(t) ? t.some(includesScopePseudo) : includesScopePseudo(t))) { - t.unshift(DESCENDANT_TOKEN); - } else { - return; - } - - t.unshift(SCOPE_TOKEN); - }); -} - -function compileToken(token, options, context) { - token = token.filter(function(t) { - return t.length > 0; - }); - - token.forEach(sortRules); - - var isArrayContext = Array.isArray(context); - - context = (options && options.context) || context; - - if (context && !isArrayContext) context = [context]; - - absolutize(token, options, context); - - var shouldTestNextSiblings = false; - - var query = token - .map(function(rules) { - if (rules[0] && rules[1] && rules[0].name === "scope") { - var ruleType = rules[1].type; - if (isArrayContext && ruleType === "descendant") { - rules[1] = FLEXIBLE_DESCENDANT_TOKEN; - } else if (ruleType === "adjacent" || ruleType === "sibling") { - shouldTestNextSiblings = true; - } - } - return compileRules(rules, options, context); - }) - .reduce(reduceRules, falseFunc); - - query.shouldTestNextSiblings = shouldTestNextSiblings; - - return query; -} - -function isTraversal(t) { - return procedure[t.type] < 0; -} - -function compileRules(rules, options, context) { - return rules.reduce(function(func, rule) { - if (func === falseFunc) return func; - - if (!(rule.type in Rules)) { - throw new Error("Rule type " + rule.type + " is not supported by css-select"); - } - - return Rules[rule.type](func, rule, options, context); - }, (options && options.rootFunc) || trueFunc); -} - -function reduceRules(a, b) { - if (b === falseFunc || a === trueFunc) { - return a; - } - if (a === falseFunc || b === trueFunc) { - return b; - } - - return function combine(elem) { - return a(elem) || b(elem); - }; -} - -function containsTraversal(t) { - return t.some(isTraversal); -} - -//:not, :has and :matches have to compile selectors -//doing this in lib/pseudos.js would lead to circular dependencies, -//so we add them here -filters.not = function(next, token, options, context) { - var opts = { - xmlMode: !!(options && options.xmlMode), - strict: !!(options && options.strict), - adapter: options.adapter - }; - - if (opts.strict) { - if (token.length > 1 || token.some(containsTraversal)) { - throw new Error("complex selectors in :not aren't allowed in strict mode"); - } - } - - var func = compileToken(token, opts, context); - - if (func === falseFunc) return next; - if (func === trueFunc) return falseFunc; - - return function not(elem) { - return !func(elem) && next(elem); - }; -}; - -filters.has = function(next, token, options) { - var adapter = options.adapter; - var opts = { - xmlMode: !!(options && options.xmlMode), - strict: !!(options && options.strict), - adapter: adapter - }; - - //FIXME: Uses an array as a pointer to the current element (side effects) - var context = token.some(containsTraversal) ? [PLACEHOLDER_ELEMENT] : null; - - var func = compileToken(token, opts, context); - - if (func === falseFunc) return falseFunc; - if (func === trueFunc) { - return function hasChild(elem) { - return adapter.getChildren(elem).some(adapter.isTag) && next(elem); - }; - } - - func = wrap(func, options); - - if (context) { - return function has(elem) { - return next(elem) && ((context[0] = elem), adapter.existsOne(func, adapter.getChildren(elem))); - }; - } - - return function has(elem) { - return next(elem) && adapter.existsOne(func, adapter.getChildren(elem)); - }; -}; - -filters.matches = function(next, token, options, context) { - var opts = { - xmlMode: !!(options && options.xmlMode), - strict: !!(options && options.strict), - rootFunc: next, - adapter: options.adapter - }; - - return compileToken(token, opts, context); -}; - -compile.compileToken = compileToken; -compile.compileUnsafe = compileUnsafe; -compile.Pseudos = Pseudos; - - -/***/ }), - -/***/ 35890: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -var attributes = __webpack_require__(91221); -var Pseudos = __webpack_require__(65582); - -/* - all available rules -*/ -module.exports = { - __proto__: null, - - attribute: attributes.compile, - pseudo: Pseudos.compile, - - //tags - tag: function(next, data, options) { - var name = data.name; - var adapter = options.adapter; - - return function tag(elem) { - return adapter.getName(elem) === name && next(elem); - }; - }, - - //traversal - descendant: function(next, data, options) { - // eslint-disable-next-line no-undef - var isFalseCache = typeof WeakSet !== "undefined" ? new WeakSet() : null; - var adapter = options.adapter; - - return function descendant(elem) { - var found = false; - - while (!found && (elem = adapter.getParent(elem))) { - if (!isFalseCache || !isFalseCache.has(elem)) { - found = next(elem); - if (!found && isFalseCache) { - isFalseCache.add(elem); - } - } - } - - return found; - }; - }, - _flexibleDescendant: function(next, data, options) { - var adapter = options.adapter; - - // Include element itself, only used while querying an array - return function descendant(elem) { - var found = next(elem); - - while (!found && (elem = adapter.getParent(elem))) { - found = next(elem); - } - - return found; - }; - }, - parent: function(next, data, options) { - if (options && options.strict) { - throw new Error("Parent selector isn't part of CSS3"); - } - - var adapter = options.adapter; - - return function parent(elem) { - return adapter.getChildren(elem).some(test); - }; - - function test(elem) { - return adapter.isTag(elem) && next(elem); - } - }, - child: function(next, data, options) { - var adapter = options.adapter; - - return function child(elem) { - var parent = adapter.getParent(elem); - return !!parent && next(parent); - }; - }, - sibling: function(next, data, options) { - var adapter = options.adapter; - - return function sibling(elem) { - var siblings = adapter.getSiblings(elem); - - for (var i = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - if (next(siblings[i])) return true; - } - } - - return false; - }; - }, - adjacent: function(next, data, options) { - var adapter = options.adapter; - - return function adjacent(elem) { - var siblings = adapter.getSiblings(elem), - lastElement; - - for (var i = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - lastElement = siblings[i]; - } - } - - return !!lastElement && next(lastElement); - }; - }, - universal: function(next) { - return next; - } -}; - - -/***/ }), - -/***/ 65582: -/***/ ((module, __unused_webpack_exports, __webpack_require__) => { - -/* - pseudo selectors - - --- - - they are available in two forms: - * filters called when the selector - is compiled and return a function - that needs to return next() - * pseudos get called on execution - they need to return a boolean -*/ - -var getNCheck = __webpack_require__(88970); -var BaseFuncs = __webpack_require__(27510); -var attributes = __webpack_require__(91221); -var trueFunc = BaseFuncs.trueFunc; -var falseFunc = BaseFuncs.falseFunc; - -var checkAttrib = attributes.rules.equals; - -function getAttribFunc(name, value) { - var data = { name: name, value: value }; - return function attribFunc(next, rule, options) { - return checkAttrib(next, data, options); - }; -} - -function getChildFunc(next, adapter) { - return function(elem) { - return !!adapter.getParent(elem) && next(elem); - }; -} - -var filters = { - contains: function(next, text, options) { - var adapter = options.adapter; - - return function contains(elem) { - return next(elem) && adapter.getText(elem).indexOf(text) >= 0; - }; - }, - icontains: function(next, text, options) { - var itext = text.toLowerCase(); - var adapter = options.adapter; - - return function icontains(elem) { - return ( - next(elem) && - adapter - .getText(elem) - .toLowerCase() - .indexOf(itext) >= 0 - ); - }; - }, - - //location specific methods - "nth-child": function(next, rule, options) { - var func = getNCheck(rule); - var adapter = options.adapter; - - if (func === falseFunc) return func; - if (func === trueFunc) return getChildFunc(next, adapter); - - return function nthChild(elem) { - var siblings = adapter.getSiblings(elem); - - for (var i = 0, pos = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - else pos++; - } - } - - return func(pos) && next(elem); - }; - }, - "nth-last-child": function(next, rule, options) { - var func = getNCheck(rule); - var adapter = options.adapter; - - if (func === falseFunc) return func; - if (func === trueFunc) return getChildFunc(next, adapter); - - return function nthLastChild(elem) { - var siblings = adapter.getSiblings(elem); - - for (var pos = 0, i = siblings.length - 1; i >= 0; i--) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - else pos++; - } - } - - return func(pos) && next(elem); - }; - }, - "nth-of-type": function(next, rule, options) { - var func = getNCheck(rule); - var adapter = options.adapter; - - if (func === falseFunc) return func; - if (func === trueFunc) return getChildFunc(next, adapter); - - return function nthOfType(elem) { - var siblings = adapter.getSiblings(elem); - - for (var pos = 0, i = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - if (adapter.getName(siblings[i]) === adapter.getName(elem)) pos++; - } - } - - return func(pos) && next(elem); - }; - }, - "nth-last-of-type": function(next, rule, options) { - var func = getNCheck(rule); - var adapter = options.adapter; - - if (func === falseFunc) return func; - if (func === trueFunc) return getChildFunc(next, adapter); - - return function nthLastOfType(elem) { - var siblings = adapter.getSiblings(elem); - - for (var pos = 0, i = siblings.length - 1; i >= 0; i--) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) break; - if (adapter.getName(siblings[i]) === adapter.getName(elem)) pos++; - } - } - - return func(pos) && next(elem); - }; - }, - - //TODO determine the actual root element - root: function(next, rule, options) { - var adapter = options.adapter; - - return function(elem) { - return !adapter.getParent(elem) && next(elem); - }; - }, - - scope: function(next, rule, options, context) { - var adapter = options.adapter; - - if (!context || context.length === 0) { - //equivalent to :root - return filters.root(next, rule, options); - } - - function equals(a, b) { - if (typeof adapter.equals === "function") return adapter.equals(a, b); - - return a === b; - } - - if (context.length === 1) { - //NOTE: can't be unpacked, as :has uses this for side-effects - return function(elem) { - return equals(context[0], elem) && next(elem); - }; - } - - return function(elem) { - return context.indexOf(elem) >= 0 && next(elem); - }; - }, - - //jQuery extensions (others follow as pseudos) - checkbox: getAttribFunc("type", "checkbox"), - file: getAttribFunc("type", "file"), - password: getAttribFunc("type", "password"), - radio: getAttribFunc("type", "radio"), - reset: getAttribFunc("type", "reset"), - image: getAttribFunc("type", "image"), - submit: getAttribFunc("type", "submit"), - - //dynamic state pseudos. These depend on optional Adapter methods. - hover: function(next, rule, options) { - var adapter = options.adapter; - - if (typeof adapter.isHovered === 'function') { - return function hover(elem) { - return next(elem) && adapter.isHovered(elem); - }; - } - - return falseFunc; - }, - visited: function(next, rule, options) { - var adapter = options.adapter; - - if (typeof adapter.isVisited === 'function') { - return function visited(elem) { - return next(elem) && adapter.isVisited(elem); - }; - } - - return falseFunc; - }, - active: function(next, rule, options) { - var adapter = options.adapter; - - if (typeof adapter.isActive === 'function') { - return function active(elem) { - return next(elem) && adapter.isActive(elem); - }; - } - - return falseFunc; - } -}; - -//helper methods -function getFirstElement(elems, adapter) { - for (var i = 0; elems && i < elems.length; i++) { - if (adapter.isTag(elems[i])) return elems[i]; - } -} - -//while filters are precompiled, pseudos get called when they are needed -var pseudos = { - empty: function(elem, adapter) { - return !adapter.getChildren(elem).some(function(elem) { - return adapter.isTag(elem) || elem.type === "text"; - }); - }, - - "first-child": function(elem, adapter) { - return getFirstElement(adapter.getSiblings(elem), adapter) === elem; - }, - "last-child": function(elem, adapter) { - var siblings = adapter.getSiblings(elem); - - for (var i = siblings.length - 1; i >= 0; i--) { - if (siblings[i] === elem) return true; - if (adapter.isTag(siblings[i])) break; - } - - return false; - }, - "first-of-type": function(elem, adapter) { - var siblings = adapter.getSiblings(elem); - - for (var i = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) return true; - if (adapter.getName(siblings[i]) === adapter.getName(elem)) break; - } - } - - return false; - }, - "last-of-type": function(elem, adapter) { - var siblings = adapter.getSiblings(elem); - - for (var i = siblings.length - 1; i >= 0; i--) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) return true; - if (adapter.getName(siblings[i]) === adapter.getName(elem)) break; - } - } - - return false; - }, - "only-of-type": function(elem, adapter) { - var siblings = adapter.getSiblings(elem); - - for (var i = 0, j = siblings.length; i < j; i++) { - if (adapter.isTag(siblings[i])) { - if (siblings[i] === elem) continue; - if (adapter.getName(siblings[i]) === adapter.getName(elem)) { - return false; - } - } - } - - return true; - }, - "only-child": function(elem, adapter) { - var siblings = adapter.getSiblings(elem); - - for (var i = 0; i < siblings.length; i++) { - if (adapter.isTag(siblings[i]) && siblings[i] !== elem) return false; - } - - return true; - }, - - //:matches(a, area, link)[href] - link: function(elem, adapter) { - return adapter.hasAttrib(elem, "href"); - }, - //TODO: :any-link once the name is finalized (as an alias of :link) - - //forms - //to consider: :target - - //:matches([selected], select:not([multiple]):not(> option[selected]) > option:first-of-type) - selected: function(elem, adapter) { - if (adapter.hasAttrib(elem, "selected")) return true; - else if (adapter.getName(elem) !== "option") return false; - - //the first