UNPKG

iostatus

Version:
177 lines (175 loc) 26.3 kB
var _ = require("lodash"); var Promise = require("bluebird"); var bodyParser = require("body-parser"); var pathExists = require("path-exists"); var IO = require("socket.io"); var express = require("express"); var jwt = require("jsonwebtoken"); var redis = require("redis"); var couchjsonconf = require("couchjsonconf"); var machClients = require("./modules/machClients"); var audClients = require("./modules/audClients"); var socketioJwt = require("socketio-jwt"); var rpj = require('request-promise-json'); var mosca = require("mosca"); var app = express(); var server = require('http').Server(app); var io = IO(server); if (!pathExists.sync('./conf.json')) { throw Error('no configuration founded'); } var conf = require('./conf.json'); var COUCHDB = new couchjsonconf(conf.couchdb); var Machines = new machClients(COUCHDB); var Auditors = new audClients(); app.use(bodyParser.urlencoded({ extended: false })); app.use(bodyParser.json()); io.use(socketioJwt.authorize({ secret: conf.secret, handshake: true })); server.listen(conf.port); var ascoltatore = { type: 'redis', redis: redis, db: 12, port: 6379, return_buffers: true, host: "localhost" }; var moscaSettings = { port: 1883, backend: ascoltatore, persistence: { factory: mosca.persistence.Redis } }; var mqttserver = new mosca.Server(moscaSettings); mqttserver.on('ready', setupmqtt); mqttserver.on('clientConnected', function (client) { console.log('client connected', client.id); }); mqttserver.on('published', function (packet, client) { console.log('Published', packet.payload); }); function setupmqtt() { console.log('Mosca server is up and running'); } app.get('/', function (req, res) { res.json({ online: true }); }); function authcouch(user, password, db) { return new Promise(function (resolve, reject) { rpj.get(COUCHDB.for(user, password, db)).then(function () { resolve({ success: true }); }).catch(function (err) { reject({ error: 'wrong credentials' }); }); }); } function authorizesocket(profile) { return jwt.sign(profile, conf.secret, { expiresInMinutes: 60 * 5 }); } app.post('/login', function (req, res) { authcouch(req.body.user, req.body.password, req.body.db).then(function () { var token = authorizesocket({ user: req.body.user, password: req.body.password, db: req.body.db, serial: req.body.serial }); res.json({ success: true, token: token }); }).catch(function (err) { res.json(err); }); }); app.get('/ip', function (req, res) { res.json({ ip: req.headers['x-forwarded-for'] }); }); app.get('/sockets', function (req, res) { res.json(Machines.sockets()); }); app.get('/machines/:serial/sockets', function (req, res) { res.json(Machines.sockets(req.params.serial)); }); app.get('/machines', function (req, res) { res.json(Machines.list()); }); app.get('/app/:app/machines', function (req, res) { }); app.get('/machines/:serial/message/:message', function (req, res) { _.map(Machines.ios(req.params.serial), function (socket) { socket.emit('message', req.params.message); }); res.json({}); }); app.post('/machines/:serial/message', function (req, res) { _.map(Machines.list(req.params.serial), function (socketid) { io.to(socketid).emit('message', req.body.data); }); }); app.post('/machines/:serial/data', function (req, res) { _.map(Machines.list(req.params.serial), function (socketid) { io.to(socketid).emit('data', req.body.data); }); }); app.post('/machines/:serial/exec', function (req, res) { _.map(Machines.list(req.params.serial), function (socketid) { io.to(socketid).emit('exec', req.body.data); }); }); app.post('/machines/:serial/npm', function (req, res) { _.map(Machines.list(req.params.serial), function (socketid) { io.to(socketid).emit('npm', req.body.data); }); }); app.post('/machines/:serial/task', function (req, res) { _.map(Machines.list(req.params.serial), function (socketid) { io.to(socketid).emit('task', req.body.data); }); }); io.on('connection', function (socket) { var c = socket.decoded_token; if (c.db) { console.log(c.db); Machines.add(c.user, c.password, c.db, c.serial, socket); _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine connection', { serial: c.serial }); }); socket.on('disconnect', function () { _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine disconnection', { serial: c.serial }); }); Machines.remove(c.serial, socket.id); }); socket.on('message', function (message) { Machines.pushdata(c.serial, 'message', message).then(function (docs) { _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine message', { serial: c.serial, data: message }); }); }); }); socket.on('data', function (data) { Machines.pushdata(c.serial, 'data', data).then(function (docs) { _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine data', { serial: c.serial, data: data }); }); }); }); socket.on('docs', function (docs) { Machines.pushdata(c.serial, 'docs', docs).then(function (docs) { _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine docs', { serial: c.serial, data: docs }); }); }); }); socket.on('up', function (datas) { _.map(Auditors.forserial(c.serial), function (socketid) { io.to(socketid).emit('machine up', { serial: c.serial }); }); }); } else { Auditors.add(c.serials, socket.id); socket.on('disconnect', function () { Auditors.remove(socket.id); }); } console.log('hello! ', socket.id); }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbImluZGV4LnRzIl0sIm5hbWVzIjpbInNldHVwbXF0dCIsImF1dGhjb3VjaCIsImF1dGhvcml6ZXNvY2tldCJdLCJtYXBwaW5ncyI6IkFBQUEsSUFBWSxDQUFDLFdBQU0sUUFBUSxDQUFDLENBQUE7QUFDNUIsSUFBWSxPQUFPLFdBQU0sVUFBVSxDQUFDLENBQUE7QUFDcEMsSUFBWSxVQUFVLFdBQU0sYUFBYSxDQUFDLENBQUE7QUFDMUMsSUFBWSxVQUFVLFdBQU0sYUFBYSxDQUFDLENBQUE7QUFDMUMsSUFBWSxFQUFFLFdBQU0sV0FBWSxDQUFDLENBQUE7QUFDakMsSUFBWSxPQUFPLFdBQU0sU0FBUyxDQUFDLENBQUE7QUFDbkMsSUFBWSxHQUFHLFdBQU0sY0FBYyxDQUFDLENBQUE7QUFDcEMsSUFBWSxLQUFLLFdBQU0sT0FBTyxDQUFDLENBQUE7QUFFL0IsSUFBTyxhQUFhLFdBQVcsZUFBZSxDQUFDLENBQUM7QUFFaEQsSUFBTyxXQUFXLFdBQVcsdUJBQXVCLENBQUMsQ0FBQztBQUN0RCxJQUFPLFVBQVUsV0FBVyxzQkFBc0IsQ0FBQyxDQUFDO0FBRXBELElBQUksV0FBVyxHQUFLLE9BQU8sQ0FBQyxjQUFjLENBQUMsQ0FBQztBQUM1QyxJQUFJLEdBQUcsR0FBRyxPQUFPLENBQUMsc0JBQXNCLENBQUMsQ0FBQztBQUMxQyxJQUFJLEtBQUssR0FBRyxPQUFPLENBQUMsT0FBTyxDQUFDLENBQUM7QUFHN0IsSUFBSSxHQUFHLEdBQUcsT0FBTyxFQUFFLENBQUM7QUFDcEIsSUFBSSxNQUFNLEdBQUcsT0FBTyxDQUFDLE1BQU0sQ0FBQyxDQUFDLE1BQU0sQ0FBQyxHQUFHLENBQUMsQ0FBQztBQUN6QyxJQUFJLEVBQUUsR0FBRyxFQUFFLENBQUMsTUFBTSxDQUFDLENBQUM7QUFNcEIsRUFBRSxDQUFDLENBQUMsQ0FBQyxVQUFVLENBQUMsSUFBSSxDQUFDLGFBQWEsQ0FBQyxDQUFDLENBQUEsQ0FBQztJQUNuQyxNQUFNLEtBQUssQ0FBQywwQkFBMEIsQ0FBQyxDQUFB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LElBQUksQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxFQUFDLFVBQVMsUUFBUTtRQUN0RCxFQUFFLENBQUMsRUFBRSxDQUFDLFFBQVEsQ0FBQyxDQUFDLElBQUksQ0FBQyxTQUFTLEVBQUUsR0FBRyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQztJQUNqRCxDQUFDLENBQUMsQ0FBQTtBQUVKLENBQUMsQ0FBQyxDQUFDO0FBQ0gsR0FBRyxDQUFDLElBQUksQ0FBQyx3QkFBd0IsRUFBRSxVQUFVLEdBQUcsRUFBRSxHQUFHO0lBQ25ELENBQUMsQ0FBQyxHQUFHLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxFQUFDLFVBQVMsUUFBUTtRQUN0RCxFQUFFLENBQUMsRUFBRSxDQUFDLFFBQVEsQ0FBQyxDQUFDLElBQUksQ0FBQyxNQUFNLEVBQUUsR0FBRyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQztJQUM5QyxDQUFDLENBQUMsQ0FBQTtBQUNKLENBQUMsQ0FBQyxDQUFDO0FBQ0gsR0FBRyxDQUFDLElBQUksQ0FBQyx3QkFBd0IsRUFBRSxVQUFVLEdBQUcsRUFBRSxHQUFHO0lBQ25ELENBQUMsQ0FBQyxHQUFHLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxFQUFDLFVBQVMsUUFBUTtRQUN0RCxFQUFFLENBQUMsRUFBRSxDQUFDLFFBQVEsQ0FBQyxDQUFDLElBQUksQ0FBQyxNQUFNLEVBQUUsR0FBRyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQztJQUM5QyxDQUFDLENBQUMsQ0FBQTtBQUNKLENBQUMsQ0FBQyxDQUFDO0FBQ0gsR0FBRyxDQUFDLElBQUksQ0FBQyx1QkFBdUIsRUFBRSxVQUFVLEdBQUcsRUFBRSxHQUFHO0lBQ2xELENBQUMsQ0FBQyxHQUFHLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxFQUFD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QUFDLE1BQU0sRUFBQyxDQUFDLENBQUMsTUFBTSxFQUFDLENBQUMsQ0FBQztZQUN4RCxDQUFDLENBQUMsQ0FBQTtRQUNKLENBQUMsQ0FBQyxDQUFBO0lBRU4sQ0FBQztJQUFDLElBQUksQ0FBQSxDQUFDO1FBQ0wsUUFBUSxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsT0FBTyxFQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsQ0FBQTtRQUNqQyxNQUFNLENBQUMsRUFBRSxDQUFDLFlBQVksRUFBRTtZQUN0QixRQUFRLENBQUMsTUFBTSxDQUFDLE1BQU0sQ0FBQyxFQUFFLENBQUMsQ0FBQTtRQUM1QixDQUFDLENBQUMsQ0FBQztJQUVMLENBQUM7SUFFRCxPQUFPLENBQUMsR0FBRyxDQUFDLFNBQVMsRUFBRSxNQUFNLENBQUMsRUFBRSxDQUFDLENBQUM7QUFDbEMsQ0FBQyxDQUFDLENBQUMiLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgKiBhcyBfIGZyb20gXCJsb2Rhc2hcIjtcbmltcG9ydCAqIGFzIFByb21pc2UgZnJvbSBcImJsdWViaXJkXCI7XG5pbXBvcnQgKiBhcyBib2R5UGFyc2VyIGZyb20gXCJib2R5LXBhcnNlclwiO1xuaW1wb3J0ICogYXMgcGF0aEV4aXN0cyBmcm9tIFwicGF0aC1leGlzdHNcIjtcbmltcG9ydCAqIGFzIElPIGZyb20gXCJzb2NrZXQuaW9cIiA7XG5pbXBvcnQgKiBhcyBleHByZXNzIGZyb20gXCJleHByZXNzXCI7XG5pbXBvcnQgKiBhcyBqd3QgZnJvbSBcImpzb253ZWJ0b2tlblwiO1xuaW1wb3J0ICogYXMgcmVkaXMgZnJvbSBcInJlZGlzXCI7XG5cbmltcG9ydCBjb3VjaGpzb25jb25mID0gcmVxdWlyZShcImNvdWNoanNvbmNvbmZcIik7XG5cbmltcG9ydCBtYWNoQ2xpZW50cyA9IHJlcXVpcmUoXCIuL21vZHVsZXMvbWFjaENsaWVudHNcIik7XG5pbXBvcnQgYXVkQ2xpZW50cyA9IHJlcXVpcmUoXCIuL21vZHVsZXMvYXVkQ2xpZW50c1wiKTtcblxubGV0IHNvY2tldGlvSnd0ICAgPSByZXF1aXJlKFwic29ja2V0aW8tand0XCIpO1xubGV0IHJwaiA9IHJlcXVpcmUoJ3JlcXVlc3QtcHJvbWlzZS1qc29uJyk7XG5sZXQgbW9zY2EgPSByZXF1aXJlKFwibW9zY2FcIik7XG5cblxubGV0IGFwcCA9IGV4cHJlc3MoKTtcbmxldCBzZXJ2ZXIgPSByZXF1aXJlKCdodHRwJykuU2VydmVyKGFwcCk7XG5sZXQgaW8gPSBJTyhzZXJ2ZXIpO1xuXG5cblxuXG5cbmlmICghcGF0aEV4aXN0cy5zeW5jKCcuL2NvbmYuanNvbicpKXtcbiAgdGhyb3cgRXJyb3IoJ25vIGNvbmZpZ3VyYXRpb24gZm91bmRlZCcpXG59XG5sZXQgY29uZj1yZXF1aXJlKCcuL2NvbmYuanNvbicpXG5cbmxldCBDT1VDSERCPSBuZXcgY291Y2hqc29uY29uZihjb25mLmNvdWNoZGIpXG5cbmxldCBNYWNoaW5lcz1uZXcgbWFjaENsaWVudHMoQ09VQ0hEQik7XG5sZXQgQXVkaXRvcnM9bmV3IGF1ZENsaWVudHMoKTtcblxuLy8gcGFyc2UgYXBwbGljYXRpb24veC13d3ctZm9ybS11cmxlbmNvZGVkXG5hcHAudXNlKGJvZHlQYXJzZXIudXJsZW5jb2RlZCh7IGV4dGVuZGVkOiBmYWxzZSB9KSlcblxuLy8gcGFyc2UgYXBwbGljYXRpb24vanNvblxuYXBwLnVzZShib2R5UGFyc2VyLmpzb24oKSlcblxuXG5cbmlvLnVzZShzb2NrZXRpb0p3dC5hdXRob3JpemUoe1xuICBzZWNyZXQ6IGNvbmYuc2VjcmV0LFxuICBoYW5kc2hha2U6IHRydWVcbn0pKTtcblxuc2VydmVyLmxpc3Rlbihjb25mLnBvcnQpO1xuXG5cbmxldCBhc2NvbHRhdG9yZSA9IHtcbiAgdHlwZTogJ3JlZGlzJyxcbiAgcmVkaXM6IHJlZGlzLFxuICBkYjogMTIsXG4gIHBvcnQ6IDYzNzksXG4gIHJldHVybl9idWZmZXJzOiB0cnVlLCAvLyB0byBoYW5kbGUgYmluYXJ5IHBheWxvYWRzXG4gIGhvc3Q6IFwibG9jYWxob3N0XCJcbn07XG5cbmxldCBtb3NjYVNldHRpbmdzID0ge1xuICBwb3J0OiAxODgzLFxuICBiYWNrZW5kOiBhc2NvbHRhdG9yZSxcbiAgcGVyc2lzdGVuY2U6IHtcbiAgICBmYWN0b3J5OiBtb3NjYS5wZXJzaXN0ZW5jZS5SZWRpc1xuICB9XG59O1xuXG5cbmxldCBtcXR0c2VydmVyID0gbmV3IG1vc2NhLlNlcnZlcihtb3NjYVNldHRpbmdzKTtcbm1xdHRzZXJ2ZXIub24oJ3JlYWR5Jywgc2V0dXBtcXR0KTtcblxuXG5tcXR0c2VydmVyLm9uKCdjbGllbnRDb25uZWN0ZWQnLCBmdW5jdGlvbihjbGllbnQpIHtcbiAgICBjb25zb2xlLmxvZygnY2xpZW50IGNvbm5lY3RlZCcsIGNsaWVudC5pZCk7ICAgICBcbn0pO1xuXG4vLyBmaXJlZCB3aGVuIGEgbWVzc2FnZSBpcyByZWNlaXZlZFxubXF0dHNlcnZlci5vbigncHVibGlzaGVkJywgZnVuY3Rpb24ocGFja2V0LCBjbGllbnQpIHtcbiAgY29uc29sZS5sb2coJ1B1Ymxpc2hlZCcsIHBhY2tldC5wYXlsb2FkKTtcbn0pO1xuXG4vLyBmaXJlZCB3aGVuIHRoZSBtcXR0IHNlcnZlciBpcyByZWFkeVxuZnVuY3Rpb24gc2V0dXBtcXR0KCkge1xuICBjb25zb2xlLmxvZygnTW9zY2Egc2VydmVyIGlzIHVwIGFuZCBydW5uaW5nJylcbn1cblxuXG5cbmludGVyZmFjZSBJU29ja2V0IHtcblxuICAgICAgICBpZDogc3RyaW5nO1xuICAgICAgICBlbWl0OkZ1bmN0aW9uO1xuICAgICAgICAgICAgICAgIG9uOkZ1bmN0aW9uO1xuICAgIGRlY29kZWRfdG9rZW46e1xuICAgICAgICBkYjpzdHJpbmc7XG4gICAgICAgIHVzZXI6c3RyaW5nO1xuICAgICAgICBwYXNzd29yZDpzdHJpbmc7XG4gICAgICAgIHNlcmlhbDpzdHJpbmc7XG4gICAgICAgIHNlcmlhbHM6c3RyaW5nW11cbiAgICB9XG59XG5cblxuXG5cbmFwcC5nZXQoJy8nLCBmdW5jdGlvbiAocmVxLCByZXMpIHtcbiAgcmVzLmpzb24oe29ubGluZTp0cnVlfSlcbn0pO1xuXG5cblxuXG5mdW5jdGlvbiBhdXRoY291Y2godXNlcjpzdHJpbmcscGFzc3dvcmQ6c3RyaW5nLGRiOnN0cmluZyl7XG4gIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbihyZXNvbHZlLHJlamVjdCl7XG4gICAgcnBqLmdldChDT1VDSERCLmZvcih1c2VyLHBhc3N3b3JkLGRiKSkudGhlbihmdW5jdGlvbigpe1xuICAgICAgcmVzb2x2ZSh7c3VjY2Vzczp0cnVlfSlcbiAgICB9KS5jYXRjaChmdW5jdGlvbihlcnIpe1xuICAgICAgcmVqZWN0KHtlcnJvcjond3JvbmcgY3JlZGVudGlhbHMnfSlcbiAgICB9KVxuICB9KVxufVxuXG5mdW5jdGlvbiBhdXRob3JpemVzb2NrZXQocHJvZmlsZSk6e317XG5yZXR1cm4gand0LnNpZ24ocHJvZmlsZSwgY29uZi5zZWNyZXQsIHsgZXhwaXJlc0luTWludXRlczogNjAqNSB9KTtcbn1cblxuYXBwLnBvc3QoJy9sb2dpbicsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICBhdXRoY291Y2gocmVxLmJvZHkudXNlcixyZXEuYm9keS5wYXNzd29yZCxyZXEuYm9keS5kYikudGhlbihmdW5jdGlvbigpe1xuXG4gIGxldCB0b2tlbj1hdXRob3JpemVzb2NrZXQoeyB1c2VyOnJlcS5ib2R5LnVzZXIscGFzc3dvcmQ6cmVxLmJvZHkucGFzc3dvcmQsZGI6cmVxLmJvZHkuZGIsc2VyaWFsOnJlcS5ib2R5LnNlcmlhbCB9KVxuXG4gICAgcmVzLmpzb24oe3N1Y2Nlc3M6dHJ1ZSx0b2tlbjp0b2tlbn0pXG4gIH0pLmNhdGNoKGZ1bmN0aW9uKGVycil7XG4gICAgcmVzLmpzb24oZXJyKVxuICB9KVxufSk7XG5cbmFwcC5nZXQoJy9pcCcsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICByZXMuanNvbih7aXA6cmVxLmhlYWRlcnNbJ3gtZm9yd2FyZGVkLWZvciddfSlcbn0pO1xuXG5hcHAuZ2V0KCcvc29ja2V0cycsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICByZXMuanNvbihNYWNoaW5lcy5zb2NrZXRzKCkpXG59KTtcbmFwcC5nZXQoJy9tYWNoaW5lcy86c2VyaWFsL3NvY2tldHMnLCBmdW5jdGlvbiAocmVxLCByZXMpIHtcbiAgcmVzLmpzb24oTWFjaGluZXMuc29ja2V0cyhyZXEucGFyYW1zLnNlcmlhbCkpXG59KTtcbmFwcC5nZXQoJy9tYWNoaW5lcycsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICByZXMuanNvbihNYWNoaW5lcy5saXN0KCkpXG59KTtcbmFwcC5nZXQoJy9hcHAvOmFwcC9tYWNoaW5lcycsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuIC8vIHJlcy5qc29uKE1hY2hpbmVzLnNlcmlhbHMoKSlcbn0pO1xuXG5hcHAuZ2V0KCcvbWFjaGluZXMvOnNlcmlhbC9tZXNzYWdlLzptZXNzYWdlJywgZnVuY3Rpb24gKHJlcSwgcmVzKSB7XG4gIF8ubWFwKE1hY2hpbmVzLmlvcyhyZXEucGFyYW1zLnNlcmlhbCksZnVuY3Rpb24oc29ja2V0KXtcbiAgICBzb2NrZXQuZW1pdCgnbWVzc2FnZScsIHJlcS5wYXJhbXMubWVzc2FnZSk7XG5cbiAgfSlcbiAgcmVzLmpzb24oe30pXG5cbn0pO1xuXG5hcHAucG9zdCgnL21hY2hpbmVzLzpzZXJpYWwvbWVzc2FnZScsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICBfLm1hcChNYWNoaW5lcy5saXN0KHJlcS5wYXJhbXMuc2VyaWFsKSxmdW5jdGlvbihzb2NrZXRpZCl7XG4gICAgaW8udG8oc29ja2V0aWQpLmVtaXQoJ21lc3NhZ2UnLCByZXEuYm9keS5kYXRhKTtcbiAgfSlcblxufSk7XG5hcHAucG9zdCgnL21hY2hpbmVzLzpzZXJpYWwvZGF0YScsIGZ1bmN0aW9uIChyZXEsIHJlcykge1xuICBfLm1hcChNYWNoaW5lcy5saXN0KHJlcS5wYXJhbXMuc2VyaWFsKSxmdW5jdGlvbihzb2NrZXRpZCl7XG4gICAgaW8udG8oc29ja2V0aWQpLmVtaXQoJ2RhdGEnLCByZXEuYm9keS5kYXRhKTtcbiAgfSlcbn0pO1xuYXBwLnBvc3QoJy9tYWNoaW5lcy86c2VyaWFsL2V4ZWMnLCBmdW5jdGlvbiAocmVxLCByZXMpIHtcbiAgXy5tYXAoTWFjaGluZXMubGlzdChyZXEucGFyYW1zLnNlcmlhbCksZnVuY3Rpb24oc29ja2V0aWQpe1xuICAgIGlvLnRvKHNvY2tldGlkKS5lbWl0KCdleGVjJywgcmVxLmJvZHkuZGF0YSk7XG4gIH0pXG59KTtcbmFwcC5wb3N0KCcvbWFjaGluZXMvOnNlcmlhbC9ucG0nLCBmdW5jdGlvbiAocmVxLCByZXMpIHtcbiAgXy5tYXAoTWFjaGluZXMubGlzdChyZXEucGFyYW1zLnNlcmlhbCksZnVuY3Rpb24oc29ja2V0aWQpe1xuICAgIGlvLnRvKHNvY2tldGlkKS5lbWl0KCducG0nLCByZXEuYm9keS5kYXRhKTtcbiAgfSlcbn0pO1xuYXBwLnBvc3QoJy9tYWNoaW5lcy86c2VyaWFsL3Rhc2snLCBmdW5jdGlvbiAocmVxLCByZXMpIHtcbiAgXy5tYXAoTWFjaGluZXMubGlzdChyZXEucGFyYW1zLnNlcmlhbCksZnVuY3Rpb24oc29ja2V0aWQpe1xuICAgIGlvLnRvKHNvY2tldGlkKS5lbWl0KCd0YXNrJywgcmVxLmJvZHkuZGF0YSk7XG4gIH0pXG59KTtcblxuaW8ub24oJ2Nvbm5lY3Rpb24nLCBmdW5jdGlvbiAoc29ja2V0OklTb2NrZXQpIHtcbiAgbGV0IGMgPSBzb2NrZXQuZGVjb2RlZF90b2tlbjtcblxuICBpZihjLmRiKXtcbiAgICBjb25zb2xlLmxvZyhjLmRiKVxuXG4gICAgTWFjaGluZXMuYWRkKGMudXNlcixjLnBhc3N3b3JkLGMuZGIsYy5zZXJpYWwsc29ja2V0KTtcbiAgICBfLm1hcChBdWRpdG9ycy5mb3JzZXJpYWwoYy5zZXJpYWwpLGZ1bmN0aW9uKHNvY2tldGlkKXtcbiAgICAgIGlvLnRvKHNvY2tldGlkKS5lbWl0KCdtYWNoaW5lIGNvbm5lY3Rpb24nLCB7c2VyaWFsOmMuc2VyaWFsfSk7XG4gICAgfSlcblxuICAgIHNvY2tldC5vbignZGlzY29ubmVjdCcsIGZ1bmN0aW9uICgpIHtcblxuICAgICAgXy5tYXAoQXVkaXRvcnMuZm9yc2VyaWFsKGMuc2VyaWFsKSxmdW5jdGlvbihzb2NrZXRpZCl7XG4gICAgICAgIGlvLnRvKHNvY2tldGlkKS5lbWl0KCdtYWNoaW5lIGRpc2Nvbm5lY3Rpb24nLCB7c2VyaWFsOmMuc2VyaWFsfSk7XG4gICAgICB9KVxuXG4gICAgICBNYWNoaW5lcy5yZW1vdmUoYy5zZXJpYWwsc29ja2V0LmlkKTtcbiAgICB9KTtcbiAgICBzb2NrZXQub24oJ21lc3NhZ2UnLCBmdW5jdGlvbiAobWVzc2FnZSkge1xuICAgICAgTWFjaGluZXMucHVzaGRhdGEoYy5zZXJpYWwsJ21lc3NhZ2UnLG1lc3NhZ2UpLnRoZW4oZnVuY3Rpb24oZG9jcyl7XG5cbiAgICAgICAgXy5tYXAoQXVkaXRvcnMuZm9yc2VyaWFsKGMuc2VyaWFsKSxmdW5jdGlvbihzb2NrZXRpZCl7XG4gICAgICAgICAgaW8udG8oc29ja2V0aWQpLmVtaXQoJ21hY2hpbmUgbWVzc2FnZScsIHtzZXJpYWw6Yy5zZXJpYWwsZGF0YTptZXNzYWdlfSk7XG4gICAgICAgIH0pXG4gICAgICB9KVxuICAgIH0pO1xuICAgIHNvY2tldC5vbignZGF0YScsIGZ1bmN0aW9uIChkYXRhKSB7XG4gICAgICBNYWNoaW5lcy5wdXNoZGF0YShjLnNlcmlhbCwnZGF0YScsZGF0YSkudGhlbihmdW5jdGlvbihkb2NzKXtcblxuICAgICAgICBfLm1hcChBdWRpdG9ycy5mb3JzZXJpYWwoYy5zZXJpYWwpLGZ1bmN0aW9uKHNvY2tldGlkKXtcbiAgICAgICAgICBpby50byhzb2NrZXRpZCkuZW1pdCgnbWFjaGluZSBkYXRhJywge3NlcmlhbDpjLnNlcmlhbCxkYXRhOmRhdGF9KTtcbiAgICAgICAgfSlcbiAgICAgIH0pXG4gICAgfSk7XG4gICAgc29ja2V0Lm9uKCdkb2NzJywgZnVuY3Rpb24gKGRvY3MpIHtcbiAgICAgIE1hY2hpbmVzLnB1c2hkYXRhKGMuc2VyaWFsLCdkb2NzJyxkb2NzKS50aGVuKGZ1bmN0aW9uKGRvY3Mpe1xuICAgICAgICBfLm1hcChBdWRpdG9ycy5mb3JzZXJpYWwoYy5zZXJpYWwpLGZ1bmN0aW9uKHNvY2tldGlkKXtcbiAgICAgICAgICBpby50byhzb2NrZXRpZCkuZW1pdCgnbWFjaGluZSBkb2NzJywge3NlcmlhbDpjLnNlcmlhbCxkYXRhOmRvY3N9KTtcbiAgICAgICAgfSlcblxuICAgICAgfSlcbiAgICB9KTtcbiAgICBzb2NrZXQub24oJ3VwJywgZnVuY3Rpb24gKGRhdGFzKSB7XG4gICAgICBfLm1hcChBdWRpdG9ycy5mb3JzZXJpYWwoYy5zZXJpYWwpLGZ1bmN0aW9uKHNvY2tldGlkKXtcbiAgICAgICAgaW8udG8oc29ja2V0aWQpLmVtaXQoJ21hY2hpbmUgdXAnLCB7c2VyaWFsOmMuc2VyaWFsfSk7XG4gICAgICB9KVxuICAgIH0pXG5cbn0gZWxzZXtcbiAgQXVkaXRvcnMuYWRkKGMuc2VyaWFscyxzb2NrZXQuaWQpXG4gIHNvY2tldC5vbignZGlzY29ubmVjdCcsIGZ1bmN0aW9uICgpIHtcbiAgICBBdWRpdG9ycy5yZW1vdmUoc29ja2V0LmlkKVxuICB9KTtcblxufVxuXG5jb25zb2xlLmxvZygnaGVsbG8hICcsIHNvY2tldC5pZCk7XG59KTtcbiJdLCJzb3VyY2VSb290IjoiL3NvdXJjZS8ifQ==