UNPKG

@tricoteuses/arbre-de-la-loi

Version:

Generate ASTs from the French bills & laws; manipulate & export them to Markdown, etc.

392 lines (300 loc) 32 kB
"use strict"; require("core-js/modules/es.array.slice.js"); require("core-js/modules/es.object.to-string.js"); require("core-js/modules/es.function.name.js"); require("core-js/modules/es.array.from.js"); require("core-js/modules/es.string.iterator.js"); require("core-js/modules/es.symbol.js"); require("core-js/modules/es.symbol.description.js"); require("core-js/modules/es.symbol.iterator.js"); require("core-js/modules/es.array.iterator.js"); require("core-js/modules/web.dom-collections.iterator.js"); require("core-js/modules/es.array.is-array.js"); require("core-js/modules/es.promise.js"); require("regenerator-runtime/runtime.js"); require("core-js/modules/es.array.join.js"); require("core-js/modules/es.array.sort.js"); require("core-js/modules/es.array.filter.js"); require("core-js/modules/es.object.values.js"); var _loaders = require("@tricoteuses/assemblee/lib/loaders"); var _assert = _interopRequireDefault(require("assert")); var _child_process = require("child_process"); var _commandLineArgs = _interopRequireDefault(require("command-line-args")); var _fsExtra = _interopRequireDefault(require("fs-extra")); var _hastUtilFromParse = _interopRequireDefault(require("hast-util-from-parse5")); var _hastUtilToHtml = _interopRequireDefault(require("hast-util-to-html")); var _parse = _interopRequireDefault(require("parse5")); var _path = _interopRequireDefault(require("path")); var _prettier = _interopRequireDefault(require("prettier")); var _unistUtilRemovePosition = _interopRequireDefault(require("unist-util-remove-position")); var _vfile = _interopRequireDefault(require("vfile")); var _cleaners = require("../cleaners"); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { "default": obj }; } 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 _createForOfIteratorHelper(o, allowArrayLike) { var it; if (typeof Symbol === "undefined" || o[Symbol.iterator] == null) { if (Array.isArray(o) || (it = _unsupportedIterableToArray(o)) || allowArrayLike && o && typeof o.length === "number") { if (it) o = it; var i = 0; var F = function F() {}; return { s: F, n: function n() { if (i >= o.length) return { done: true }; return { done: false, value: o[i++] }; }, e: function e(_e) { throw _e; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var normalCompletion = true, didErr = false, err; return { s: function s() { it = o[Symbol.iterator](); }, n: function n() { var step = it.next(); normalCompletion = step.done; return step; }, e: function e(_e2) { didErr = true; err = _e2; }, f: function f() { try { if (!normalCompletion && it["return"] != null) it["return"](); } finally { if (didErr) throw err; } } }; } function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); } function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; } var optionsDefinitions = [{ alias: "c", help: "commit documents", name: "commit", type: Boolean }, { alias: "f", help: "clean even already retrieved documents", name: "full", type: Boolean }, { alias: "l", defaultValue: "15", name: "legislature", type: String }, { alias: "o", help: "clean only one document", name: "one", type: Boolean }, { alias: "r", help: "push commit to given remote", multiple: true, name: "remote", type: String }, { alias: "s", help: "don't log anything", name: "silent", type: Boolean }, { alias: "u", help: "UID of first Assembl\xE9e's \"texte de loi\" to clean", name: "uid", type: String }, { alias: "v", help: "verbose logs", name: "verbose", type: Boolean }, { defaultOption: true, help: "directory containing Assemblée open data files", name: "dataDir", type: String }]; var options = (0, _commandLineArgs["default"])(optionsDefinitions); function commitAndPush(repositoryDir, commit, remotes) { var error = false; if (commit) { (0, _child_process.execSync)("git add .", { cwd: repositoryDir, env: process.env, encoding: "utf-8", stdio: ["ignore", "ignore", "pipe"] }); try { (0, _child_process.execSync)('git commit -m "Nouvelle moisson"', { cwd: repositoryDir, env: process.env, encoding: "utf-8" }); } catch (childProcess) { if (childProcess.stderr === null || !/nothing to commit/.test(childProcess.stdout)) { console.error(childProcess.output); throw childProcess; } } var _iterator = _createForOfIteratorHelper(remotes || []), _step; try { for (_iterator.s(); !(_step = _iterator.n()).done;) { var remote = _step.value; try { (0, _child_process.execSync)("git push ".concat(remote, " master"), { cwd: repositoryDir, env: process.env, encoding: "utf-8", stdio: ["ignore", "ignore", "pipe"] }); } catch (childProcess) { // Don't stop when push fails. console.error(childProcess.output); error = true; } } } catch (err) { _iterator.e(err); } finally { _iterator.f(); } } return error; } function convertTextesLois() { return _convertTextesLois.apply(this, arguments); } function _convertTextesLois() { _convertTextesLois = _asyncToGenerator( /*#__PURE__*/regeneratorRuntime.mark(function _callee() { var dataDir, _loadAssembleeData, documentByUid, documentsRawHtmlDir, documentsCleanHtmlDir, _iterator2, _step2, filename, documents, firstUid, skip, _iterator3, _step3, document, documentCleanHtmlBasename, documentCleanHtmlFilePath, documentRawHtmlBasename, documentRawHtmlFilePath, documentRawHtml, documentHtml, documentParse5Ast, documentVfile, documentHast, documentCleanHtml; return regeneratorRuntime.wrap(function _callee$(_context) { while (1) { switch (_context.prev = _context.next) { case 0: (0, _assert["default"])(!options.commit || options.one, 'Options "commit" & "one" are incompatible'); (0, _assert["default"])(!options.commit || options.uid, 'Options "commit" & "uid" are incompatible'); dataDir = options.dataDir; _loadAssembleeData = (0, _loaders.loadAssembleeData)(dataDir, _loaders.EnabledDatasets.DossiersLegislatifs, options.legislature), documentByUid = _loadAssembleeData.documentByUid; documentsRawHtmlDir = _path["default"].join(dataDir, "documents_html"); (0, _assert["default"])(_fsExtra["default"].existsSync(documentsRawHtmlDir), "Directory \"".concat(documentsRawHtmlDir, "\" doesn't exist")); documentsCleanHtmlDir = _path["default"].join(dataDir, "documents_html_nettoye"); _fsExtra["default"].ensureDirSync(documentsCleanHtmlDir); if (!(options.full && !options.one && !options.uid)) { _context.next = 27; break; } _iterator2 = _createForOfIteratorHelper(_fsExtra["default"].readdirSync(documentsCleanHtmlDir)); _context.prev = 10; _iterator2.s(); case 12: if ((_step2 = _iterator2.n()).done) { _context.next = 19; break; } filename = _step2.value; if (!(filename[0] === ".")) { _context.next = 16; break; } return _context.abrupt("continue", 17); case 16: _fsExtra["default"].removeSync(_path["default"].join(documentsCleanHtmlDir, filename)); case 17: _context.next = 12; break; case 19: _context.next = 24; break; case 21: _context.prev = 21; _context.t0 = _context["catch"](10); _iterator2.e(_context.t0); case 24: _context.prev = 24; _iterator2.f(); return _context.finish(24); case 27: documents = Object.values(documentByUid) // Ignore documents from Sénat. .filter(function (document) { return document.uid.substring(4, 6) !== "SN"; }).sort(function (a, b) { return a.uid.localeCompare(b.uid); }); firstUid = options.uid; skip = !!firstUid; _iterator3 = _createForOfIteratorHelper(documents); _context.prev = 31; _iterator3.s(); case 33: if ((_step3 = _iterator3.n()).done) { _context.next = 69; break; } document = _step3.value; if (!skip) { _context.next = 41; break; } if (!(document.uid === firstUid)) { _context.next = 40; break; } skip = false; _context.next = 41; break; case 40: return _context.abrupt("continue", 67); case 41: documentCleanHtmlBasename = (0, _loaders.pathFromDocumentUid)(documentsCleanHtmlDir, document.uid); documentCleanHtmlFilePath = "".concat(documentCleanHtmlBasename, ".html"); if (!(!options.full && _fsExtra["default"].existsSync(documentCleanHtmlFilePath))) { _context.next = 45; break; } return _context.abrupt("continue", 67); case 45: documentRawHtmlBasename = (0, _loaders.pathFromDocumentUid)(documentsRawHtmlDir, document.uid); documentRawHtmlFilePath = "".concat(documentRawHtmlBasename, ".html"); if (_fsExtra["default"].existsSync(documentRawHtmlFilePath)) { _context.next = 49; break; } return _context.abrupt("continue", 67); case 49: if (!options.silent) { console.log("Cleaning HTML of document ".concat(document.uid, "\u2026")); } documentRawHtml = _fsExtra["default"].readFileSync(documentRawHtmlFilePath, { encoding: "utf8" }); documentHtml = documentRawHtml; documentHtml = (0, _cleaners.removeLetterSpacingStyleAttributes)(documentHtml); documentHtml = (0, _cleaners.removeEmptyStyleAttributes)(documentHtml); documentParse5Ast = _parse["default"].parse(documentHtml, { sourceCodeLocationInfo: true }); documentVfile = (0, _vfile["default"])({ contents: documentRawHtml, path: documentRawHtmlFilePath }); documentHast = (0, _hastUtilFromParse["default"])(documentParse5Ast, { file: documentVfile }); (0, _unistUtilRemovePosition["default"])(documentHast); (0, _cleaners.removeStyleElements)(documentHast); (0, _cleaners.mergeSpanElementsWithSameAttributes)(documentHast); (0, _cleaners.replaceSpanElementsContainingOnlySpacesWithTexts)(documentHast); (0, _cleaners.replaceSpanElementsWithoutPropertiesWithTexts)(documentHast); (0, _cleaners.mergeTexts)(documentHast); documentCleanHtml = _prettier["default"].format((0, _hastUtilToHtml["default"])(documentHast), { parser: "html" }); _fsExtra["default"].writeFileSync(documentCleanHtmlFilePath, documentCleanHtml, { encoding: "utf8" }); if (!options.one) { _context.next = 67; break; } return _context.abrupt("break", 69); case 67: _context.next = 33; break; case 69: _context.next = 74; break; case 71: _context.prev = 71; _context.t1 = _context["catch"](31); _iterator3.e(_context.t1); case 74: _context.prev = 74; _iterator3.f(); return _context.finish(74); case 77: if (commitAndPush(documentsCleanHtmlDir, options.commit, options.remote)) { process.exit(1); } case 78: case "end": return _context.stop(); } } }, _callee, null, [[10, 21, 24, 27], [31, 71, 74, 77]]); })); return _convertTextesLois.apply(this, arguments); } convertTextesLois()["catch"](function (error) { console.log(error); process.exit(1); }); //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9zY3JpcHRzL2NsZWFuX2Fzc2VtYmxlZV9kb2N1bWVudHMudHMiXSwibmFtZXMiOlsib3B0aW9uc0RlZmluaXRpb25zIiwiYWxpYXMiLCJoZWxwIiwibmFtZSIsInR5cGUiLCJCb29sZWFuIiwiZGVmYXVsdFZhbHVlIiwiU3RyaW5nIiwibXVsdGlwbGUiLCJkZWZhdWx0T3B0aW9uIiwib3B0aW9ucyIsImNvbW1pdEFuZFB1c2giLCJyZXBvc2l0b3J5RGlyIiwiY29tbWl0IiwicmVtb3RlcyIsImVycm9yIiwiY3dkIiwiZW52IiwicHJvY2VzcyIsImVuY29kaW5nIiwic3RkaW8iLCJjaGlsZFByb2Nlc3MiLCJzdGRlcnIiLCJ0ZXN0Iiwic3Rkb3V0IiwiY29uc29sZSIsIm91dHB1dCIsInJlbW90ZSIsImNvbnZlcnRUZXh0ZXNMb2lzIiwib25lIiwidWlkIiwiZGF0YURpciIsIkVuYWJsZWREYXRhc2V0cyIsIkRvc3NpZXJzTGVnaXNsYXRpZnMiLCJsZWdpc2xhdHVyZSIsImRvY3VtZW50QnlVaWQiLCJkb2N1bWVudHNSYXdIdG1sRGlyIiwicGF0aCIsImpvaW4iLCJmcyIsImV4aXN0c1N5bmMiLCJkb2N1bWVudHNDbGVhbkh0bWxEaXIiLCJlbnN1cmVEaXJTeW5jIiwiZnVsbCIsInJlYWRkaXJTeW5jIiwiZmlsZW5hbWUiLCJyZW1vdmVTeW5jIiwiZG9jdW1lbnRzIiwiT2JqZWN0IiwidmFsdWVzIiwiZmlsdGVyIiwiZG9jdW1lbnQiLCJzdWJzdHJpbmciLCJzb3J0IiwiYSIsImIiLCJsb2NhbGVDb21wYXJlIiwiZmlyc3RVaWQiLCJza2lwIiwiZG9jdW1lbnRDbGVhbkh0bWxCYXNlbmFtZSIsImRvY3VtZW50Q2xlYW5IdG1sRmlsZVBhdGgiLCJkb2N1bWVudFJhd0h0bWxCYXNlbmFtZSIsImRvY3VtZW50UmF3SHRtbEZpbGVQYXRoIiwic2lsZW50IiwibG9nIiwiZG9jdW1lbnRSYXdIdG1sIiwicmVhZEZpbGVTeW5jIiwiZG9jdW1lbnRIdG1sIiwiZG9jdW1lbnRQYXJzZTVBc3QiLCJwYXJzZTUiLCJwYXJzZSIsInNvdXJjZUNvZGVMb2NhdGlvbkluZm8iLCJkb2N1bWVudFZmaWxlIiwiY29udGVudHMiLCJkb2N1bWVudEhhc3QiLCJmaWxlIiwiZG9jdW1lbnRDbGVhbkh0bWwiLCJwcmV0dGllciIsImZvcm1hdCIsInBhcnNlciIsIndyaXRlRmlsZVN5bmMiLCJleGl0Il0sIm1hcHBpbmdzIjoiOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFBQTs7QUFLQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFDQTs7QUFFQTs7Ozs7Ozs7Ozs7Ozs7QUFXQSxJQUFNQSxrQkFBa0IsR0FBRyxDQUN6QjtBQUNFQyxFQUFBQSxLQUFLLEVBQUUsR0FEVDtBQUVFQyxFQUFBQSxJQUFJLEVBQUUsa0JBRlI7QUFHRUMsRUFBQUEsSUFBSSxFQUFFLFFBSFI7QUFJRUMsRUFBQUEsSUFBSSxFQUFFQztBQUpSLENBRHlCLEVBT3pCO0FBQ0VKLEVBQUFBLEtBQUssRUFBRSxHQURUO0FBRUVDLEVBQUFBLElBQUksRUFBRSx3Q0FGUjtBQUdFQyxFQUFBQSxJQUFJLEVBQUUsTUFIUjtBQUlFQyxFQUFBQSxJQUFJLEVBQUVDO0FBSlIsQ0FQeUIsRUFhekI7QUFDRUosRUFBQUEsS0FBSyxFQUFFLEdBRFQ7QUFFRUssRUFBQUEsWUFBWSxFQUFFLElBRmhCO0FBR0VILEVBQUFBLElBQUksRUFBRSxhQUhSO0FBSUVDLEVBQUFBLElBQUksRUFBRUc7QUFKUixDQWJ5QixFQW1CekI7QUFDRU4sRUFBQUEsS0FBSyxFQUFFLEdBRFQ7QUFFRUMsRUFBQUEsSUFBSSxFQUFFLHlCQUZSO0FBR0VDLEVBQUFBLElBQUksRUFBRSxLQUhSO0FBSUVDLEVBQUFBLElBQUksRUFBRUM7QUFKUixDQW5CeUIsRUF5QnpCO0FBQ0VKLEVBQUFBLEtBQUssRUFBRSxHQURUO0FBRUVDLEVBQUFBLElBQUksRUFBRSw2QkFG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aUJBbEdWLEdBa0c4QkMscUJBQVNDLE1BQVQsQ0FBZ0IsZ0NBQVdKLFlBQVgsQ0FBaEIsRUFBMEM7QUFDbEVLLGNBQUFBLE1BQU0sRUFBRTtBQUQwRCxhQUExQyxDQWxHOUI7O0FBc0dJeEMsZ0NBQUd5QyxhQUFILENBQWlCcEIseUJBQWpCLEVBQTRDZ0IsaUJBQTVDLEVBQStEO0FBQzdEekQsY0FBQUEsUUFBUSxFQUFFO0FBRG1ELGFBQS9EOztBQXRHSixpQkEwR1FULE9BQU8sQ0FBQ21CLEdBMUdoQjtBQUFBO0FBQUE7QUFBQTs7QUFBQTs7QUFBQTtBQUFBO0FBQUE7O0FBQUE7QUFBQTtBQUFBOztBQUFBO0FBQUE7QUFBQTs7QUFBQTs7QUFBQTtBQUFBOztBQUFBOztBQUFBOztBQUFBO0FBK0dFLGdCQUFJbEIsYUFBYSxDQUFDOEIscUJBQUQsRUFBd0IvQixPQUFPLENBQUNHLE1BQWhDLEVBQXdDSCxPQUFPLENBQUNpQixNQUFoRCxDQUFqQixFQUEwRTtBQUN4RVQsY0FBQUEsT0FBTyxDQUFDK0QsSUFBUixDQUFhLENBQWI7QUFDRDs7QUFqSEg7QUFBQTtBQUFBO0FBQUE7QUFBQTtBQUFBO0FBQUEsRzs7OztBQW9IQXJELGlCQUFpQixXQUFqQixDQUEwQixVQUFDYixLQUFELEVBQVc7QUFDbkNVLEVBQUFBLE9BQU8sQ0FBQ3VDLEdBQVIsQ0FBWWpELEtBQVo7QUFDQUcsRUFBQUEsT0FBTyxDQUFDK0QsSUFBUixDQUFhLENBQWI7QUFDRCxDQUhEIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHtcbiAgRW5hYmxlZERhdGFzZXRzLFxuICBsb2FkQXNzZW1ibGVlRGF0YSxcbiAgcGF0aEZyb21Eb2N1bWVudFVpZCxcbn0gZnJvbSBcIkB0cmljb3RldXNlcy9hc3NlbWJsZWUvbGliL2xvYWRlcnNcIlxuaW1wb3J0IGFzc2VydCBmcm9tIFwiYXNzZXJ0XCJcbmltcG9ydCB7IGV4ZWNTeW5jIH0gZnJvbSBcImNoaWxkX3Byb2Nlc3NcIlxuaW1wb3J0IGNvbW1hbmRMaW5lQXJncyBmcm9tIFwiY29tbWFuZC1saW5lLWFyZ3NcIlxuaW1wb3J0IGZzIGZyb20gXCJmcy1leHRyYVwiXG5pbXBvcnQgaGFzdEZyb21QYXJzZTUgZnJvbSBcImhhc3QtdXRpbC1mcm9tLXBhcnNlNVwiXG5pbXBvcnQgaGFzdFRvSHRtbCBmcm9tIFwiaGFzdC11dGlsLXRvLWh0bWxcIlxuaW1wb3J0IHBhcnNlNSBmcm9tIFwicGFyc2U1XCJcbmltcG9ydCBwYXRoIGZyb20gXCJwYXRoXCJcbmltcG9ydCBwcmV0dGllciBmcm9tIFwicHJldHRpZXJcIlxuaW1wb3J0IHVuaXN0UmVtb3ZlUG9zaXRpb24gZnJvbSBcInVuaXN0LXV0aWwtcmVtb3ZlLXBvc2l0aW9uXCJcbmltcG9ydCB2ZmlsZSBmcm9tIFwidmZpbGVcIlxuXG5pbXBvcnQge1xuICBtZXJnZVNwYW5FbGVtZW50c1dpdGhTYW1lQXR0cmlidXRlcyxcbiAgbWVyZ2VUZXh0cyxcbiAgcmVtb3ZlRW1wdHlTdHlsZUF0dHJpYnV0ZXMsXG4gIHJlbW92ZUxldHRlclNwYWNpbmdTdHlsZUF0dHJpYnV0ZXMsXG4gIHJlbW92ZVN0eWxlRWxlbWVudHMsXG4gIHJlcGxhY2VTcGFuRWxlbWVudHNDb250YWluaW5nT25seVNwYWNlc1dpdGhUZXh0cyxcbiAgcmVwbGFjZVNwYW5FbGVtZW50c1dpdGhvdXRQcm9wZXJ0aWVzV2l0aFRleHRzLFxufSBmcm9tIFwiLi4vY2xlYW5lcnNcIlxuaW1wb3J0IHsgSGFzdFJvb3QgfSBmcm9tIFwiLi4vaGFzdFwiXG5cbmNvbnN0IG9wdGlvbnNEZWZpbml0aW9ucyA9IFtcbiAge1xuICAgIGFsaWFzOiBcImNcIixcbiAgICBoZWxwOiBcImNvbW1pdCBkb2N1bWVudHNcIixcbiAgICBuYW1lOiBcImNvbW1pdFwiLFxuICAgIHR5cGU6IEJvb2xlYW4sXG4gIH0sXG4gIHtcbiAgICBhbGlhczogXCJmXCIsXG4gICAgaGVscDogXCJjbGVhbiBldmVuIGFscmVhZHkgcmV0cmlldmVkIGRvY3VtZW50c1wiLFxuICAgIG5hbWU6IFwiZnVsbFwiLFxuICAgIHR5cGU6IEJvb2xlYW4sXG4gIH0sXG4gIHtcbiAgICBhbGlhczogXCJsXCIsXG4gICAgZGVmYXVsdFZhbHVlOiBcIjE1XCIsXG4gICAgbmFtZTogXCJsZWdpc2xhdHVyZVwiLFxuICAgIHR5cGU6IFN0cmluZyxcbiAgfSxcbiAge1xuICAgIGFsaWFzOiBcIm9cIixcbiAgICBoZWxwOiBcImNsZWFuIG9ubHkgb25lIGRvY3VtZW50XCIsXG4gICAgbmFtZTogXCJvbmVcIixcbiAgICB0eXBlOiBCb29sZWFuLFxuICB9LFxuICB7XG4gICAgYWxpYXM6IFwiclwiLFxuICAgIGhlbHA6IFwicHVzaCBjb21taXQgdG8gZ2l2ZW4gcmVtb3RlXCIsXG4gICAgbXVsdGlwbGU6IHRydWUsXG4gICAgbmFtZTogXCJyZW1vdGVcIixcbiAgICB0eXBlOiBTdHJpbmcsXG4gIH0sXG4gIHtcbiAgICBhbGlhczogXCJzXCIsXG4gICAgaGVscDogXCJkb24ndCBsb2cgYW55dGhpbmdcIixcbiAgICBuYW1lOiBcInNpbGVudFwiLFxuICAgIHR5cGU6IEJvb2xlYW4sXG4gIH0sXG4gIHtcbiAgICBhbGlhczogXCJ1XCIsXG4gICAgaGVscDogYFVJRCBvZiBmaXJzdCBBc3NlbWJsw6llJ3MgXCJ0ZXh0ZSBkZSBsb2lcIiB0byBjbGVhbmAsXG4gICAgbmFtZTogXCJ1aWRcIixcbiAgICB0eXBlOiBTdHJpbmcsXG4gIH0sXG4gIHtcbiAgICBhbGlhczogXCJ2XCIsXG4gICAgaGVscDogXCJ2ZXJib3NlIGxvZ3NcIixcbiAgICBuYW1lOiBcInZlcmJvc2VcIixcbiAgICB0eXBlOiBCb29sZWFuLFxuICB9LFxuICB7XG4gICAgZGVmYXVsdE9wdGlvbjogdHJ1ZSxcbiAgICBoZWxwOiBcImRpcmVjdG9yeSBjb250YWluaW5nIEFzc2VtYmzDqWUgb3BlbiBkYXRhIGZpbGVzXCIsXG4gICAgbmFtZTogXCJkYXRhRGlyXCIsXG4gICAgdHlwZTogU3RyaW5nLFxuICB9LFxuXVxuY29uc3Qgb3B0aW9ucyA9IGNvbW1hbmRMaW5lQXJncyhvcHRpb25zRGVmaW5pdGlvbnMpXG5cbmZ1bmN0aW9uIGNvbW1pdEFuZFB1c2goXG4gIHJlcG9zaXRvcnlEaXI6IHN0cmluZyxcbiAgY29tbWl0OiBib29sZWFuLFxuICByZW1vdGVzPzogc3RyaW5nW10sXG4pOiBib29sZWFuIHtcbiAgbGV0IGVycm9yID0gZmFsc2VcbiAgaWYgKGNvbW1pdCkge1xuICAgIGV4ZWNTeW5jKFwiZ2l0IGFkZCAuXCIsIHtcbiAgICAgIGN3ZDogcmVwb3NpdG9yeURpcixcbiAgICAgIGVudjogcHJvY2Vzcy5lbnYsXG4gICAgICBlbmNvZGluZzogXCJ1dGYtOFwiLFxuICAgICAgc3RkaW86IFtcImlnbm9yZVwiLCBcImlnbm9yZVwiLCBcInBpcGVcIl0sXG4gICAgfSlcbiAgICB0cnkge1xuICAgICAgZXhlY1N5bmMoJ2dpdCBjb21taXQgLW0gXCJOb3V2ZWxsZSBtb2lzc29uXCInLCB7XG4gICAgICAgIGN3ZDogcmVwb3NpdG9yeURpcixcbiAgICAgICAgZW52OiBwcm9jZXNzLmVudixcbiAgICAgICAgZW5jb2Rpbmc6IFwidXRmLThcIixcbiAgICAgIH0pXG4gICAgfSBjYXRjaCAoY2hpbGRQcm9jZXNzKSB7XG4gICAgICBpZiAoXG4gICAgICAgIGNoaWxkUHJvY2Vzcy5zdGRlcnIgPT09IG51bGwgfHxcbiAgICAgICAgIS9ub3RoaW5nIHRvIGNvbW1pdC8udGVzdChjaGlsZFByb2Nlc3Muc3Rkb3V0KVxuICAgICAgKSB7XG4gICAgICAgIGNvbnNvbGUuZXJyb3IoY2hpbGRQcm9jZXNzLm91dHB1dClcbiAgICAgICAgdGhyb3cgY2hpbGRQcm9jZXNzXG4gICAgICB9XG4gICAgfVxuICAgIGZvciAoY29uc3QgcmVtb3RlIG9mIHJlbW90ZXMgfHwgW10pIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGV4ZWNTeW5jKGBnaXQgcHVzaCAke3JlbW90ZX0gbWFzdGVyYCwge1xuICAgICAgICAgIGN3ZDogcmVwb3NpdG9yeURpcixcbiAgICAgICAgICBlbnY6IHByb2Nlc3MuZW52LFxuICAgICAgICAgIGVuY29kaW5nOiBcInV0Zi04XCIsXG4gICAgICAgICAgc3RkaW86IFtcImlnbm9yZVwiLCBcImlnbm9yZVwiLCBcInBpcGVcIl0sXG4gICAgICAgIH0pXG4gICAgICB9IGNhdGNoIChjaGlsZFByb2Nlc3MpIHtcbiAgICAgICAgLy8gRG9uJ3Qgc3RvcCB3aGVuIHB1c2ggZmFpbHMuXG4gICAgICAgIGNvbnNvbGUuZXJyb3IoY2hpbGRQcm9jZXNzLm91dHB1dClcbiAgICAgICAgZXJyb3IgPSB0cnVlXG4gICAgICB9XG4gICAgfVxuICB9XG4gIHJldHVybiBlcnJvclxufVxuXG5hc3luYyBmdW5jdGlvbiBjb252ZXJ0VGV4dGVzTG9pcygpOiBQcm9taXNlPHZvaWQ+IHtcbiAgYXNzZXJ0KFxuICAgICFvcHRpb25zLmNvbW1pdCB8fCBvcHRpb25zLm9uZSxcbiAgICAnT3B0aW9ucyBcImNvbW1pdFwiICYgXCJvbmVcIiBhcmUgaW5jb21wYXRpYmxlJyxcbiAgKVxuICBhc3NlcnQoXG4gICAgIW9wdGlvbnMuY29tbWl0IHx8IG9wdGlvbnMudWlkLFxuICAgICdPcHRpb25zIFwiY29tbWl0XCIgJiBcInVpZFwiIGFyZSBpbmNvbXBhdGlibGUnLFxuICApXG5cbiAgY29uc3QgZGF0YURpciA9IG9wdGlvbnMuZGF0YURpclxuICBjb25zdCB7IGRvY3VtZW50QnlVaWQgfSA9IGxvYWRBc3NlbWJsZWVEYXRhKFxuICAgIGRhdGFEaXIsXG4gICAgRW5hYmxlZERhdGFzZXRzLkRvc3NpZXJzTGVnaXNsYXRpZnMsXG4gICAgb3B0aW9ucy5sZWdpc2xhdHVyZSxcbiAgKVxuXG4gIGNvbnN0IGRvY3VtZW50c1Jhd0h0bWxEaXIgPSBwYXRoLmpvaW4oZGF0YURpciwgXCJkb2N1bWVudHNfaHRtbFwiKVxuICBhc3NlcnQoXG4gICAgZnMuZXhpc3RzU3luYyhkb2N1bWVudHNSYXdIdG1sRGlyKSxcbiAgICBgRGlyZWN0b3J5IFwiJHtkb2N1bWVudHNSYXdIdG1sRGlyfVwiIGRvZXNuJ3QgZXhpc3RgLFxuICApXG5cbiAgY29uc3QgZG9jdW1lbnRzQ2xlYW5IdG1sRGlyID0gcGF0aC5qb2luKGRhdGFEaXIsIFwiZG9jdW1lbnRzX2h0bWxfbmV0dG95ZVwiKVxuICBmcy5lbnN1cmVEaXJTeW5jKGRvY3VtZW50c0NsZWFuSHRtbERpcilcbiAgaWYgKG9wdGlvbnMuZnVsbCAmJiAhb3B0aW9ucy5vbmUgJiYgIW9wdGlvbnMudWlkKSB7XG4gICAgZm9yIChjb25zdCBmaWxlbmFtZSBvZiBmcy5yZWFkZGlyU3luYyhkb2N1bWVudHNDbGVhbkh0bWxEaXIpKSB7XG4gICAgICBpZiAoZmlsZW5hbWVbMF0gPT09IFwiLlwiKSB7XG4gICAgICAgIGNvbnRpbnVlXG4gICAgICB9XG4gICAgICBmcy5yZW1vdmVTeW5jKHBhdGguam9pbihkb2N1bWVudHNDbGVhbkh0bWxEaXIsIGZpbGVuYW1lKSlcbiAgICB9XG4gIH1cblxuICBjb25zdCBkb2N1bWVudHMgPSBPYmplY3QudmFsdWVzKGRvY3VtZW50QnlVaWQpXG4gICAgLy8gSWdub3JlIGRvY3VtZW50cyBmcm9tIFPDqW5hdC5cbiAgICAuZmlsdGVyKChkb2N1bWVudCkgPT4gZG9jdW1lbnQudWlkLnN1YnN0cmluZyg0LCA2KSAhPT0gXCJTTlwiKVxuICAgIC5zb3J0KChhLCBiKSA9PiBhLnVpZC5sb2NhbGVDb21wYXJlKGIudWlkKSlcblxuICBjb25zdCBmaXJzdFVpZCA9IG9wdGlvbnMudWlkXG4gIGxldCBza2lwID0gISFmaXJzdFVpZFxuICBmb3IgKGNvbnN0IGRvY3VtZW50IG9mIGRvY3VtZW50cykge1xuICAgIGlmIChza2lwKSB7XG4gICAgICBpZiAoZG9jdW1lbnQudWlkID09PSBmaXJzdFVpZCkge1xuICAgICAgICBza2lwID0gZmFsc2VcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGNvbnRpbnVlXG4gICAgICB9XG4gICAgfVxuXG4gICAgY29uc3QgZG9jdW1lbnRDbGVhbkh0bWxCYXNlbmFtZSA9IHBhdGhGcm9tRG9jdW1lbnRVaWQoXG4gICAgICBkb2N1bWVudHNDbGVhbkh0bWxEaXIsXG4gICAgICBkb2N1bWVudC51aWQsXG4gICAgKVxuICAgIGNvbnN0IGRvY3VtZW50Q2xlYW5IdG1sRmlsZVBhdGggPSBgJHtkb2N1bWVudENsZWFuSHRtbEJhc2VuYW1lfS5odG1sYFxuICAgIGlmICghb3B0aW9ucy5mdWxsICYmIGZzLmV4aXN0c1N5bmMoZG9jdW1lbnRDbGVhbkh0bWxGaWxlUGF0aCkpIHtcbiAgICAgIGNvbnRpbnVlXG4gICAgfVxuXG4gICAgY29uc3QgZG9jdW1lbnRSYXdIdG1sQmFzZW5hbWUgPSBwYXRoRnJvbURvY3VtZW50VWlkKFxuICAgICAgZG9jdW1lbnRzUmF3SHRtbERpcixcbiAgICAgIGRvY3VtZW50LnVpZCxcbiAgICApXG4gICAgY29uc3QgZG9jdW1lbnRSYXdIdG1sRmlsZVBhdGggPSBgJHtkb2N1bWVudFJhd0h0bWxCYXNlbmFtZX0uaHRtbGBcbiAgICBpZiAoIWZzLmV4aXN0c1N5bmMoZG9jdW1lbnRSYXdIdG1sRmlsZVBhdGgpKSB7XG4gICAgICBjb250aW51ZVxuICAgIH1cblxuICAgIGlmICghb3B0aW9ucy5zaWxlbnQpIHtcbiAgICAgIGNvbnNvbGUubG9nKGBDbGVhbmluZyBIVE1MIG9mIGRvY3VtZW50ICR7ZG9jdW1lbnQudWlkfeKApmApXG4gICAgfVxuXG4gICAgY29uc3QgZG9jdW1lbnRSYXdIdG1sID0gZnMucmVhZEZpbGVTeW5jKGRvY3VtZW50UmF3SHRtbEZpbGVQYXRoLCB7XG4gICAgICBlbmNvZGluZzogXCJ1dGY4XCIsXG4gICAgfSlcblxuICAgIGxldCBkb2N1bWVudEh0bWwgPSBkb2N1bWVudFJhd0h0bWxcbiAgICBkb2N1bWVudEh0bWwgPSByZW1vdmVMZXR0ZXJTcGFjaW5nU3R5bGVBdHRyaWJ1dGVzKGRvY3VtZW50SHRtbClcbiAgICBkb2N1bWVudEh0bWwgPSByZW1vdmVFbXB0eVN0eWxlQXR0cmlidXRlcyhkb2N1bWVudEh0bWwpXG5cbiAgICBjb25zdCBkb2N1bWVudFBhcnNlNUFzdCA9IHBhcnNlNS5wYXJzZShkb2N1bWVudEh0bWwsIHtcbiAgICAgIHNvdXJjZUNvZGVMb2NhdGlvbkluZm86IHRydWUsXG4gICAgfSlcbiAgICBjb25zdCBkb2N1bWVudFZmaWxlID0gdmZpbGUoe1xuICAgICAgY29udGVudHM6IGRvY3VtZW50UmF3SHRtbCxcbiAgICAgIHBhdGg6IGRvY3VtZW50UmF3SHRtbEZpbGVQYXRoLFxuICAgIH0pXG4gICAgY29uc3QgZG9jdW1lbnRIYXN0ID0gKGhhc3RGcm9tUGFyc2U1KGRvY3VtZW50UGFyc2U1QXN0LCB7XG4gICAgICBmaWxlOiBkb2N1bWVudFZmaWxlLFxuICAgIH0pIGFzIHVua25vd24pIGFzIEhhc3RSb290XG4gICAgdW5pc3RSZW1vdmVQb3NpdGlvbihkb2N1bWVudEhhc3QpXG5cbiAgICByZW1vdmVTdHlsZUVsZW1lbnRzKGRvY3VtZW50SGFzdClcbiAgICBtZXJnZVNwYW5FbGVtZW50c1dpdGhTYW1lQXR0cmlidXRlcyhkb2N1bWVudEhhc3QpXG4gICAgcmVwbGFjZVNwYW5FbGVtZW50c0NvbnRhaW5pbmdPbmx5U3BhY2VzV2l0aFRleHRzKGRvY3VtZW50SGFzdClcbiAgICByZXBsYWNlU3BhbkVsZW1lbnRzV2l0aG91dFByb3BlcnRpZXNXaXRoVGV4dHMoZG9jdW1lbnRIYXN0KVxuICAgIG1lcmdlVGV4dHMoZG9jdW1lbnRIYXN0KVxuXG4gICAgY29uc3QgZG9jdW1lbnRDbGVhbkh0bWwgPSBwcmV0dGllci5mb3JtYXQoaGFzdFRvSHRtbChkb2N1bWVudEhhc3QpLCB7XG4gICAgICBwYXJzZXI6IFwiaHRtbFwiLFxuICAgIH0pXG5cbiAgICBmcy53cml0ZUZpbGVTeW5jKGRvY3VtZW50Q2xlYW5IdG1sRmlsZVBhdGgsIGRvY3VtZW50Q2xlYW5IdG1sLCB7XG4gICAgICBlbmNvZGluZzogXCJ1dGY4XCIsXG4gICAgfSlcblxuICAgIGlmIChvcHRpb25zLm9uZSkge1xuICAgICAgYnJlYWtcbiAgICB9XG4gIH1cblxuICBpZiAoY29tbWl0QW5kUHVzaChkb2N1bWVudHNDbGVhbkh0bWxEaXIsIG9wdGlvbnMuY29tbWl0LCBvcHRpb25zLnJlbW90ZSkpIHtcbiAgICBwcm9jZXNzLmV4aXQoMSlcbiAgfVxufVxuXG5jb252ZXJ0VGV4dGVzTG9pcygpLmNhdGNoKChlcnJvcikgPT4ge1xuICBjb25zb2xlLmxvZyhlcnJvcilcbiAgcHJvY2Vzcy5leGl0KDEpXG59KVxuIl19