diff --git a/README.md b/README.md
index 36de694..07933cb 100644
--- a/README.md
+++ b/README.md
@@ -31,17 +31,35 @@ autossh({
ssh -NL 64444:localhost:5432 -o "ExitOnForwardFailure yes" -o ServerAliveInterval=120 -o ServerAliveCountMax=1 root@111.22.333.444
```
+
+
#### Event Listeners
-Autossh inherits from node.js's EventEmitter, and implements two events: `error`, `connect`
+Autossh inherits from node.js's EventEmitter, and implements three events: `error`, `timeout`, `connect`
**error**
-The `error` event will fire anytime there is an error throughout the life of the `autossh` process.
+The `error` event will fire anytime there is an error throughout the life of the autossh process.
+
+**timeout**
+
+Normally, a timeout would be an error, but autossh treats it as a separate event. The `timeout` event will fire anytime there is a timeout error throughout the life of the autossh process.
+
+Autossh will automatically attempt to re-establish a connection.
**connect**
-The `connect` event will fire only once when the initial ssh connection is made
+The `connect` event will fire only once when the initial ssh connection is made. The callback's first argument is connection object which contains the following properties:
+
+- `kill` - a method to kill autossh
+- `pid` - the autossh process id
+- `host`
+- `username`
+- `remotePort`
+- `localPort`
+- `execString` - the autossh command string
+
+**Example 1**
``` javascript
autossh({
@@ -59,6 +77,33 @@ autossh({
});
```
+**Example 2**
+
+``` javascript
+const autosshClient = autossh({
+ host: '111.22.333.444',
+ username: 'root',
+ localPort: 64444,
+ remotePort: 5432
+});
+
+autosshClient.on('error', err => {
+ console.error('ERROR: ', err);
+ autosshClient.kill();
+});
+
+autosshClient.on('timeout', connection => {
+ console.warn('Connection to ' + connection.host + ' timed out.');
+});
+
+autosshClient.on('connect', connection => {
+ console.log('Tunnel established on port ' + connection.localPort);
+ console.log('pid: ' + connection.pid);
+});
+```
+
+
+
#### Generate Dynamic Local Port
If you want to dynamically/randomly generate a port number, provide a string `auto` for the `localPort`.
@@ -80,6 +125,8 @@ autossh({
});
```
+
+
#### Killing the Autossh Process
The autossh process will automatically die if the node process is closed, but you can manually kill the process using `kill`.
@@ -117,6 +164,8 @@ autossh({
});
```
+
+
#### Adjusting `serverAliveInterval` and `serverAliveCountMax`
These two options are the bread and butter butter as far as polling the ssh connection.
@@ -148,6 +197,8 @@ autossh({
});
```
+
+
#### Specifying the Private Key File
Select a file from which the identity (private key) for public key authentication is read. The default is `~/.ssh/id_rsa`.
@@ -171,6 +222,8 @@ autossh({
});
```
+
+
#### Adjusting/Disabling Max Poll Count
When first trying to establish the ssh tunnel, `autoshh` will poll the local port until the connection has been established. The default max poll count is `30`.
@@ -211,6 +264,8 @@ autossh({
**Warning:** The max poll count is there to prevent `autossh` from infinitely polling the local port. Rather than disabling it, it may be wise to set it to a high number (e.g. `500`).
+
+
#### Specifying a Different SSH Port
The designated port for SSH according to the Transmission Control Protocol (TCP) is port 22, but you can specify a different port if you are using a different port. Set the `sshPort` property in the object you pass to `autossh`.
diff --git a/index.js b/index.js
index b5a3132..8ae77c2 100644
--- a/index.js
+++ b/index.js
@@ -113,13 +113,34 @@ var AutoSSH = function (_EventEmitter) {
});
}
+ /* fired when timeout error occurs
+ */
+
+ }, {
+ key: 'emitTimeout',
+ value: function emitTimeout() {
+ var _this4 = this;
+
+ this.emit('timeout', {
+ kill: function kill() {
+ return _this4.kill;
+ },
+ pid: this.currentProcess.pid,
+ host: this.host,
+ username: this.username,
+ remotePort: this.remotePort,
+ localPort: this.localPort,
+ execString: this.execString
+ });
+ }
+
/* starts polling the port to see if connection established
*/
}, {
key: 'pollConnection',
value: function pollConnection() {
- var _this4 = this;
+ var _this5 = this;
if (this.killed) return;
@@ -128,11 +149,11 @@ var AutoSSH = function (_EventEmitter) {
this.kill();
} else {
this.isConnectionEstablished(function (result) {
- if (result) _this4.emitConnect();else {
+ if (result) _this5.emitConnect();else {
setTimeout(function () {
- _this4.pollCount++;
- _this4.pollConnection();
- }, _this4.pollTimeout);
+ _this5.pollCount++;
+ _this5.pollConnection();
+ }, _this5.pollTimeout);
}
});
}
@@ -144,12 +165,12 @@ var AutoSSH = function (_EventEmitter) {
}, {
key: 'isConnectionEstablished',
value: function isConnectionEstablished(connEstablishedCb) {
- var _this5 = this;
+ var _this6 = this;
_portfinder2.default.getPort({ port: this.localPort }, function (portfinderErr, freePort) {
if (portfinderErr) return connEstablishedCb(false);
- if (_this5.localPort === freePort) return connEstablishedCb(false);else return connEstablishedCb(true);
+ if (_this6.localPort === freePort) return connEstablishedCb(false);else return connEstablishedCb(true);
});
}
@@ -247,21 +268,23 @@ var AutoSSH = function (_EventEmitter) {
}, {
key: 'execTunnel',
value: function execTunnel(execTunnelCb) {
- var _this6 = this;
+ var _this7 = this;
this.execString = this.generateExecString();
this.currentProcess = (0, _child_process.exec)(this.execString, function (execErr, stdout, stderr) {
- if (_this6.killed) return;
+ if (_this7.killed) return;
if (/Address already in use/i.test(stderr)) {
- _this6.kill();
- _this6.emit('error', stderr);
+ _this7.kill();
+ _this7.emit('error', stderr);
return;
}
- if (execErr) _this6.emit('error', execErr);
+ if (execErr) {
+ if (/(timeout)|(timed out)/i.test(stderr)) _this7.emitTimeout();else _this7.emit('error', execErr);
+ }
- if (!_this6.killed) _this6.execTunnel(function () {
+ if (!_this7.killed) _this7.execTunnel(function () {
return console.log('Restarting autossh...');
});
});
diff --git a/src/index.js b/src/index.js
index 859cdbe..82b84b2 100644
--- a/src/index.js
+++ b/src/index.js
@@ -77,6 +77,20 @@ class AutoSSH extends EventEmitter {
execString: this.execString
});
}
+
+ /* fired when timeout error occurs
+ */
+ emitTimeout() {
+ this.emit('timeout', {
+ kill: () => this.kill,
+ pid: this.currentProcess.pid,
+ host: this.host,
+ username: this.username,
+ remotePort: this.remotePort,
+ localPort: this.localPort,
+ execString: this.execString
+ });
+ }
/* starts polling the port to see if connection established
*/
@@ -217,8 +231,12 @@ class AutoSSH extends EventEmitter {
return;
}
- if (execErr)
- this.emit('error', execErr);
+ if (execErr) {
+ if ((/(timeout)|(timed out)/i).test(stderr))
+ this.emitTimeout();
+ else
+ this.emit('error', execErr);
+ }
if (!this.killed)
this.execTunnel(() => console.log('Restarting autossh...'));