appium-doctor
Version:
Test environment for fitness to run Appium
548 lines (433 loc) • 26.8 kB
JavaScript
;
var _get = require('babel-runtime/helpers/get')['default'];
var _inherits = require('babel-runtime/helpers/inherits')['default'];
var _classCallCheck = require('babel-runtime/helpers/class-call-check')['default'];
var _createClass = require('babel-runtime/helpers/create-class')['default'];
var _regeneratorRuntime = require('babel-runtime/regenerator')['default'];
var _getIterator = require('babel-runtime/core-js/get-iterator')['default'];
var _interopRequireDefault = require('babel-runtime/helpers/interop-require-default')['default'];
Object.defineProperty(exports, '__esModule', {
value: true
});
require('colors');
var _lodash = require('lodash');
var _lodash2 = _interopRequireDefault(_lodash);
var _logger = require('./logger');
var _logger2 = _interopRequireDefault(_logger);
var FixSkippedError = (function (_Error) {
_inherits(FixSkippedError, _Error);
function FixSkippedError() {
_classCallCheck(this, FixSkippedError);
_get(Object.getPrototypeOf(FixSkippedError.prototype), 'constructor', this).apply(this, arguments);
}
return FixSkippedError;
})(Error);
var DoctorCheck = (function () {
function DoctorCheck() {
var opts = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];
_classCallCheck(this, DoctorCheck);
this.autofix = !!opts.autofix;
}
_createClass(DoctorCheck, [{
key: 'diagnose',
value: function diagnose() {
throw new Error('Not Implemented!');
}
}, {
key: 'fix',
value: function fix() {
// return string for manual fixes.
throw new Error('Not Implemented!');
}
}]);
return DoctorCheck;
})();
var Doctor = (function () {
function Doctor() {
_classCallCheck(this, Doctor);
this.checks = [];
this.toFix = [];
}
_createClass(Doctor, [{
key: 'register',
value: function register(checks) {
checks = Array.isArray(checks) ? checks : [checks];
this.checks = this.checks.concat(checks);
}
}, {
key: 'diagnose',
value: function diagnose() {
var _iteratorNormalCompletion, _didIteratorError, _iteratorError, _iterator, _step, check, res, errorMessage, fixMessage;
return _regeneratorRuntime.async(function diagnose$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
_logger2['default'].info('### Diagnostic starting ###');
this.toFix = [];
_iteratorNormalCompletion = true;
_didIteratorError = false;
_iteratorError = undefined;
context$2$0.prev = 5;
_iterator = _getIterator(this.checks);
case 7:
if (_iteratorNormalCompletion = (_step = _iterator.next()).done) {
context$2$0.next = 16;
break;
}
check = _step.value;
context$2$0.next = 11;
return _regeneratorRuntime.awrap(check.diagnose());
case 11:
res = context$2$0.sent;
if (res.ok) {
_logger2['default'].info(' ' + '✔'.green + ' ' + res.message);
} else {
errorMessage = ' ' + '✖'.red + ' ' + res.message;
_logger2['default'].warn(errorMessage);
this.toFix.push({
error: errorMessage,
check: check
});
}
case 13:
_iteratorNormalCompletion = true;
context$2$0.next = 7;
break;
case 16:
context$2$0.next = 22;
break;
case 18:
context$2$0.prev = 18;
context$2$0.t0 = context$2$0['catch'](5);
_didIteratorError = true;
_iteratorError = context$2$0.t0;
case 22:
context$2$0.prev = 22;
context$2$0.prev = 23;
if (!_iteratorNormalCompletion && _iterator['return']) {
_iterator['return']();
}
case 25:
context$2$0.prev = 25;
if (!_didIteratorError) {
context$2$0.next = 28;
break;
}
throw _iteratorError;
case 28:
return context$2$0.finish(25);
case 29:
return context$2$0.finish(22);
case 30:
fixMessage = undefined;
context$2$0.t1 = this.toFix.length;
context$2$0.next = context$2$0.t1 === 0 ? 34 : context$2$0.t1 === 1 ? 36 : 38;
break;
case 34:
fixMessage = 'no fix needed';
return context$2$0.abrupt('break', 39);
case 36:
fixMessage = 'one fix needed';
return context$2$0.abrupt('break', 39);
case 38:
fixMessage = this.toFix.length + ' fixes needed';
case 39:
_logger2['default'].info('### Diagnostic completed, ' + fixMessage + '. ###');
_logger2['default'].info('');
case 41:
case 'end':
return context$2$0.stop();
}
}, null, this, [[5, 18, 22, 30], [23,, 25, 29]]);
}
}, {
key: 'reportSuccess',
value: function reportSuccess() {
return _regeneratorRuntime.async(function reportSuccess$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
if (!(this.toFix.length === 0)) {
context$2$0.next = 6;
break;
}
_logger2['default'].info('Everything looks good, bye!');
_logger2['default'].info('');
return context$2$0.abrupt('return', true);
case 6:
return context$2$0.abrupt('return', false);
case 7:
case 'end':
return context$2$0.stop();
}
}, null, this);
}
}, {
key: 'reportManualFixes',
value: function reportManualFixes() {
var manualFixes, fixMessages, _iteratorNormalCompletion2, _didIteratorError2, _iteratorError2, _iterator2, _step2, f, _iteratorNormalCompletion3, _didIteratorError3, _iteratorError3, _iterator3, _step3, m;
return _regeneratorRuntime.async(function reportManualFixes$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
manualFixes = _lodash2['default'].filter(this.toFix, function (f) {
return !f.check.autofix;
});
if (!(manualFixes.length > 0)) {
context$2$0.next = 60;
break;
}
_logger2['default'].info('### Manual Fixes Needed ###');
_logger2['default'].info('The configuration cannot be automatically fixed, please do the following first:');
// for manual fixes, the fix method always return a string
fixMessages = [];
_iteratorNormalCompletion2 = true;
_didIteratorError2 = false;
_iteratorError2 = undefined;
context$2$0.prev = 8;
_iterator2 = _getIterator(manualFixes);
case 10:
if (_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done) {
context$2$0.next = 20;
break;
}
f = _step2.value;
context$2$0.t0 = fixMessages;
context$2$0.next = 15;
return _regeneratorRuntime.awrap(f.check.fix());
case 15:
context$2$0.t1 = context$2$0.sent;
context$2$0.t0.push.call(context$2$0.t0, context$2$0.t1);
case 17:
_iteratorNormalCompletion2 = true;
context$2$0.next = 10;
break;
case 20:
context$2$0.next = 26;
break;
case 22:
context$2$0.prev = 22;
context$2$0.t2 = context$2$0['catch'](8);
_didIteratorError2 = true;
_iteratorError2 = context$2$0.t2;
case 26:
context$2$0.prev = 26;
context$2$0.prev = 27;
if (!_iteratorNormalCompletion2 && _iterator2['return']) {
_iterator2['return']();
}
case 29:
context$2$0.prev = 29;
if (!_didIteratorError2) {
context$2$0.next = 32;
break;
}
throw _iteratorError2;
case 32:
return context$2$0.finish(29);
case 33:
return context$2$0.finish(26);
case 34:
_iteratorNormalCompletion3 = true;
_didIteratorError3 = false;
_iteratorError3 = undefined;
context$2$0.prev = 37;
for (_iterator3 = _getIterator(_lodash2['default'].uniq(fixMessages)); !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
m = _step3.value;
_logger2['default'].warn('- ' + m);
}
context$2$0.next = 45;
break;
case 41:
context$2$0.prev = 41;
context$2$0.t3 = context$2$0['catch'](37);
_didIteratorError3 = true;
_iteratorError3 = context$2$0.t3;
case 45:
context$2$0.prev = 45;
context$2$0.prev = 46;
if (!_iteratorNormalCompletion3 && _iterator3['return']) {
_iterator3['return']();
}
case 48:
context$2$0.prev = 48;
if (!_didIteratorError3) {
context$2$0.next = 51;
break;
}
throw _iteratorError3;
case 51:
return context$2$0.finish(48);
case 52:
return context$2$0.finish(45);
case 53:
_logger2['default'].info('###');
_logger2['default'].info('');
_logger2['default'].info('Bye, run appium-doctor again when all manual fixes have been applied!');
_logger2['default'].info('');
return context$2$0.abrupt('return', true);
case 60:
return context$2$0.abrupt('return', false);
case 61:
case 'end':
return context$2$0.stop();
}
}, null, this, [[8, 22, 26, 34], [27,, 29, 33], [37, 41, 45, 53], [46,, 48, 52]]);
}
}, {
key: 'runAutoFix',
value: function runAutoFix(f) {
var res;
return _regeneratorRuntime.async(function runAutoFix$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
_logger2['default'].info('### Fixing: ' + f.error + ' ###');
context$2$0.prev = 1;
context$2$0.next = 4;
return _regeneratorRuntime.awrap(f.check.fix());
case 4:
context$2$0.next = 16;
break;
case 6:
context$2$0.prev = 6;
context$2$0.t0 = context$2$0['catch'](1);
if (!(context$2$0.t0 instanceof FixSkippedError)) {
context$2$0.next = 13;
break;
}
_logger2['default'].info('### Skipped fix ###');
return context$2$0.abrupt('return');
case 13:
_logger2['default'].warn(('' + context$2$0.t0).replace(/\n$/g, ''));
_logger2['default'].info('### Fix did not succeed ###');
return context$2$0.abrupt('return');
case 16:
_logger2['default'].info('Checking if this was fixed:');
context$2$0.next = 19;
return _regeneratorRuntime.awrap(f.check.diagnose());
case 19:
res = context$2$0.sent;
if (res.ok) {
f.fixed = true;
_logger2['default'].info(' ' + '✔'.green + ' ' + res.message);
_logger2['default'].info('### Fix was successfully applied ###');
} else {
_logger2['default'].info(' ' + '✖'.red + ' ' + res.message);
_logger2['default'].info('### Fix was applied but issue remains ###');
}
case 21:
case 'end':
return context$2$0.stop();
}
}, null, this, [[1, 6]]);
}
}, {
key: 'runAutoFixes',
value: function runAutoFixes() {
var autoFixes, _iteratorNormalCompletion4, _didIteratorError4, _iteratorError4, _iterator4, _step4, f;
return _regeneratorRuntime.async(function runAutoFixes$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
autoFixes = _lodash2['default'].filter(this.toFix, function (f) {
return f.check.autofix;
});
_iteratorNormalCompletion4 = true;
_didIteratorError4 = false;
_iteratorError4 = undefined;
context$2$0.prev = 4;
_iterator4 = _getIterator(autoFixes);
case 6:
if (_iteratorNormalCompletion4 = (_step4 = _iterator4.next()).done) {
context$2$0.next = 14;
break;
}
f = _step4.value;
context$2$0.next = 10;
return _regeneratorRuntime.awrap(this.runAutoFix(f));
case 10:
_logger2['default'].info('');
case 11:
_iteratorNormalCompletion4 = true;
context$2$0.next = 6;
break;
case 14:
context$2$0.next = 20;
break;
case 16:
context$2$0.prev = 16;
context$2$0.t0 = context$2$0['catch'](4);
_didIteratorError4 = true;
_iteratorError4 = context$2$0.t0;
case 20:
context$2$0.prev = 20;
context$2$0.prev = 21;
if (!_iteratorNormalCompletion4 && _iterator4['return']) {
_iterator4['return']();
}
case 23:
context$2$0.prev = 23;
if (!_didIteratorError4) {
context$2$0.next = 26;
break;
}
throw _iteratorError4;
case 26:
return context$2$0.finish(23);
case 27:
return context$2$0.finish(20);
case 28:
if (_lodash2['default'].find(autoFixes, function (f) {
return !f.fixed;
})) {
// a few issues remain.
_logger2['default'].info('Bye, a few issues remain, fix manually and/or rerun appium-doctor!');
} else {
// nothing left to fix.
_logger2['default'].info('Bye, all issues have been fixed!');
}
_logger2['default'].info('');
case 30:
case 'end':
return context$2$0.stop();
}
}, null, this, [[4, 16, 20, 28], [21,, 23, 27]]);
}
}, {
key: 'run',
value: function run() {
return _regeneratorRuntime.async(function run$(context$2$0) {
while (1) switch (context$2$0.prev = context$2$0.next) {
case 0:
context$2$0.next = 2;
return _regeneratorRuntime.awrap(this.diagnose());
case 2:
context$2$0.next = 4;
return _regeneratorRuntime.awrap(this.reportSuccess());
case 4:
if (!context$2$0.sent) {
context$2$0.next = 6;
break;
}
return context$2$0.abrupt('return');
case 6:
context$2$0.next = 8;
return _regeneratorRuntime.awrap(this.reportManualFixes());
case 8:
if (!context$2$0.sent) {
context$2$0.next = 10;
break;
}
return context$2$0.abrupt('return');
case 10:
context$2$0.next = 12;
return _regeneratorRuntime.awrap(this.runAutoFixes());
case 12:
case 'end':
return context$2$0.stop();
}
}, null, this);
}
}]);
return Doctor;
})();
exports.Doctor = Doctor;
exports.DoctorCheck = DoctorCheck;
exports.FixSkippedError = FixSkippedError;
//# sourceMappingURL=data:application/json;base64,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Q0FBQzthQUFFLENBQUMsRUFBRTs7QUFFakQsa0NBQUksSUFBSSxDQUFDLG9FQUFvRSxDQUFDLENBQUM7YUFDaEYsTUFBTTs7QUFFTCxrQ0FBSSxJQUFJLENBQUMsa0NBQWtDLENBQUMsQ0FBQzthQUM5QztBQUNELGdDQUFJLElBQUksQ0FBQyxFQUFFLENBQUMsQ0FBQzs7Ozs7OztLQUNkOzs7V0FFUzs7Ozs7NkNBQ0YsSUFBSSxDQUFDLFFBQVEsRUFBRTs7Ozs2Q0FDWCxJQUFJLENBQUMsYUFBYSxFQUFFOzs7Ozs7Ozs7Ozs7NkNBR3BCLElBQUksQ0FBQyxpQkFBaUIsRUFBRTs7Ozs7Ozs7Ozs7OzZDQUc1QixJQUFJLENBQUMsWUFBWSxFQUFFOzs7Ozs7O0tBQzFCOzs7U0E5SEcsTUFBTTs7O1FBaUlILE1BQU0sR0FBTixNQUFNO1FBQUUsV0FBVyxHQUFYLFdBQVc7UUFBRSxlQUFlLEdBQWYsZUFBZSIsImZpbGUiOiJsaWIvZG9jdG9yLmpzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0ICdjb2xvcnMnO1xuaW1wb3J0IF8gZnJvbSAnbG9kYXNoJztcbmltcG9ydCBsb2cgZnJvbSAnLi9sb2dnZXInO1xuXG5jbGFzcyBGaXhTa2lwcGVkRXJyb3IgZXh0ZW5kcyBFcnJvciB7XG59XG5cbmNsYXNzIERvY3RvckNoZWNrIHtcbiAgY29uc3RydWN0b3Iob3B0cz17fSkge1xuICAgIHRoaXMuYXV0b2ZpeCA9ICEhb3B0cy5hdXRvZml4O1xuICB9XG5cbiAgZGlhZ25vc2UgKCkgeyB0aHJvdyBuZXcgRXJyb3IoJ05vdCBJbXBsZW1lbnRlZCEnKTsgfVxuXG4gIGZpeCAoKSB7XG4gICAgLy8gcmV0dXJuIHN0cmluZyBmb3IgbWFudWFsIGZpeGVzLlxuICAgIHRocm93IG5ldyBFcnJvcignTm90IEltcGxlbWVudGVkIScpO1xuICB9XG59XG5cbmNsYXNzIERvY3RvciB7XG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIHRoaXMuY2hlY2tzID0gW107XG4gICAgdGhpcy50b0ZpeCA9IFtdO1xuICB9XG5cbiAgcmVnaXN0ZXIgKGNoZWNrcykge1xuICAgIGNoZWNrcyA9IEFycmF5LmlzQXJyYXkoY2hlY2tzKSA/IGNoZWNrcyA6IFtjaGVja3NdO1xuICAgIHRoaXMuY2hlY2tzID0gdGhpcy5jaGVja3MuY29uY2F0KGNoZWNrcyk7XG4gIH1cblxuICBhc3luYyBkaWFnbm9zZSgpIHtcbiAgICBsb2cuaW5mbygnIyMjIERpYWdub3N0aWMgc3RhcnRpbmcgIyMjJyk7XG4gICAgdGhpcy50b0ZpeCA9IFtdO1xuICAgIGZvciAobGV0IGNoZWNrIG9mIHRoaXMuY2hlY2tzKSB7XG4gICAgICBsZXQgcmVzID0gYXdhaXQgY2hlY2suZGlhZ25vc2UoKTtcbiAgICAgIGlmIChyZXMub2spIHtcbiAgICAgICAgbG9nLmluZm8oYCAkeydcXHUyNzE0Jy5ncmVlbn0gJHtyZXMubWVzc2FnZX1gKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxldCBlcnJvck1lc3NhZ2UgPSBgICR7J1xcdTI3MTYnLnJlZH0gJHtyZXMubWVzc2FnZX1gO1xuICAgICAgICBsb2cud2FybihlcnJvck1lc3NhZ2UpO1xuICAgICAgICB0aGlzLnRvRml4LnB1c2goe1xuICAgICAgICAgIGVycm9yOiBlcnJvck1lc3NhZ2UsXG4gICAgICAgICAgY2hlY2s6IGNoZWNrXG4gICAgICAgIH0pO1xuICAgICAgfVxuICAgIH1cbiAgICBsZXQgZml4TWVzc2FnZTtcbiAgICBzd2l0Y2ggKHRoaXMudG9GaXgubGVuZ3RoKSB7XG4gICAgICBjYXNlIDA6XG4gICAgICAgIGZpeE1lc3NhZ2UgPSAnbm8gZml4IG5lZWRlZCc7XG4gICAgICAgIGJyZWFrO1xuICAgICAgY2FzZSAxOlxuICAgICAgICBmaXhNZXNzYWdlID0gJ29uZSBmaXggbmVlZGVkJztcbiAgICAgICAgYnJlYWs7XG4gICAgICBkZWZhdWx0OlxuICAgICAgICBmaXhNZXNzYWdlID0gYCR7dGhpcy50b0ZpeC5sZW5ndGh9IGZpeGVzIG5lZWRlZGA7XG4gICAgfVxuICAgIGxvZy5pbmZvKGAjIyMgRGlhZ25vc3RpYyBjb21wbGV0ZWQsICR7Zml4TWVzc2FnZX0uICMjI2ApO1xuICAgIGxvZy5pbmZvKCcnKTtcbiAgfVxuXG4gIGFzeW5jIHJlcG9ydFN1Y2Nlc3MgKCkge1xuICAgIGlmICh0aGlzLnRvRml4Lmxlbmd0aCA9PT0gMCkge1xuICAgICAgbG9nLmluZm8oJ0V2ZXJ5dGhpbmcgbG9va3MgZ29vZCwgYnllIScpO1xuICAgICAgbG9nLmluZm8oJycpO1xuICAgICAgcmV0dXJuIHRydWU7XG4gICAgfSBlbHNlIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gIH1cblxuICBhc3luYyByZXBvcnRNYW51YWxGaXhlcyAoKSB7XG4gICAgbGV0IG1hbnVhbEZpeGVzID0gXy5maWx0ZXIodGhpcy50b0ZpeCwgKGYpID0+IHtyZXR1cm4gIWYuY2hlY2suYXV0b2ZpeDt9KTtcbiAgICBpZiAobWFudWFsRml4ZXMubGVuZ3RoID4wKSB7XG4gICAgICBsb2cuaW5mbygnIyMjIE1hbnVhbCBGaXhlcyBOZWVkZWQgIyMjJyk7XG4gICAgICBsb2cuaW5mbygnVGhlIGNvbmZpZ3VyYXRpb24gY2Fubm90IGJlIGF1dG9tYXRpY2FsbHkgZml4ZWQsIHBsZWFzZSBkbyB0aGUgZm9sbG93aW5nIGZpcnN0OicpO1xuICAgICAgLy8gZm9yIG1hbnVhbCBmaXhlcywgdGhlIGZpeCBtZXRob2QgYWx3YXlzIHJldHVybiBhIHN0cmluZ1xuICAgICAgbGV0IGZpeE1lc3NhZ2VzID0gW107XG4gICAgICBmb3IgKGxldCBmIG9mIG1hbnVhbEZpeGVzKSB7XG4gICAgICAgIGZpeE1lc3NhZ2VzLnB1c2goYXdhaXQgZi5jaGVjay5maXgoKSk7XG4gICAgICB9XG4gICAgICBmb3IgKGxldCBtIG9mIF8udW5pcShmaXhNZXNzYWdlcykpIHtcbiAgICAgICAgbG9nLndhcm4oYC0gJHttfWApO1xuICAgICAgfVxuICAgICAgbG9nLmluZm8oJyMjIycpO1xuICAgICAgbG9nLmluZm8oJycpO1xuICAgICAgbG9nLmluZm8oJ0J5ZSwgcnVuIGFwcGl1bS1kb2N0b3IgYWdhaW4gd2hlbiBhbGwgbWFudWFsIGZpeGVzIGhhdmUgYmVlbiBhcHBsaWVkIScpO1xuICAgICAgbG9nLmluZm8oJycpO1xuICAgICAgcmV0dXJuIHRydWU7XG4gICAgfSBlbHNlIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG4gIH1cblxuICBhc3luYyBydW5BdXRvRml4IChmKSB7XG4gICAgbG9nLmluZm8oYCMjIyBGaXhpbmc6ICR7Zi5lcnJvcn0gIyMjYCk7XG4gICAgdHJ5IHtcbiAgICAgIGF3YWl0IGYuY2hlY2suZml4KCk7XG4gICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICBpZiAoZXJyIGluc3RhbmNlb2YgRml4U2tpcHBlZEVycm9yKSB7XG4gICAgICAgIGxvZy5pbmZvKGAjIyMgU2tpcHBlZCBmaXggIyMjYCk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGxvZy53YXJuKGAke2Vycn1gLnJlcGxhY2UoL1xcbiQvZywgJycpKTtcbiAgICAgICAgbG9nLmluZm8oYCMjIyBGaXggZGlkIG5vdCBzdWNjZWVkICMjI2ApO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgfVxuICAgIGxvZy5pbmZvKCdDaGVja2luZyBpZiB0aGlzIHdhcyBmaXhlZDonKTtcbiAgICBsZXQgcmVzID0gYXdhaXQgZi5jaGVjay5kaWFnbm9zZSgpO1xuICAgIGlmIChyZXMub2spIHtcbiAgICAgIGYuZml4ZWQgPSB0cnVlO1xuICAgICAgbG9nLmluZm8oYCAkeydcXHUyNzE0Jy5ncmVlbn0gJHtyZXMubWVzc2FnZX1gKTtcbiAgICAgIGxvZy5pbmZvKGAjIyMgRml4IHdhcyBzdWNjZXNzZnVsbHkgYXBwbGllZCAjIyNgKTtcbiAgICB9IGVsc2Uge1xuICAgICAgbG9nLmluZm8oYCAkeydcXHUyNzE2Jy5yZWR9ICR7cmVzLm1lc3NhZ2V9YCk7XG4gICAgICBsb2cuaW5mbyhgIyMjIEZpeCB3YXMgYXBwbGllZCBidXQgaXNzdWUgcmVtYWlucyAjIyNgKTtcbiAgICB9XG4gIH1cblxuICBhc3luYyBydW5BdXRvRml4ZXMgKCkge1xuICAgIGxldCBhdXRvRml4ZXMgPSBfLmZpbHRlcih0aGlzLnRvRml4LCAoZikgPT4ge3JldHVybiBmLmNoZWNrLmF1dG9maXg7fSk7XG4gICAgZm9yIChsZXQgZiBvZiBhdXRvRml4ZXMpIHtcbiAgICAgIGF3YWl0IHRoaXMucnVuQXV0b0ZpeChmKTtcbiAgICAgIGxvZy5pbmZvKCcnKTtcbiAgICB9XG4gICAgaWYoXy5maW5kKGF1dG9GaXhlcywgKGYpID0+IHsgcmV0dXJuICFmLmZpeGVkOyB9KSkge1xuICAgICAgLy8gYSBmZXcgaXNzdWVzIHJlbWFpbi5cbiAgICAgIGxvZy5pbmZvKCdCeWUsIGEgZmV3IGlzc3VlcyByZW1haW4sIGZpeCBtYW51YWxseSBhbmQvb3IgcmVydW4gYXBwaXVtLWRvY3RvciEnKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gbm90aGluZyBsZWZ0IHRvIGZpeC5cbiAgICAgIGxvZy5pbmZvKCdCeWUsIGFsbCBpc3N1ZXMgaGF2ZSBiZWVuIGZpeGVkIScpO1xuICAgIH1cbiAgICBsb2cuaW5mbygnJyk7XG4gIH1cblxuICBhc3luYyBydW4gKCkge1xuICAgIGF3YWl0IHRoaXMuZGlhZ25vc2UoKTtcbiAgICBpZiAoYXdhaXQgdGhpcy5yZXBvcnRTdWNjZXNzKCkpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgaWYgKGF3YWl0IHRoaXMucmVwb3J0TWFudWFsRml4ZXMoKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBhd2FpdCB0aGlzLnJ1bkF1dG9GaXhlcygpO1xuICB9XG59XG5cbmV4cG9ydCB7IERvY3RvciwgRG9jdG9yQ2hlY2ssIEZpeFNraXBwZWRFcnJvciB9O1xuIl19