Node-mysql2: Connection.connectTimeout is not cleared when connect error happens

Created on 6 Aug 2019  路  8Comments  路  Source: sidorares/node-mysql2

Timeout connectTimeout which is created in Connection constructor (node_modules/mysql2/lib/connection.js) is not cleared when error happens. It should be cleared for example in callback _handleNetworkError.

Run this without mysqld listening on 127.0.0.1:3306:
``` node js
let mysql = require("mysql2");
let connection = mysql.createConnection({});
connection.on("error", err => console.log(new Date(), "error", err))
process.on("exit", () => console.log(new Date(), "exit"));

Possible output:

2019-08-06T20:05:27.571Z error Error: connect ECONNREFUSED 127.0.0.1:3306
at TCPConnectWrap.afterConnect [as oncomplete] (net.js:1056:14) {
errno: 'ECONNREFUSED',
code: 'ECONNREFUSED',
syscall: 'connect',
address: '127.0.0.1',
port: 3306,
fatal: true
}
2019-08-06T20:05:37.573Z exit

Notice that it takes 10 seconds to exit which is default for connect timeout.

Without error event handler on repl.it:
``` node js
let mysql = require("mysql2");
let connection = mysql.createConnection({});
Process crashed with: Error: connect ECONNREFUSED 127.0.0.1:3306
    at TCPConnectWrap.afterConnect [as oncomplete] (net.js:1106:14)
Process crashed with: Error: Connection lost: The server closed the connection.
    at Socket.Connection.stream.on (/home/runner/node_modules/mysql2/lib/connection.js:88:31)
    at Socket.emit (events.js:198:13)
    at TCP._handle.close (net.js:606:12)
Process crashed with: Error: connect ETIMEDOUT
    at Connection._handleTimeoutError (/home/runner/node_modules/mysql2/lib/connection.js:171:17)
    at ontimeout (timers.js:436:11)
    at tryOnTimeout (timers.js:300:5)
    at listOnTimeout (timers.js:263:5)
    at Timer.processTimers (timers.js:223:10)
  ```

This change solves this problem:
Before:
``` node js
  _handleNetworkError(err) {
    // Do not throw an error when a connection ends with a RST,ACK packet
    if (err.errno === 'ECONNRESET' && this._closing) {
      return;
    }
    this._handleFatalError(err);
  }

After:
``` node js
_handleNetworkError(err) {
if (this.connectTimeout) {
Timers.clearTimeout(this.connectTimeout);
this.connectTimeout = null;
}
// Do not throw an error when a connection ends with a RST,ACK packet
if (err.errno === 'ECONNRESET' && this._closing) {
return;
}
this._handleFatalError(err);
}

Now it exits immediately:

2019-08-06T20:11:31.459Z error Error: connect ECONNREFUSED 127.0.0.1:3306
at TCPConnectWrap.afterConnect [as oncomplete] (net.js:1056:14) {
errno: 'ECONNREFUSED',
code: 'ECONNREFUSED',
syscall: 'connect',
address: '127.0.0.1',
port: 3306,
fatal: true
}
2019-08-06T20:11:31.464Z exit
```

Maybe it should be cleared also in _handleFatalError.

Most helpful comment

@dvisztempacct It is basically leak. What if someone uses really long timeout? These leaked timeouts can add up and cause real problems. It is like leaking files by not closing stream created by fs.createReadStream.

All 8 comments

@misos1 Hi

Have you had any issues other than node.js taking extra time to exit?

Thanks!

@dvisztempacct It is basically leak. What if someone uses really long timeout? These leaked timeouts can add up and cause real problems. It is like leaking files by not closing stream created by fs.createReadStream.

hi @misos1 , I think you are correct. Do you want to create PR with the fix?

Yup, bumped into this issue today,
it seems it is correctly cleared in _handleTimeoutError

_handleTimeoutError() {
    if (this.connectTimeout) {
      Timers.clearTimeout(this.connectTimeout);
      this.connectTimeout = null;
    }
    this.stream.destroy && this.stream.destroy();
    const err = new Error('connect ETIMEDOUT');
    console.log(err.stack);
    err.errorno = 'ETIMEDOUT';
    err.code = 'ETIMEDOUT';
    err.syscall = 'connect';
    this._handleNetworkError(err);
  }

I will do PR, i need this fixed in my project

And what about that second place in _handleFatalError?

@misos1 good point. @jacobbogers can you double check that?

Was this page helpful?
0 / 5 - 0 ratings

Related issues

magicxie picture magicxie  路  6Comments

vcorr picture vcorr  路  5Comments

MHDante picture MHDante  路  4Comments

SiroDiaz picture SiroDiaz  路  6Comments

framp picture framp  路  3Comments