autossh/index.js

139 lines
5.1 KiB
JavaScript
Raw Normal View History

2016-04-07 19:22:13 -06:00
'use strict';
var _createClass = 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); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
var _child_process = require('child_process');
var _events = require('events');
var _portfinder = require('portfinder');
var _portfinder2 = _interopRequireDefault(_portfinder);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
2016-04-07 19:22:13 -06:00
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
2016-04-08 01:35:38 -06:00
/* AutoSSH class
*/
2016-04-07 19:22:13 -06:00
2016-04-08 01:35:38 -06:00
var AutoSSH = function (_EventEmitter) {
_inherits(AutoSSH, _EventEmitter);
function AutoSSH() {
2016-04-07 19:22:13 -06:00
var conf = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];
2016-04-08 01:35:38 -06:00
_classCallCheck(this, AutoSSH);
2016-04-07 19:22:13 -06:00
2016-04-08 01:35:38 -06:00
var _this = _possibleConstructorReturn(this, Object.getPrototypeOf(AutoSSH).call(this));
2016-04-07 19:22:13 -06:00
_this.host = conf.host;
_this.username = conf.username;
_this.remotePort = conf.remotePort;
_this.localPort = conf.localPort;
setImmediate(function () {
if (!conf.localPort) return _this.emit('error', 'Missing localPort');
2016-04-08 14:28:58 -06:00
_portfinder2.default.getPort({
port: _this.localPort === 'auto' ? _this.generateRandomPort() : _this.localPort
}, function (err, freePort) {
if (err) return _this.emit('error', 'Port error: ' + err);
if (_this.localPort !== 'auto' && _this.localPort !== freePort) return _this.emit('error', 'Port ' + _this.localPort + ' is not available');
if (!conf.host) return _this.emit('error', 'Missing host');
if (!conf.username) return _this.emit('error', 'Missing username');
if (!conf.remotePort) return _this.emit('error', 'Missing remotePort');
_this.localPort = freePort;
_this.execTunnel();
_this.emit('connect', {
kill: _this.kill,
pid: _this.currentProcess.pid,
host: _this.host,
username: _this.username,
remotePort: _this.remotePort,
localPort: _this.localPort
});
});
2016-04-08 01:35:38 -06:00
});
process.on('exit', function () {
_this.kill();
2016-04-07 19:22:13 -06:00
});
return _this;
}
2016-04-08 01:35:38 -06:00
_createClass(AutoSSH, [{
2016-04-08 14:28:58 -06:00
key: 'generateRandomPort',
value: function generateRandomPort() {
var minPort = 3000;
var maxPort = 65535;
return Math.floor(Math.random() * (maxPort - minPort + 1)) + minPort;
}
}, {
2016-04-07 19:22:13 -06:00
key: 'execTunnel',
value: function execTunnel() {
var _this2 = this;
2016-04-08 01:35:38 -06:00
var bindAddress = this.localPort + ':localhost:' + this.remotePort;
var userAtHost = this.username + '@' + this.host;
var exitOnFailure = '-o "ExitOnForwardFailure yes"';
var execString = 'ssh -NL ' + bindAddress + ' ' + exitOnFailure + ' ' + userAtHost;
2016-04-08 14:28:58 -06:00
2016-04-08 01:35:38 -06:00
this.currentProcess = (0, _child_process.exec)(execString, function (err, stdout, stderr) {
if (/Address already in use/i.test(stderr)) {
_this2.kill();
return _this2.emit('error', stderr);
}
2016-04-07 19:22:13 -06:00
if (err) _this2.emit('error', err);
2016-04-08 01:35:38 -06:00
if (!_this2.killed) {
console.log('Restarting autossh...');
_this2.execTunnel();
}
2016-04-07 19:22:13 -06:00
});
}
}, {
key: 'kill',
value: function kill() {
this.killed = true;
this.currentProcess.kill();
return this;
}
}]);
2016-04-08 01:35:38 -06:00
return AutoSSH;
2016-04-07 19:22:13 -06:00
}(_events.EventEmitter);
2016-04-08 01:35:38 -06:00
function autoSSH(conf) {
var newAutoSSH = new AutoSSH(conf);
var returnObj = {
on: function on(evt) {
for (var _len = arguments.length, args = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
args[_key - 1] = arguments[_key];
}
newAutoSSH.on.apply(newAutoSSH, [evt].concat(args));
return this;
},
kill: function kill() {
newAutoSSH.kill();
return this;
}
};
Object.defineProperty(returnObj, 'pid', {
get: function get() {
return newAutoSSH.currentProcess.pid;
}
});
return returnObj;
2016-04-07 19:22:13 -06:00
}
2016-04-08 01:35:38 -06:00
module.exports = autoSSH;