From e6f6d4475cc3ec76aa7da990e5ba4f3a8a4fc298 Mon Sep 17 00:00:00 2001 From: Valeri Karpov Date: Wed, 28 Feb 2024 14:49:22 -0500 Subject: [PATCH] fix(connection): avoid unhandled error on createConnection() if on('error') handler registered Fix #14377 --- lib/connection.js | 24 ++++++++++++++++++++++++ test/connection.test.js | 15 +++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/lib/connection.js b/lib/connection.js index 542bdf3c572..05ff52461b0 100644 --- a/lib/connection.js +++ b/lib/connection.js @@ -829,6 +829,30 @@ Connection.prototype.openUri = async function openUri(uri, options) { return this; }; +/*! + * Treat `on('error')` handlers as handling the initialConnection promise + * to avoid uncaught exceptions when using `on('error')`. See gh-14377. + */ + +Connection.prototype.on = function on(event, callback) { + if (event === 'error' && this.$initialConnection) { + this.$initialConnection.catch(() => {}); + } + return EventEmitter.prototype.on.call(this, event, callback); +}; + +/*! + * Treat `once('error')` handlers as handling the initialConnection promise + * to avoid uncaught exceptions when using `on('error')`. See gh-14377. + */ + +Connection.prototype.once = function on(event, callback) { + if (event === 'error' && this.$initialConnection) { + this.$initialConnection.catch(() => {}); + } + return EventEmitter.prototype.once.call(this, event, callback); +}; + /*! * ignore */ diff --git a/test/connection.test.js b/test/connection.test.js index 9ea81e356d0..3d1170838cf 100644 --- a/test/connection.test.js +++ b/test/connection.test.js @@ -916,6 +916,21 @@ describe('connections:', function() { assert.equal(err.name, 'MongooseServerSelectionError'); }); + it('avoids unhandled error on createConnection() if error handler registered (gh-14377)', async function() { + const opts = { + serverSelectionTimeoutMS: 100 + }; + const uri = 'mongodb://baddomain:27017/test'; + + const conn = mongoose.createConnection(uri, opts); + await new Promise(resolve => { + conn.on('error', err => { + assert.equal(err.name, 'MongoServerSelectionError'); + resolve(); + }); + }); + }); + it('`watch()` on a whole collection (gh-8425)', async function() { this.timeout(10000); if (!process.env.REPLICA_SET) {