From 5f87446e0aa1f72771dd98b56e19c8e61c09a637 Mon Sep 17 00:00:00 2001 From: Aditi Khare Date: Mon, 4 Mar 2024 16:46:29 -0500 Subject: [PATCH 1/4] Basic implementation done, need to UTR changes + sync spec tests still --- src/error.ts | 11 ++++++++++- test/unit/error.test.ts | 18 ++++++++++++++++++ 2 files changed, 28 insertions(+), 1 deletion(-) diff --git a/src/error.ts b/src/error.ts index b488d0d5d7..87732aa374 100644 --- a/src/error.ts +++ b/src/error.ts @@ -200,6 +200,7 @@ export class MongoError extends Error { * @category Error */ export class MongoServerError extends MongoError { + errorResponse?: ErrorDescription; codeName?: string; writeConcernError?: Document; errInfo?: Document; @@ -223,9 +224,17 @@ export class MongoServerError extends MongoError { this[kErrorLabels] = new Set(message.errorLabels); } + this.errorResponse = message; + for (const name in message) { - if (name !== 'errorLabels' && name !== 'errmsg' && name !== 'message') + if ( + name !== 'errorLabels' && + name !== 'errmsg' && + name !== 'message' && + name !== 'errorResponse' + ) { this[name] = message[name]; + } } } diff --git a/test/unit/error.test.ts b/test/unit/error.test.ts index 678398d27e..4a9d1423a5 100644 --- a/test/unit/error.test.ts +++ b/test/unit/error.test.ts @@ -113,6 +113,24 @@ describe('MongoErrors', () => { expect(err.message).to.equal(errorMessage); expect(err.someData).to.equal(12345); }); + context('errorResponse property', function () { + it(`should set errorResponse to raw results document passed in`, function () { + const errorDoc = { message: 'A test error', someData: 12345 }; + const err = new MongoServerError(errorDoc); + expect(err).to.be.an.instanceof(Error); + expect(err.errorResponse).to.deep.equal(errorDoc); + }); + it(`should not construct enumerated key 'errorResponse' if present`, function () { + const errorDoc = { + message: 'A test error', + errorResponse: 'I will not be an enumerated key' + }; + const err = new MongoServerError(errorDoc); + expect(err).to.be.an.instanceof(Error); + expect(err.errorResponse).to.deep.equal(errorDoc); + expect(err.errorResponse?.errorResponse).to.deep.equal('I will not be an enumerated key'); + }); + }); }); describe('MongoNetworkError#constructor', () => { From 2cf786a2d59292828ebc4e30314e4cfa1b302e39 Mon Sep 17 00:00:00 2001 From: Aditi Khare Date: Fri, 8 Mar 2024 16:55:58 -0500 Subject: [PATCH 2/4] fake rebase: --- src/error.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/error.ts b/src/error.ts index 87732aa374..6f91f24634 100644 --- a/src/error.ts +++ b/src/error.ts @@ -200,7 +200,8 @@ export class MongoError extends Error { * @category Error */ export class MongoServerError extends MongoError { - errorResponse?: ErrorDescription; + /** Raw error result document returned by server. */ + errorResponse: ErrorDescription; codeName?: string; writeConcernError?: Document; errInfo?: Document; From 20066f3da28fa92b78e9f28b18d14c0c066cdf1e Mon Sep 17 00:00:00 2001 From: Aditi Khare Date: Mon, 11 Mar 2024 13:24:31 -0400 Subject: [PATCH 3/4] Expanded types --- src/sdam/monitor.ts | 4 ++-- src/sdam/server.ts | 6 +++--- src/sdam/server_description.ts | 4 ++-- src/sdam/topology_description.ts | 6 +++--- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/src/sdam/monitor.ts b/src/sdam/monitor.ts index 6accf8cd3c..7b7df45c23 100644 --- a/src/sdam/monitor.ts +++ b/src/sdam/monitor.ts @@ -5,7 +5,7 @@ import { connect, makeConnection, makeSocket, performInitialHandshake } from '.. import type { Connection, ConnectionOptions } from '../cmap/connection'; import { getFAASEnv } from '../cmap/handshake/client_metadata'; import { LEGACY_HELLO_COMMAND } from '../constants'; -import { MongoError, MongoErrorLabel, MongoNetworkTimeoutError } from '../error'; +import { MongoError, MongoErrorLabel, MongoNetworkTimeoutError, MongoServerError } from '../error'; import { MongoLoggableComponent } from '../mongo_logger'; import { CancellationToken, TypedEventEmitter } from '../mongo_types'; import type { Callback, EventEmitterWithState } from '../utils'; @@ -258,7 +258,7 @@ function checkServer(monitor: Monitor, callback: Callback) { ); const error = !(err instanceof MongoError) - ? new MongoError(MongoError.buildErrorMessage(err), { cause: err }) + ? new MongoServerError({ errmsg: MongoError.buildErrorMessage(err), cause: err }) : err; error.addErrorLabel(MongoErrorLabel.ResetPool); if (error instanceof MongoNetworkTimeoutError) { diff --git a/src/sdam/server.ts b/src/sdam/server.ts index f1a0bf1d98..edb96546c9 100644 --- a/src/sdam/server.ts +++ b/src/sdam/server.ts @@ -369,7 +369,7 @@ export class Server extends TypedEventEmitter { // clear for the specific service id. if (!this.loadBalanced) { error.addErrorLabel(MongoErrorLabel.ResetPool); - markServerUnknown(this, error as MongoServerError); + markServerUnknown(this, error); } else if (connection) { this.pool.clear({ serviceId: connection.serviceId }); } @@ -385,7 +385,7 @@ export class Server extends TypedEventEmitter { if (shouldClearPool) { error.addErrorLabel(MongoErrorLabel.ResetPool); } - markServerUnknown(this, error as MongoServerError); + markServerUnknown(this, error); process.nextTick(() => this.requestCheck()); } } @@ -488,7 +488,7 @@ function calculateRoundTripTime(oldRtt: number, duration: number): number { return alpha * duration + (1 - alpha) * oldRtt; } -function markServerUnknown(server: Server, error?: MongoServerError) { +function markServerUnknown(server: Server, error?: MongoError) { // Load balancer servers can never be marked unknown. if (server.loadBalanced) { return; diff --git a/src/sdam/server_description.ts b/src/sdam/server_description.ts index 62fe0aadde..ec9b1939db 100644 --- a/src/sdam/server_description.ts +++ b/src/sdam/server_description.ts @@ -1,5 +1,5 @@ import { type Document, Long, type ObjectId } from '../bson'; -import { type MongoError, MongoRuntimeError, type MongoServerError } from '../error'; +import { type MongoError, MongoRuntimeError } from '../error'; import { arrayStrictEqual, compareObjectId, errorStrictEqual, HostAddress, now } from '../utils'; import type { ClusterTime } from './common'; import { ServerType } from './common'; @@ -31,7 +31,7 @@ export type TagSet = { [key: string]: string }; /** @internal */ export interface ServerDescriptionOptions { /** An Error used for better reporting debugging */ - error?: MongoServerError; + error?: MongoError; /** The round trip time to ping this server (in ms) */ roundTripTime?: number; diff --git a/src/sdam/topology_description.ts b/src/sdam/topology_description.ts index f2fafaf87b..442b0fd4a6 100644 --- a/src/sdam/topology_description.ts +++ b/src/sdam/topology_description.ts @@ -1,6 +1,6 @@ import type { ObjectId } from '../bson'; import * as WIRE_CONSTANTS from '../cmap/wire_protocol/constants'; -import { MongoRuntimeError, type MongoServerError } from '../error'; +import { MongoError, MongoRuntimeError } from '../error'; import { compareObjectId, shuffle } from '../utils'; import { ServerType, TopologyType } from './common'; import { ServerDescription } from './server_description'; @@ -307,13 +307,13 @@ export class TopologyDescription { ); } - get error(): MongoServerError | null { + get error(): MongoError | null { const descriptionsWithError = Array.from(this.servers.values()).filter( (sd: ServerDescription) => sd.error ); if (descriptionsWithError.length > 0) { - return descriptionsWithError[0].error as MongoServerError; + return descriptionsWithError[0].error; } return null; From de5194991c3017daa3bbb77e4df52a2634fb612e Mon Sep 17 00:00:00 2001 From: Aditi Khare Date: Mon, 11 Mar 2024 13:28:02 -0400 Subject: [PATCH 4/4] removed extraneous change to monitor --- src/sdam/monitor.ts | 4 ++-- src/sdam/topology_description.ts | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/sdam/monitor.ts b/src/sdam/monitor.ts index 7b7df45c23..6accf8cd3c 100644 --- a/src/sdam/monitor.ts +++ b/src/sdam/monitor.ts @@ -5,7 +5,7 @@ import { connect, makeConnection, makeSocket, performInitialHandshake } from '.. import type { Connection, ConnectionOptions } from '../cmap/connection'; import { getFAASEnv } from '../cmap/handshake/client_metadata'; import { LEGACY_HELLO_COMMAND } from '../constants'; -import { MongoError, MongoErrorLabel, MongoNetworkTimeoutError, MongoServerError } from '../error'; +import { MongoError, MongoErrorLabel, MongoNetworkTimeoutError } from '../error'; import { MongoLoggableComponent } from '../mongo_logger'; import { CancellationToken, TypedEventEmitter } from '../mongo_types'; import type { Callback, EventEmitterWithState } from '../utils'; @@ -258,7 +258,7 @@ function checkServer(monitor: Monitor, callback: Callback) { ); const error = !(err instanceof MongoError) - ? new MongoServerError({ errmsg: MongoError.buildErrorMessage(err), cause: err }) + ? new MongoError(MongoError.buildErrorMessage(err), { cause: err }) : err; error.addErrorLabel(MongoErrorLabel.ResetPool); if (error instanceof MongoNetworkTimeoutError) { diff --git a/src/sdam/topology_description.ts b/src/sdam/topology_description.ts index 442b0fd4a6..5073429866 100644 --- a/src/sdam/topology_description.ts +++ b/src/sdam/topology_description.ts @@ -1,6 +1,6 @@ import type { ObjectId } from '../bson'; import * as WIRE_CONSTANTS from '../cmap/wire_protocol/constants'; -import { MongoError, MongoRuntimeError } from '../error'; +import { type MongoError, MongoRuntimeError } from '../error'; import { compareObjectId, shuffle } from '../utils'; import { ServerType, TopologyType } from './common'; import { ServerDescription } from './server_description';