mongodb 4.4.1 → 4.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -2
- package/lib/admin.js +5 -6
- package/lib/admin.js.map +1 -1
- package/lib/bulk/common.js +34 -7
- package/lib/bulk/common.js.map +1 -1
- package/lib/bulk/unordered.js.map +1 -1
- package/lib/change_stream.js +251 -245
- package/lib/change_stream.js.map +1 -1
- package/lib/cmap/auth/gssapi.js.map +1 -1
- package/lib/cmap/auth/mongocr.js.map +1 -1
- package/lib/cmap/auth/mongodb_aws.js +3 -0
- package/lib/cmap/auth/mongodb_aws.js.map +1 -1
- package/lib/cmap/auth/plain.js.map +1 -1
- package/lib/cmap/auth/scram.js +1 -0
- package/lib/cmap/auth/scram.js.map +1 -1
- package/lib/cmap/auth/x509.js.map +1 -1
- package/lib/cmap/commands.js +12 -11
- package/lib/cmap/commands.js.map +1 -1
- package/lib/cmap/connect.js +8 -1
- package/lib/cmap/connect.js.map +1 -1
- package/lib/cmap/connection.js +111 -145
- package/lib/cmap/connection.js.map +1 -1
- package/lib/cmap/errors.js.map +1 -1
- package/lib/cmap/message_stream.js.map +1 -1
- package/lib/cmap/stream_description.js +3 -0
- package/lib/cmap/stream_description.js.map +1 -1
- package/lib/collection.js +60 -29
- package/lib/collection.js.map +1 -1
- package/lib/connection_string.js +32 -11
- package/lib/connection_string.js.map +1 -1
- package/lib/constants.js +8 -1
- package/lib/constants.js.map +1 -1
- package/lib/cursor/abstract_cursor.js +64 -51
- package/lib/cursor/abstract_cursor.js.map +1 -1
- package/lib/cursor/aggregation_cursor.js +2 -2
- package/lib/cursor/aggregation_cursor.js.map +1 -1
- package/lib/cursor/find_cursor.js +9 -4
- package/lib/cursor/find_cursor.js.map +1 -1
- package/lib/db.js +20 -13
- package/lib/db.js.map +1 -1
- package/lib/encrypter.js +21 -10
- package/lib/encrypter.js.map +1 -1
- package/lib/error.js +121 -59
- package/lib/error.js.map +1 -1
- package/lib/gridfs/download.js +2 -0
- package/lib/gridfs/download.js.map +1 -1
- package/lib/gridfs/index.js +42 -51
- package/lib/gridfs/index.js.map +1 -1
- package/lib/gridfs/upload.js +1 -1
- package/lib/gridfs/upload.js.map +1 -1
- package/lib/index.js +7 -3
- package/lib/index.js.map +1 -1
- package/lib/mongo_client.js +21 -27
- package/lib/mongo_client.js.map +1 -1
- package/lib/operations/add_user.js +8 -1
- package/lib/operations/add_user.js.map +1 -1
- package/lib/operations/aggregate.js +5 -0
- package/lib/operations/aggregate.js.map +1 -1
- package/lib/operations/bulk_write.js.map +1 -1
- package/lib/operations/collections.js.map +1 -1
- package/lib/operations/command.js +0 -3
- package/lib/operations/command.js.map +1 -1
- package/lib/operations/common_functions.js +8 -1
- package/lib/operations/common_functions.js.map +1 -1
- package/lib/operations/count.js.map +1 -1
- package/lib/operations/count_documents.js.map +1 -1
- package/lib/operations/create_collection.js +51 -17
- package/lib/operations/create_collection.js.map +1 -1
- package/lib/operations/delete.js +5 -3
- package/lib/operations/delete.js.map +1 -1
- package/lib/operations/distinct.js.map +1 -1
- package/lib/operations/drop.js +67 -7
- package/lib/operations/drop.js.map +1 -1
- package/lib/operations/estimated_document_count.js.map +1 -1
- package/lib/operations/eval.js.map +1 -1
- package/lib/operations/execute_operation.js +71 -79
- package/lib/operations/execute_operation.js.map +1 -1
- package/lib/operations/find.js +3 -52
- package/lib/operations/find.js.map +1 -1
- package/lib/operations/find_and_modify.js +5 -0
- package/lib/operations/find_and_modify.js.map +1 -1
- package/lib/operations/get_more.js +5 -0
- package/lib/operations/get_more.js.map +1 -1
- package/lib/operations/indexes.js +8 -9
- package/lib/operations/indexes.js.map +1 -1
- package/lib/operations/insert.js +8 -2
- package/lib/operations/insert.js.map +1 -1
- package/lib/operations/is_capped.js.map +1 -1
- package/lib/operations/list_collections.js +10 -42
- package/lib/operations/list_collections.js.map +1 -1
- package/lib/operations/list_databases.js +5 -0
- package/lib/operations/list_databases.js.map +1 -1
- package/lib/operations/map_reduce.js +1 -2
- package/lib/operations/map_reduce.js.map +1 -1
- package/lib/operations/operation.js +1 -3
- package/lib/operations/operation.js.map +1 -1
- package/lib/operations/options_operation.js.map +1 -1
- package/lib/operations/profiling_level.js.map +1 -1
- package/lib/operations/remove_user.js.map +1 -1
- package/lib/operations/rename.js +1 -1
- package/lib/operations/rename.js.map +1 -1
- package/lib/operations/run_command.js.map +1 -1
- package/lib/operations/set_profiling_level.js.map +1 -1
- package/lib/operations/stats.js.map +1 -1
- package/lib/operations/update.js +5 -0
- package/lib/operations/update.js.map +1 -1
- package/lib/operations/validate_collection.js.map +1 -1
- package/lib/read_concern.js +1 -0
- package/lib/read_concern.js.map +1 -1
- package/lib/sdam/common.js +1 -7
- package/lib/sdam/common.js.map +1 -1
- package/lib/sdam/events.js +1 -1
- package/lib/sdam/events.js.map +1 -1
- package/lib/sdam/monitor.js +1 -2
- package/lib/sdam/monitor.js.map +1 -1
- package/lib/sdam/server.js +108 -78
- package/lib/sdam/server.js.map +1 -1
- package/lib/sdam/topology.js +38 -55
- package/lib/sdam/topology.js.map +1 -1
- package/lib/sdam/topology_description.js +3 -4
- package/lib/sdam/topology_description.js.map +1 -1
- package/lib/sessions.js +93 -68
- package/lib/sessions.js.map +1 -1
- package/lib/utils.js +21 -97
- package/lib/utils.js.map +1 -1
- package/mongodb.d.ts +417 -92
- package/package.json +25 -29
- package/src/admin.ts +6 -10
- package/src/bulk/common.ts +45 -14
- package/src/bulk/unordered.ts +1 -1
- package/src/change_stream.ts +559 -425
- package/src/cmap/auth/gssapi.ts +1 -1
- package/src/cmap/auth/mongocr.ts +1 -1
- package/src/cmap/auth/mongodb_aws.ts +6 -1
- package/src/cmap/auth/plain.ts +1 -1
- package/src/cmap/auth/scram.ts +3 -2
- package/src/cmap/auth/x509.ts +6 -2
- package/src/cmap/commands.ts +26 -22
- package/src/cmap/connect.ts +15 -14
- package/src/cmap/connection.ts +163 -185
- package/src/cmap/errors.ts +2 -2
- package/src/cmap/message_stream.ts +2 -2
- package/src/cmap/stream_description.ts +4 -1
- package/src/collection.ts +66 -35
- package/src/connection_string.ts +46 -18
- package/src/constants.ts +6 -0
- package/src/cursor/abstract_cursor.ts +87 -65
- package/src/cursor/aggregation_cursor.ts +4 -4
- package/src/cursor/find_cursor.ts +16 -8
- package/src/db.ts +27 -24
- package/src/deps.ts +40 -0
- package/src/encrypter.ts +22 -11
- package/src/error.ts +170 -89
- package/src/gridfs/download.ts +3 -1
- package/src/gridfs/index.ts +51 -68
- package/src/gridfs/upload.ts +13 -13
- package/src/index.ts +21 -0
- package/src/mongo_client.ts +36 -50
- package/src/mongo_types.ts +1 -1
- package/src/operations/add_user.ts +14 -3
- package/src/operations/aggregate.ts +15 -5
- package/src/operations/bulk_write.ts +6 -2
- package/src/operations/collections.ts +6 -2
- package/src/operations/command.ts +23 -12
- package/src/operations/common_functions.ts +8 -1
- package/src/operations/count.ts +6 -2
- package/src/operations/count_documents.ts +5 -1
- package/src/operations/create_collection.ts +91 -23
- package/src/operations/delete.ts +19 -13
- package/src/operations/distinct.ts +6 -2
- package/src/operations/drop.ts +100 -10
- package/src/operations/estimated_document_count.ts +11 -3
- package/src/operations/eval.ts +6 -2
- package/src/operations/execute_operation.ts +103 -101
- package/src/operations/find.ts +9 -85
- package/src/operations/find_and_modify.ts +21 -2
- package/src/operations/get_more.ts +20 -6
- package/src/operations/indexes.ts +54 -36
- package/src/operations/insert.ts +28 -7
- package/src/operations/is_capped.ts +6 -2
- package/src/operations/list_collections.ts +24 -59
- package/src/operations/list_databases.ts +13 -3
- package/src/operations/map_reduce.ts +7 -6
- package/src/operations/operation.ts +10 -9
- package/src/operations/options_operation.ts +6 -2
- package/src/operations/profiling_level.ts +6 -2
- package/src/operations/remove_user.ts +6 -2
- package/src/operations/rename.ts +7 -3
- package/src/operations/run_command.ts +6 -2
- package/src/operations/set_profiling_level.ts +6 -2
- package/src/operations/stats.ts +12 -4
- package/src/operations/update.ts +19 -9
- package/src/operations/validate_collection.ts +6 -2
- package/src/read_concern.ts +1 -0
- package/src/sdam/common.ts +0 -6
- package/src/sdam/events.ts +2 -2
- package/src/sdam/monitor.ts +4 -5
- package/src/sdam/server.ts +125 -117
- package/src/sdam/topology.ts +39 -78
- package/src/sdam/topology_description.ts +3 -4
- package/src/sessions.ts +108 -78
- package/src/utils.ts +39 -119
- package/tsconfig.json +40 -0
- package/mongodb.ts34.d.ts +0 -5720
package/src/cmap/connection.ts
CHANGED
|
@@ -21,7 +21,7 @@ import {
|
|
|
21
21
|
} from '../error';
|
|
22
22
|
import type { ServerApi, SupportedNodeConnectionOptions } from '../mongo_client';
|
|
23
23
|
import { CancellationToken, TypedEventEmitter } from '../mongo_types';
|
|
24
|
-
import { ReadPreference, ReadPreferenceLike } from '../read_preference';
|
|
24
|
+
import type { ReadPreference, ReadPreferenceLike } from '../read_preference';
|
|
25
25
|
import { applySession, ClientSession, updateSessionFromResponse } from '../sessions';
|
|
26
26
|
import {
|
|
27
27
|
calculateDurationInMs,
|
|
@@ -33,7 +33,7 @@ import {
|
|
|
33
33
|
now,
|
|
34
34
|
uuidV4
|
|
35
35
|
} from '../utils';
|
|
36
|
-
import type {
|
|
36
|
+
import type { WriteConcern } from '../write_concern';
|
|
37
37
|
import type { MongoCredentials } from './auth/mongo_credentials';
|
|
38
38
|
import {
|
|
39
39
|
CommandFailedEvent,
|
|
@@ -45,7 +45,6 @@ import {
|
|
|
45
45
|
GetMore,
|
|
46
46
|
KillCursor,
|
|
47
47
|
Msg,
|
|
48
|
-
OpQueryOptions,
|
|
49
48
|
Query,
|
|
50
49
|
Response,
|
|
51
50
|
WriteProtocolMessageType
|
|
@@ -75,6 +74,8 @@ const kHello = Symbol('hello');
|
|
|
75
74
|
const kAutoEncrypter = Symbol('autoEncrypter');
|
|
76
75
|
/** @internal */
|
|
77
76
|
const kFullResult = Symbol('fullResult');
|
|
77
|
+
/** @internal */
|
|
78
|
+
const kDelayedTimeoutId = Symbol('delayedTimeoutId');
|
|
78
79
|
|
|
79
80
|
/** @internal */
|
|
80
81
|
export interface QueryOptions extends BSONSerializeOptions {
|
|
@@ -109,11 +110,14 @@ export interface CommandOptions extends BSONSerializeOptions {
|
|
|
109
110
|
noResponse?: boolean;
|
|
110
111
|
omitReadPreference?: boolean;
|
|
111
112
|
|
|
112
|
-
//
|
|
113
|
+
// TODO(NODE-2802): Currently the CommandOptions take a property willRetryWrite which is a hint
|
|
114
|
+
// from executeOperation that the txnNum should be applied to this command.
|
|
115
|
+
// Applying a session to a command should happen as part of command construction,
|
|
116
|
+
// most likely in the CommandOperation#executeCommand method, where we have access to
|
|
117
|
+
// the details we need to determine if a txnNum should also be applied.
|
|
113
118
|
willRetryWrite?: boolean;
|
|
114
119
|
|
|
115
|
-
|
|
116
|
-
writeConcern?: WriteConcernOptions | WriteConcern | W;
|
|
120
|
+
writeConcern?: WriteConcern;
|
|
117
121
|
}
|
|
118
122
|
|
|
119
123
|
/** @internal */
|
|
@@ -121,7 +125,15 @@ export interface GetMoreOptions extends CommandOptions {
|
|
|
121
125
|
batchSize?: number;
|
|
122
126
|
maxTimeMS?: number;
|
|
123
127
|
maxAwaitTimeMS?: number;
|
|
124
|
-
|
|
128
|
+
/**
|
|
129
|
+
* Comment to apply to the operation.
|
|
130
|
+
*
|
|
131
|
+
* In server versions pre-4.4, 'comment' must be string. A server
|
|
132
|
+
* error will be thrown if any other type is provided.
|
|
133
|
+
*
|
|
134
|
+
* In server versions 4.4 and above, 'comment' can be any valid BSON type.
|
|
135
|
+
*/
|
|
136
|
+
comment?: unknown;
|
|
125
137
|
}
|
|
126
138
|
|
|
127
139
|
/** @public */
|
|
@@ -188,6 +200,9 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
188
200
|
lastHelloMS?: number;
|
|
189
201
|
serverApi?: ServerApi;
|
|
190
202
|
helloOk?: boolean;
|
|
203
|
+
|
|
204
|
+
/**@internal */
|
|
205
|
+
[kDelayedTimeoutId]: NodeJS.Timeout | null;
|
|
191
206
|
/** @internal */
|
|
192
207
|
[kDescription]: StreamDescription;
|
|
193
208
|
/** @internal */
|
|
@@ -201,9 +216,9 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
201
216
|
/** @internal */
|
|
202
217
|
[kStream]: Stream;
|
|
203
218
|
/** @internal */
|
|
204
|
-
[kHello]: Document;
|
|
219
|
+
[kHello]: Document | null;
|
|
205
220
|
/** @internal */
|
|
206
|
-
[kClusterTime]: Document;
|
|
221
|
+
[kClusterTime]: Document | null;
|
|
207
222
|
|
|
208
223
|
/** @event */
|
|
209
224
|
static readonly COMMAND_STARTED = COMMAND_STARTED;
|
|
@@ -231,6 +246,8 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
231
246
|
this.serverApi = options.serverApi;
|
|
232
247
|
this.closed = false;
|
|
233
248
|
this.destroyed = false;
|
|
249
|
+
this[kHello] = null;
|
|
250
|
+
this[kClusterTime] = null;
|
|
234
251
|
|
|
235
252
|
this[kDescription] = new StreamDescription(this.address, options);
|
|
236
253
|
this[kGeneration] = options.generation;
|
|
@@ -242,31 +259,33 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
242
259
|
...options,
|
|
243
260
|
maxBsonMessageSize: this.hello?.maxBsonMessageSize
|
|
244
261
|
});
|
|
245
|
-
this[kMessageStream].on('message', messageHandler(this));
|
|
246
262
|
this[kStream] = stream;
|
|
247
|
-
|
|
263
|
+
|
|
264
|
+
this[kDelayedTimeoutId] = null;
|
|
265
|
+
|
|
266
|
+
this[kMessageStream].on('message', message => this.onMessage(message));
|
|
267
|
+
this[kMessageStream].on('error', error => this.onError(error));
|
|
268
|
+
this[kStream].on('close', () => this.onClose());
|
|
269
|
+
this[kStream].on('timeout', () => this.onTimeout());
|
|
270
|
+
this[kStream].on('error', () => {
|
|
248
271
|
/* ignore errors, listen to `close` instead */
|
|
249
272
|
});
|
|
250
273
|
|
|
251
|
-
this[kMessageStream].on('error', error => this.handleIssue({ destroy: error }));
|
|
252
|
-
stream.on('close', () => this.handleIssue({ isClose: true }));
|
|
253
|
-
stream.on('timeout', () => this.handleIssue({ isTimeout: true, destroy: true }));
|
|
254
|
-
|
|
255
274
|
// hook the message stream up to the passed in stream
|
|
256
|
-
|
|
257
|
-
this[kMessageStream].pipe(
|
|
275
|
+
this[kStream].pipe(this[kMessageStream]);
|
|
276
|
+
this[kMessageStream].pipe(this[kStream]);
|
|
258
277
|
}
|
|
259
278
|
|
|
260
279
|
get description(): StreamDescription {
|
|
261
280
|
return this[kDescription];
|
|
262
281
|
}
|
|
263
282
|
|
|
264
|
-
get hello(): Document {
|
|
283
|
+
get hello(): Document | null {
|
|
265
284
|
return this[kHello];
|
|
266
285
|
}
|
|
267
286
|
|
|
268
287
|
// the `connect` method stores the result of the handshake hello on the connection
|
|
269
|
-
set hello(response: Document) {
|
|
288
|
+
set hello(response: Document | null) {
|
|
270
289
|
this[kDescription].receiveResponse(response);
|
|
271
290
|
this[kDescription] = Object.freeze(this[kDescription]);
|
|
272
291
|
|
|
@@ -294,7 +313,7 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
294
313
|
return calculateDurationInMs(this[kLastUseTime]);
|
|
295
314
|
}
|
|
296
315
|
|
|
297
|
-
get clusterTime(): Document {
|
|
316
|
+
get clusterTime(): Document | null {
|
|
298
317
|
return this[kClusterTime];
|
|
299
318
|
}
|
|
300
319
|
|
|
@@ -306,40 +325,133 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
306
325
|
this[kLastUseTime] = now();
|
|
307
326
|
}
|
|
308
327
|
|
|
309
|
-
|
|
328
|
+
onError(error: Error) {
|
|
310
329
|
if (this.closed) {
|
|
311
330
|
return;
|
|
312
331
|
}
|
|
313
332
|
|
|
314
|
-
|
|
315
|
-
|
|
333
|
+
this[kStream].destroy(error);
|
|
334
|
+
|
|
335
|
+
this.closed = true;
|
|
336
|
+
|
|
337
|
+
for (const op of this[kQueue].values()) {
|
|
338
|
+
op.cb(error);
|
|
339
|
+
}
|
|
340
|
+
|
|
341
|
+
this[kQueue].clear();
|
|
342
|
+
this.emit(Connection.CLOSE);
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
onClose() {
|
|
346
|
+
if (this.closed) {
|
|
347
|
+
return;
|
|
316
348
|
}
|
|
317
349
|
|
|
318
350
|
this.closed = true;
|
|
319
351
|
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
new MongoNetworkTimeoutError(`connection ${this.id} to ${this.address} timed out`, {
|
|
324
|
-
beforeHandshake: this.hello == null
|
|
325
|
-
})
|
|
326
|
-
);
|
|
327
|
-
} else if (issue.isClose) {
|
|
328
|
-
op.cb(new MongoNetworkError(`connection ${this.id} to ${this.address} closed`));
|
|
329
|
-
} else {
|
|
330
|
-
op.cb(typeof issue.destroy === 'boolean' ? undefined : issue.destroy);
|
|
331
|
-
}
|
|
352
|
+
const message = `connection ${this.id} to ${this.address} closed`;
|
|
353
|
+
for (const op of this[kQueue].values()) {
|
|
354
|
+
op.cb(new MongoNetworkError(message));
|
|
332
355
|
}
|
|
333
356
|
|
|
334
357
|
this[kQueue].clear();
|
|
335
358
|
this.emit(Connection.CLOSE);
|
|
336
359
|
}
|
|
337
360
|
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
361
|
+
onTimeout() {
|
|
362
|
+
if (this.closed) {
|
|
363
|
+
return;
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
this[kDelayedTimeoutId] = setTimeout(() => {
|
|
367
|
+
this[kStream].destroy();
|
|
368
|
+
|
|
369
|
+
this.closed = true;
|
|
370
|
+
|
|
371
|
+
const message = `connection ${this.id} to ${this.address} timed out`;
|
|
372
|
+
const beforeHandshake = this.hello == null;
|
|
373
|
+
for (const op of this[kQueue].values()) {
|
|
374
|
+
op.cb(new MongoNetworkTimeoutError(message, { beforeHandshake }));
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
this[kQueue].clear();
|
|
378
|
+
this.emit(Connection.CLOSE);
|
|
379
|
+
}, 1).unref(); // No need for this timer to hold the event loop open
|
|
380
|
+
}
|
|
381
|
+
|
|
382
|
+
onMessage(message: BinMsg | Response) {
|
|
383
|
+
const delayedTimeoutId = this[kDelayedTimeoutId];
|
|
384
|
+
if (delayedTimeoutId != null) {
|
|
385
|
+
clearTimeout(delayedTimeoutId);
|
|
386
|
+
this[kDelayedTimeoutId] = null;
|
|
387
|
+
}
|
|
388
|
+
|
|
389
|
+
// always emit the message, in case we are streaming
|
|
390
|
+
this.emit('message', message);
|
|
391
|
+
const operationDescription = this[kQueue].get(message.responseTo);
|
|
392
|
+
if (!operationDescription) {
|
|
393
|
+
return;
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
const callback = operationDescription.cb;
|
|
397
|
+
|
|
398
|
+
// SERVER-45775: For exhaust responses we should be able to use the same requestId to
|
|
399
|
+
// track response, however the server currently synthetically produces remote requests
|
|
400
|
+
// making the `responseTo` change on each response
|
|
401
|
+
this[kQueue].delete(message.responseTo);
|
|
402
|
+
if ('moreToCome' in message && message.moreToCome) {
|
|
403
|
+
// requeue the callback for next synthetic request
|
|
404
|
+
this[kQueue].set(message.requestId, operationDescription);
|
|
405
|
+
} else if (operationDescription.socketTimeoutOverride) {
|
|
406
|
+
this[kStream].setTimeout(this.socketTimeoutMS);
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
try {
|
|
410
|
+
// Pass in the entire description because it has BSON parsing options
|
|
411
|
+
message.parse(operationDescription);
|
|
412
|
+
} catch (err) {
|
|
413
|
+
// If this error is generated by our own code, it will already have the correct class applied
|
|
414
|
+
// if it is not, then it is coming from a catastrophic data parse failure or the BSON library
|
|
415
|
+
// in either case, it should not be wrapped
|
|
416
|
+
callback(err);
|
|
417
|
+
return;
|
|
418
|
+
}
|
|
419
|
+
|
|
420
|
+
if (message.documents[0]) {
|
|
421
|
+
const document: Document = message.documents[0];
|
|
422
|
+
const session = operationDescription.session;
|
|
423
|
+
if (session) {
|
|
424
|
+
updateSessionFromResponse(session, document);
|
|
425
|
+
}
|
|
426
|
+
|
|
427
|
+
if (document.$clusterTime) {
|
|
428
|
+
this[kClusterTime] = document.$clusterTime;
|
|
429
|
+
this.emit(Connection.CLUSTER_TIME_RECEIVED, document.$clusterTime);
|
|
430
|
+
}
|
|
431
|
+
|
|
432
|
+
if (operationDescription.command) {
|
|
433
|
+
if (document.writeConcernError) {
|
|
434
|
+
callback(new MongoWriteConcernError(document.writeConcernError, document));
|
|
435
|
+
return;
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
if (document.ok === 0 || document.$err || document.errmsg || document.code) {
|
|
439
|
+
callback(new MongoServerError(document));
|
|
440
|
+
return;
|
|
441
|
+
}
|
|
442
|
+
} else {
|
|
443
|
+
// Pre 3.2 support
|
|
444
|
+
if (document.ok === 0 || document.$err || document.errmsg) {
|
|
445
|
+
callback(new MongoServerError(document));
|
|
446
|
+
return;
|
|
447
|
+
}
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
callback(undefined, operationDescription.fullResult ? message : message.documents[0]);
|
|
452
|
+
}
|
|
453
|
+
|
|
454
|
+
destroy(options?: DestroyOptions, callback?: Callback): void {
|
|
343
455
|
if (typeof options === 'function') {
|
|
344
456
|
callback = options;
|
|
345
457
|
options = { force: false };
|
|
@@ -376,7 +488,6 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
376
488
|
});
|
|
377
489
|
}
|
|
378
490
|
|
|
379
|
-
/** @internal */
|
|
380
491
|
command(
|
|
381
492
|
ns: MongoDBNamespace,
|
|
382
493
|
cmd: Document,
|
|
@@ -453,80 +564,6 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
453
564
|
}
|
|
454
565
|
}
|
|
455
566
|
|
|
456
|
-
/** @internal */
|
|
457
|
-
query(ns: MongoDBNamespace, cmd: Document, options: QueryOptions, callback: Callback): void {
|
|
458
|
-
const isExplain = cmd.$explain != null;
|
|
459
|
-
const readPreference = options.readPreference ?? ReadPreference.primary;
|
|
460
|
-
const batchSize = options.batchSize || 0;
|
|
461
|
-
const limit = options.limit;
|
|
462
|
-
const numberToSkip = options.skip || 0;
|
|
463
|
-
let numberToReturn = 0;
|
|
464
|
-
if (
|
|
465
|
-
limit &&
|
|
466
|
-
(limit < 0 || (limit !== 0 && limit < batchSize) || (limit > 0 && batchSize === 0))
|
|
467
|
-
) {
|
|
468
|
-
numberToReturn = limit;
|
|
469
|
-
} else {
|
|
470
|
-
numberToReturn = batchSize;
|
|
471
|
-
}
|
|
472
|
-
|
|
473
|
-
if (isExplain) {
|
|
474
|
-
// nToReturn must be 0 (match all) or negative (match N and close cursor)
|
|
475
|
-
// nToReturn > 0 will give explain results equivalent to limit(0)
|
|
476
|
-
numberToReturn = -Math.abs(limit || 0);
|
|
477
|
-
}
|
|
478
|
-
|
|
479
|
-
const queryOptions: OpQueryOptions = {
|
|
480
|
-
numberToSkip,
|
|
481
|
-
numberToReturn,
|
|
482
|
-
pre32Limit: typeof limit === 'number' ? limit : undefined,
|
|
483
|
-
checkKeys: false,
|
|
484
|
-
secondaryOk: readPreference.secondaryOk()
|
|
485
|
-
};
|
|
486
|
-
|
|
487
|
-
if (options.projection) {
|
|
488
|
-
queryOptions.returnFieldSelector = options.projection;
|
|
489
|
-
}
|
|
490
|
-
|
|
491
|
-
const query = new Query(ns.toString(), cmd, queryOptions);
|
|
492
|
-
if (typeof options.tailable === 'boolean') {
|
|
493
|
-
query.tailable = options.tailable;
|
|
494
|
-
}
|
|
495
|
-
|
|
496
|
-
if (typeof options.oplogReplay === 'boolean') {
|
|
497
|
-
query.oplogReplay = options.oplogReplay;
|
|
498
|
-
}
|
|
499
|
-
|
|
500
|
-
if (typeof options.timeout === 'boolean') {
|
|
501
|
-
query.noCursorTimeout = !options.timeout;
|
|
502
|
-
} else if (typeof options.noCursorTimeout === 'boolean') {
|
|
503
|
-
query.noCursorTimeout = options.noCursorTimeout;
|
|
504
|
-
}
|
|
505
|
-
|
|
506
|
-
if (typeof options.awaitData === 'boolean') {
|
|
507
|
-
query.awaitData = options.awaitData;
|
|
508
|
-
}
|
|
509
|
-
|
|
510
|
-
if (typeof options.partial === 'boolean') {
|
|
511
|
-
query.partial = options.partial;
|
|
512
|
-
}
|
|
513
|
-
|
|
514
|
-
write(
|
|
515
|
-
this,
|
|
516
|
-
query,
|
|
517
|
-
{ [kFullResult]: true, ...pluckBSONSerializeOptions(options) },
|
|
518
|
-
(err, result) => {
|
|
519
|
-
if (err || !result) return callback(err, result);
|
|
520
|
-
if (isExplain && result.documents && result.documents[0]) {
|
|
521
|
-
return callback(undefined, result.documents[0]);
|
|
522
|
-
}
|
|
523
|
-
|
|
524
|
-
callback(undefined, result);
|
|
525
|
-
}
|
|
526
|
-
);
|
|
527
|
-
}
|
|
528
|
-
|
|
529
|
-
/** @internal */
|
|
530
567
|
getMore(
|
|
531
568
|
ns: MongoDBNamespace,
|
|
532
569
|
cursorId: Long,
|
|
@@ -571,6 +608,11 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
571
608
|
if (typeof options.maxAwaitTimeMS === 'number') {
|
|
572
609
|
getMoreCmd.maxTimeMS = options.maxAwaitTimeMS;
|
|
573
610
|
}
|
|
611
|
+
// we check for undefined specifically here to allow falsy values
|
|
612
|
+
// eslint-disable-next-line no-restricted-syntax
|
|
613
|
+
if (options.comment !== undefined) {
|
|
614
|
+
getMoreCmd.comment = options.comment;
|
|
615
|
+
}
|
|
574
616
|
|
|
575
617
|
const commandOptions = Object.assign(
|
|
576
618
|
{
|
|
@@ -583,7 +625,6 @@ export class Connection extends TypedEventEmitter<ConnectionEvents> {
|
|
|
583
625
|
this.command(ns, getMoreCmd, commandOptions, callback);
|
|
584
626
|
}
|
|
585
627
|
|
|
586
|
-
/** @internal */
|
|
587
628
|
killCursors(
|
|
588
629
|
ns: MongoDBNamespace,
|
|
589
630
|
cursorIds: Long[],
|
|
@@ -646,7 +687,12 @@ export class CryptoConnection extends Connection {
|
|
|
646
687
|
}
|
|
647
688
|
|
|
648
689
|
/** @internal @override */
|
|
649
|
-
command(
|
|
690
|
+
override command(
|
|
691
|
+
ns: MongoDBNamespace,
|
|
692
|
+
cmd: Document,
|
|
693
|
+
options: CommandOptions,
|
|
694
|
+
callback: Callback
|
|
695
|
+
): void {
|
|
650
696
|
const autoEncrypter = this[kAutoEncrypter];
|
|
651
697
|
if (!autoEncrypter) {
|
|
652
698
|
return callback(new MongoMissingDependencyError('No AutoEncrypter available for encryption'));
|
|
@@ -698,74 +744,6 @@ function supportsOpMsg(conn: Connection) {
|
|
|
698
744
|
return maxWireVersion(conn) >= 6 && !description.__nodejs_mock_server__;
|
|
699
745
|
}
|
|
700
746
|
|
|
701
|
-
function messageHandler(conn: Connection) {
|
|
702
|
-
return function messageHandler(message: BinMsg | Response) {
|
|
703
|
-
// always emit the message, in case we are streaming
|
|
704
|
-
conn.emit('message', message);
|
|
705
|
-
const operationDescription = conn[kQueue].get(message.responseTo);
|
|
706
|
-
if (!operationDescription) {
|
|
707
|
-
return;
|
|
708
|
-
}
|
|
709
|
-
|
|
710
|
-
const callback = operationDescription.cb;
|
|
711
|
-
|
|
712
|
-
// SERVER-45775: For exhaust responses we should be able to use the same requestId to
|
|
713
|
-
// track response, however the server currently synthetically produces remote requests
|
|
714
|
-
// making the `responseTo` change on each response
|
|
715
|
-
conn[kQueue].delete(message.responseTo);
|
|
716
|
-
if ('moreToCome' in message && message.moreToCome) {
|
|
717
|
-
// requeue the callback for next synthetic request
|
|
718
|
-
conn[kQueue].set(message.requestId, operationDescription);
|
|
719
|
-
} else if (operationDescription.socketTimeoutOverride) {
|
|
720
|
-
conn[kStream].setTimeout(conn.socketTimeoutMS);
|
|
721
|
-
}
|
|
722
|
-
|
|
723
|
-
try {
|
|
724
|
-
// Pass in the entire description because it has BSON parsing options
|
|
725
|
-
message.parse(operationDescription);
|
|
726
|
-
} catch (err) {
|
|
727
|
-
// If this error is generated by our own code, it will already have the correct class applied
|
|
728
|
-
// if it is not, then it is coming from a catastrophic data parse failure or the BSON library
|
|
729
|
-
// in either case, it should not be wrapped
|
|
730
|
-
callback(err);
|
|
731
|
-
return;
|
|
732
|
-
}
|
|
733
|
-
|
|
734
|
-
if (message.documents[0]) {
|
|
735
|
-
const document: Document = message.documents[0];
|
|
736
|
-
const session = operationDescription.session;
|
|
737
|
-
if (session) {
|
|
738
|
-
updateSessionFromResponse(session, document);
|
|
739
|
-
}
|
|
740
|
-
|
|
741
|
-
if (document.$clusterTime) {
|
|
742
|
-
conn[kClusterTime] = document.$clusterTime;
|
|
743
|
-
conn.emit(Connection.CLUSTER_TIME_RECEIVED, document.$clusterTime);
|
|
744
|
-
}
|
|
745
|
-
|
|
746
|
-
if (operationDescription.command) {
|
|
747
|
-
if (document.writeConcernError) {
|
|
748
|
-
callback(new MongoWriteConcernError(document.writeConcernError, document));
|
|
749
|
-
return;
|
|
750
|
-
}
|
|
751
|
-
|
|
752
|
-
if (document.ok === 0 || document.$err || document.errmsg || document.code) {
|
|
753
|
-
callback(new MongoServerError(document));
|
|
754
|
-
return;
|
|
755
|
-
}
|
|
756
|
-
} else {
|
|
757
|
-
// Pre 3.2 support
|
|
758
|
-
if (document.ok === 0 || document.$err || document.errmsg) {
|
|
759
|
-
callback(new MongoServerError(document));
|
|
760
|
-
return;
|
|
761
|
-
}
|
|
762
|
-
}
|
|
763
|
-
}
|
|
764
|
-
|
|
765
|
-
callback(undefined, operationDescription.fullResult ? message : message.documents[0]);
|
|
766
|
-
};
|
|
767
|
-
}
|
|
768
|
-
|
|
769
747
|
function streamIdentifier(stream: Stream, options: ConnectionOptions): string {
|
|
770
748
|
if (options.proxyHost) {
|
|
771
749
|
// If proxy options are specified, the properties of `stream` itself
|
package/src/cmap/errors.ts
CHANGED
|
@@ -14,7 +14,7 @@ export class PoolClosedError extends MongoDriverError {
|
|
|
14
14
|
this.address = pool.address;
|
|
15
15
|
}
|
|
16
16
|
|
|
17
|
-
get name(): string {
|
|
17
|
+
override get name(): string {
|
|
18
18
|
return 'MongoPoolClosedError';
|
|
19
19
|
}
|
|
20
20
|
}
|
|
@@ -32,7 +32,7 @@ export class WaitQueueTimeoutError extends MongoDriverError {
|
|
|
32
32
|
this.address = address;
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
get name(): string {
|
|
35
|
+
override get name(): string {
|
|
36
36
|
return 'MongoWaitQueueTimeoutError';
|
|
37
37
|
}
|
|
38
38
|
}
|
|
@@ -60,12 +60,12 @@ export class MessageStream extends Duplex {
|
|
|
60
60
|
this[kBuffer] = new BufferPool();
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
-
_write(chunk: Buffer, _: unknown, callback: Callback<Buffer>): void {
|
|
63
|
+
override _write(chunk: Buffer, _: unknown, callback: Callback<Buffer>): void {
|
|
64
64
|
this[kBuffer].append(chunk);
|
|
65
65
|
processIncomingData(this, callback);
|
|
66
66
|
}
|
|
67
67
|
|
|
68
|
-
_read(/* size */): void {
|
|
68
|
+
override _read(/* size */): void {
|
|
69
69
|
// NOTE: This implementation is empty because we explicitly push data to be read
|
|
70
70
|
// when `writeMessage` is called.
|
|
71
71
|
return;
|
|
@@ -53,7 +53,10 @@ export class StreamDescription {
|
|
|
53
53
|
: [];
|
|
54
54
|
}
|
|
55
55
|
|
|
56
|
-
receiveResponse(response: Document): void {
|
|
56
|
+
receiveResponse(response: Document | null): void {
|
|
57
|
+
if (response == null) {
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
57
60
|
this.type = parseServerType(response);
|
|
58
61
|
for (const field of RESPONSE_FIELDS) {
|
|
59
62
|
if (response[field] != null) {
|