mongodb 3.2.5 → 3.3.0-beta2

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.
Files changed (133) hide show
  1. package/HISTORY.md +0 -10
  2. package/index.js +4 -4
  3. package/lib/admin.js +56 -56
  4. package/lib/aggregation_cursor.js +7 -3
  5. package/lib/bulk/common.js +18 -13
  6. package/lib/change_stream.js +196 -89
  7. package/lib/collection.js +217 -169
  8. package/lib/command_cursor.js +17 -7
  9. package/lib/core/auth/auth_provider.js +158 -0
  10. package/lib/core/auth/defaultAuthProviders.js +29 -0
  11. package/lib/core/auth/gssapi.js +241 -0
  12. package/lib/core/auth/mongo_credentials.js +81 -0
  13. package/lib/core/auth/mongocr.js +51 -0
  14. package/lib/core/auth/plain.js +35 -0
  15. package/lib/core/auth/scram.js +293 -0
  16. package/lib/core/auth/sspi.js +131 -0
  17. package/lib/core/auth/x509.js +26 -0
  18. package/lib/core/connection/apm.js +236 -0
  19. package/lib/core/connection/command_result.js +36 -0
  20. package/lib/core/connection/commands.js +507 -0
  21. package/lib/core/connection/connect.js +370 -0
  22. package/lib/core/connection/connection.js +624 -0
  23. package/lib/core/connection/logger.js +246 -0
  24. package/lib/core/connection/msg.js +219 -0
  25. package/lib/core/connection/pool.js +1285 -0
  26. package/lib/core/connection/utils.js +57 -0
  27. package/lib/core/cursor.js +752 -0
  28. package/lib/core/error.js +186 -0
  29. package/lib/core/index.js +50 -0
  30. package/lib/core/sdam/monitoring.js +228 -0
  31. package/lib/core/sdam/server.js +467 -0
  32. package/lib/core/sdam/server_description.js +163 -0
  33. package/lib/core/sdam/server_selectors.js +244 -0
  34. package/lib/core/sdam/srv_polling.js +135 -0
  35. package/lib/core/sdam/topology.js +1151 -0
  36. package/lib/core/sdam/topology_description.js +408 -0
  37. package/lib/core/sessions.js +711 -0
  38. package/lib/core/tools/smoke_plugin.js +61 -0
  39. package/lib/core/topologies/mongos.js +1337 -0
  40. package/lib/core/topologies/read_preference.js +202 -0
  41. package/lib/core/topologies/replset.js +1507 -0
  42. package/lib/core/topologies/replset_state.js +1121 -0
  43. package/lib/core/topologies/server.js +984 -0
  44. package/lib/core/topologies/shared.js +453 -0
  45. package/lib/core/transactions.js +167 -0
  46. package/lib/core/uri_parser.js +631 -0
  47. package/lib/core/utils.js +165 -0
  48. package/lib/core/wireprotocol/command.js +170 -0
  49. package/lib/core/wireprotocol/compression.js +73 -0
  50. package/lib/core/wireprotocol/constants.js +13 -0
  51. package/lib/core/wireprotocol/get_more.js +86 -0
  52. package/lib/core/wireprotocol/index.js +18 -0
  53. package/lib/core/wireprotocol/kill_cursors.js +70 -0
  54. package/lib/core/wireprotocol/query.js +224 -0
  55. package/lib/core/wireprotocol/shared.js +115 -0
  56. package/lib/core/wireprotocol/write_command.js +50 -0
  57. package/lib/cursor.js +40 -46
  58. package/lib/db.js +141 -95
  59. package/lib/dynamic_loaders.js +32 -0
  60. package/lib/error.js +12 -10
  61. package/lib/gridfs/chunk.js +2 -2
  62. package/lib/gridfs/grid_store.js +31 -25
  63. package/lib/gridfs-stream/index.js +4 -4
  64. package/lib/gridfs-stream/upload.js +1 -1
  65. package/lib/mongo_client.js +37 -15
  66. package/lib/operations/add_user.js +96 -0
  67. package/lib/operations/aggregate.js +24 -13
  68. package/lib/operations/aggregate_operation.js +127 -0
  69. package/lib/operations/bulk_write.js +104 -0
  70. package/lib/operations/close.js +47 -0
  71. package/lib/operations/collection_ops.js +28 -287
  72. package/lib/operations/collections.js +55 -0
  73. package/lib/operations/command.js +120 -0
  74. package/lib/operations/command_v2.js +43 -0
  75. package/lib/operations/common_functions.js +372 -0
  76. package/lib/operations/{mongo_client_ops.js → connect.js} +185 -157
  77. package/lib/operations/count.js +72 -0
  78. package/lib/operations/count_documents.js +46 -0
  79. package/lib/operations/create_collection.js +118 -0
  80. package/lib/operations/create_index.js +92 -0
  81. package/lib/operations/create_indexes.js +61 -0
  82. package/lib/operations/cursor_ops.js +3 -4
  83. package/lib/operations/db_ops.js +15 -12
  84. package/lib/operations/delete_many.js +25 -0
  85. package/lib/operations/delete_one.js +25 -0
  86. package/lib/operations/distinct.js +85 -0
  87. package/lib/operations/drop.js +53 -0
  88. package/lib/operations/drop_index.js +42 -0
  89. package/lib/operations/drop_indexes.js +23 -0
  90. package/lib/operations/estimated_document_count.js +33 -0
  91. package/lib/operations/execute_db_admin_command.js +34 -0
  92. package/lib/operations/execute_operation.js +165 -0
  93. package/lib/operations/explain.js +23 -0
  94. package/lib/operations/find_and_modify.js +98 -0
  95. package/lib/operations/find_one.js +33 -0
  96. package/lib/operations/find_one_and_delete.js +16 -0
  97. package/lib/operations/find_one_and_replace.js +18 -0
  98. package/lib/operations/find_one_and_update.js +19 -0
  99. package/lib/operations/geo_haystack_search.js +79 -0
  100. package/lib/operations/has_next.js +40 -0
  101. package/lib/operations/index_exists.js +39 -0
  102. package/lib/operations/index_information.js +23 -0
  103. package/lib/operations/indexes.js +22 -0
  104. package/lib/operations/insert_many.js +63 -0
  105. package/lib/operations/insert_one.js +75 -0
  106. package/lib/operations/is_capped.js +19 -0
  107. package/lib/operations/list_indexes.js +66 -0
  108. package/lib/operations/map_reduce.js +189 -0
  109. package/lib/operations/next.js +32 -0
  110. package/lib/operations/operation.js +63 -0
  111. package/lib/operations/options_operation.js +32 -0
  112. package/lib/operations/profiling_level.js +31 -0
  113. package/lib/operations/re_index.js +28 -0
  114. package/lib/operations/remove_user.js +52 -0
  115. package/lib/operations/rename.js +61 -0
  116. package/lib/operations/replace_one.js +47 -0
  117. package/lib/operations/set_profiling_level.js +48 -0
  118. package/lib/operations/stats.js +45 -0
  119. package/lib/operations/to_array.js +68 -0
  120. package/lib/operations/update_many.js +29 -0
  121. package/lib/operations/update_one.js +44 -0
  122. package/lib/operations/validate_collection.js +40 -0
  123. package/lib/read_concern.js +55 -0
  124. package/lib/topologies/mongos.js +3 -3
  125. package/lib/topologies/native_topology.js +22 -2
  126. package/lib/topologies/replset.js +3 -3
  127. package/lib/topologies/server.js +4 -4
  128. package/lib/topologies/topology_base.js +6 -6
  129. package/lib/url_parser.js +4 -3
  130. package/lib/utils.js +46 -59
  131. package/lib/write_concern.js +66 -0
  132. package/package.json +15 -6
  133. package/lib/.DS_Store +0 -0
@@ -0,0 +1,165 @@
1
+ 'use strict';
2
+
3
+ const crypto = require('crypto');
4
+ const requireOptional = require('require_optional');
5
+
6
+ /**
7
+ * Generate a UUIDv4
8
+ */
9
+ const uuidV4 = () => {
10
+ const result = crypto.randomBytes(16);
11
+ result[6] = (result[6] & 0x0f) | 0x40;
12
+ result[8] = (result[8] & 0x3f) | 0x80;
13
+ return result;
14
+ };
15
+
16
+ /**
17
+ * Returns the duration calculated from two high resolution timers in milliseconds
18
+ *
19
+ * @param {Object} started A high resolution timestamp created from `process.hrtime()`
20
+ * @returns {Number} The duration in milliseconds
21
+ */
22
+ const calculateDurationInMs = started => {
23
+ const hrtime = process.hrtime(started);
24
+ return (hrtime[0] * 1e9 + hrtime[1]) / 1e6;
25
+ };
26
+
27
+ /**
28
+ * Relays events for a given listener and emitter
29
+ *
30
+ * @param {EventEmitter} listener the EventEmitter to listen to the events from
31
+ * @param {EventEmitter} emitter the EventEmitter to relay the events to
32
+ */
33
+ function relayEvents(listener, emitter, events) {
34
+ events.forEach(eventName => listener.on(eventName, event => emitter.emit(eventName, event)));
35
+ }
36
+
37
+ function retrieveKerberos() {
38
+ let kerberos;
39
+
40
+ try {
41
+ kerberos = requireOptional('kerberos');
42
+ } catch (err) {
43
+ if (err.code === 'MODULE_NOT_FOUND') {
44
+ throw new Error('The `kerberos` module was not found. Please install it and try again.');
45
+ }
46
+
47
+ throw err;
48
+ }
49
+
50
+ return kerberos;
51
+ }
52
+
53
+ // Throw an error if an attempt to use EJSON is made when it is not installed
54
+ const noEJSONError = function() {
55
+ throw new Error('The `mongodb-extjson` module was not found. Please install it and try again.');
56
+ };
57
+
58
+ // Facilitate loading EJSON optionally
59
+ function retrieveEJSON() {
60
+ let EJSON = null;
61
+ try {
62
+ EJSON = requireOptional('mongodb-extjson');
63
+ } catch (error) {} // eslint-disable-line
64
+ if (!EJSON) {
65
+ EJSON = {
66
+ parse: noEJSONError,
67
+ deserialize: noEJSONError,
68
+ serialize: noEJSONError,
69
+ stringify: noEJSONError,
70
+ setBSONModule: noEJSONError,
71
+ BSON: noEJSONError
72
+ };
73
+ }
74
+
75
+ return EJSON;
76
+ }
77
+
78
+ /**
79
+ * A helper function for determining `maxWireVersion` between legacy and new topology
80
+ * instances
81
+ *
82
+ * @private
83
+ * @param {(Topology|Server)} topologyOrServer
84
+ */
85
+ function maxWireVersion(topologyOrServer) {
86
+ if (topologyOrServer.ismaster) {
87
+ return topologyOrServer.ismaster.maxWireVersion;
88
+ }
89
+
90
+ if (topologyOrServer.description) {
91
+ return topologyOrServer.description.maxWireVersion;
92
+ }
93
+
94
+ return null;
95
+ }
96
+
97
+ /*
98
+ * Checks that collation is supported by server.
99
+ *
100
+ * @param {Server} [server] to check against
101
+ * @param {object} [cmd] object where collation may be specified
102
+ * @param {function} [callback] callback function
103
+ * @return true if server does not support collation
104
+ */
105
+ function collationNotSupported(server, cmd) {
106
+ return cmd && cmd.collation && maxWireVersion(server) < 5;
107
+ }
108
+
109
+ /**
110
+ * Checks if a given value is a Promise
111
+ *
112
+ * @param {*} maybePromise
113
+ * @return true if the provided value is a Promise
114
+ */
115
+ function isPromiseLike(maybePromise) {
116
+ return maybePromise && typeof maybePromise.then === 'function';
117
+ }
118
+
119
+ /**
120
+ * Applies the function `eachFn` to each item in `arr`, in parallel.
121
+ *
122
+ * @param {array} arr an array of items to asynchronusly iterate over
123
+ * @param {function} eachFn A function to call on each item of the array. The callback signature is `(item, callback)`, where the callback indicates iteration is complete.
124
+ * @param {function} callback The callback called after every item has been iterated
125
+ */
126
+ function eachAsync(arr, eachFn, callback) {
127
+ if (arr.length === 0) {
128
+ callback(null);
129
+ return;
130
+ }
131
+
132
+ const length = arr.length;
133
+ let completed = 0;
134
+ function eachCallback(err) {
135
+ if (err) {
136
+ callback(err, null);
137
+ return;
138
+ }
139
+
140
+ if (++completed === length) {
141
+ callback(null);
142
+ }
143
+ }
144
+
145
+ for (let idx = 0; idx < length; ++idx) {
146
+ eachFn(arr[idx], eachCallback);
147
+ }
148
+ }
149
+
150
+ function isUnifiedTopology(topology) {
151
+ return topology.description != null;
152
+ }
153
+
154
+ module.exports = {
155
+ uuidV4,
156
+ calculateDurationInMs,
157
+ relayEvents,
158
+ collationNotSupported,
159
+ retrieveEJSON,
160
+ retrieveKerberos,
161
+ maxWireVersion,
162
+ isPromiseLike,
163
+ eachAsync,
164
+ isUnifiedTopology
165
+ };
@@ -0,0 +1,170 @@
1
+ 'use strict';
2
+
3
+ const Query = require('../connection/commands').Query;
4
+ const Msg = require('../connection/msg').Msg;
5
+ const MongoError = require('../error').MongoError;
6
+ const getReadPreference = require('./shared').getReadPreference;
7
+ const isSharded = require('./shared').isSharded;
8
+ const databaseNamespace = require('./shared').databaseNamespace;
9
+ const isTransactionCommand = require('../transactions').isTransactionCommand;
10
+ const applySession = require('../sessions').applySession;
11
+
12
+ function isClientEncryptionEnabled(server) {
13
+ return server.autoEncrypter;
14
+ }
15
+
16
+ function command(server, ns, cmd, options, callback) {
17
+ if (typeof options === 'function') (callback = options), (options = {});
18
+ options = options || {};
19
+
20
+ if (cmd == null) {
21
+ return callback(new MongoError(`command ${JSON.stringify(cmd)} does not return a cursor`));
22
+ }
23
+
24
+ if (!isClientEncryptionEnabled(server)) {
25
+ _command(server, ns, cmd, options, callback);
26
+ return;
27
+ }
28
+
29
+ _cryptCommand(server, ns, cmd, options, callback);
30
+ }
31
+
32
+ function _command(server, ns, cmd, options, callback) {
33
+ const bson = server.s.bson;
34
+ const pool = server.s.pool;
35
+ const readPreference = getReadPreference(cmd, options);
36
+ const shouldUseOpMsg = supportsOpMsg(server);
37
+ const session = options.session;
38
+
39
+ let clusterTime = server.clusterTime;
40
+ let finalCmd = Object.assign({}, cmd);
41
+ if (hasSessionSupport(server) && session) {
42
+ if (
43
+ session.clusterTime &&
44
+ session.clusterTime.clusterTime.greaterThan(clusterTime.clusterTime)
45
+ ) {
46
+ clusterTime = session.clusterTime;
47
+ }
48
+
49
+ const err = applySession(session, finalCmd, options);
50
+ if (err) {
51
+ return callback(err);
52
+ }
53
+ }
54
+
55
+ // if we have a known cluster time, gossip it
56
+ if (clusterTime) {
57
+ finalCmd.$clusterTime = clusterTime;
58
+ }
59
+
60
+ if (
61
+ isSharded(server) &&
62
+ !shouldUseOpMsg &&
63
+ readPreference &&
64
+ readPreference.preference !== 'primary'
65
+ ) {
66
+ finalCmd = {
67
+ $query: finalCmd,
68
+ $readPreference: readPreference.toJSON()
69
+ };
70
+ }
71
+
72
+ const commandOptions = Object.assign(
73
+ {
74
+ command: true,
75
+ numberToSkip: 0,
76
+ numberToReturn: -1,
77
+ checkKeys: false
78
+ },
79
+ options
80
+ );
81
+
82
+ // This value is not overridable
83
+ commandOptions.slaveOk = readPreference.slaveOk();
84
+
85
+ const cmdNs = `${databaseNamespace(ns)}.$cmd`;
86
+ const message = shouldUseOpMsg
87
+ ? new Msg(bson, cmdNs, finalCmd, commandOptions)
88
+ : new Query(bson, cmdNs, finalCmd, commandOptions);
89
+
90
+ const inTransaction = session && (session.inTransaction() || isTransactionCommand(finalCmd));
91
+ const commandResponseHandler = inTransaction
92
+ ? function(err) {
93
+ if (
94
+ !cmd.commitTransaction &&
95
+ err &&
96
+ err instanceof MongoError &&
97
+ err.hasErrorLabel('TransientTransactionError')
98
+ ) {
99
+ session.transaction.unpinServer();
100
+ }
101
+
102
+ return callback.apply(null, arguments);
103
+ }
104
+ : callback;
105
+
106
+ try {
107
+ pool.write(message, commandOptions, commandResponseHandler);
108
+ } catch (err) {
109
+ commandResponseHandler(err);
110
+ }
111
+ }
112
+
113
+ function hasSessionSupport(topology) {
114
+ if (topology == null) return false;
115
+ if (topology.description) {
116
+ return topology.description.maxWireVersion >= 6;
117
+ }
118
+
119
+ return topology.ismaster == null ? false : topology.ismaster.maxWireVersion >= 6;
120
+ }
121
+
122
+ function supportsOpMsg(topologyOrServer) {
123
+ const description = topologyOrServer.ismaster
124
+ ? topologyOrServer.ismaster
125
+ : topologyOrServer.description;
126
+
127
+ if (description == null) {
128
+ return false;
129
+ }
130
+
131
+ return description.maxWireVersion >= 6 && description.__nodejs_mock_server__ == null;
132
+ }
133
+
134
+ function _cryptCommand(server, ns, cmd, options, callback) {
135
+ const shouldBypassAutoEncryption = !!server.s.options.bypassAutoEncryption;
136
+ const autoEncrypter = server.autoEncrypter;
137
+ function commandResponseHandler(err, response) {
138
+ if (err || response == null) {
139
+ callback(err, response);
140
+ return;
141
+ }
142
+
143
+ autoEncrypter.decrypt(response.result, (err, decrypted) => {
144
+ if (err) {
145
+ callback(err, null);
146
+ return;
147
+ }
148
+
149
+ response.result = decrypted;
150
+ response.message.documents = [decrypted];
151
+ callback(null, response);
152
+ });
153
+ }
154
+
155
+ if (shouldBypassAutoEncryption) {
156
+ _command(server, ns, cmd, options, commandResponseHandler);
157
+ return;
158
+ }
159
+
160
+ autoEncrypter.encrypt(ns, cmd, (err, encrypted) => {
161
+ if (err) {
162
+ callback(err, null);
163
+ return;
164
+ }
165
+
166
+ _command(server, ns, encrypted, options, commandResponseHandler);
167
+ });
168
+ }
169
+
170
+ module.exports = command;
@@ -0,0 +1,73 @@
1
+ 'use strict';
2
+
3
+ var Snappy = require('../connection/utils').retrieveSnappy(),
4
+ zlib = require('zlib');
5
+
6
+ var compressorIDs = {
7
+ snappy: 1,
8
+ zlib: 2
9
+ };
10
+
11
+ var uncompressibleCommands = [
12
+ 'ismaster',
13
+ 'saslStart',
14
+ 'saslContinue',
15
+ 'getnonce',
16
+ 'authenticate',
17
+ 'createUser',
18
+ 'updateUser',
19
+ 'copydbSaslStart',
20
+ 'copydbgetnonce',
21
+ 'copydb'
22
+ ];
23
+
24
+ // Facilitate compressing a message using an agreed compressor
25
+ var compress = function(self, dataToBeCompressed, callback) {
26
+ switch (self.options.agreedCompressor) {
27
+ case 'snappy':
28
+ Snappy.compress(dataToBeCompressed, callback);
29
+ break;
30
+ case 'zlib':
31
+ // Determine zlibCompressionLevel
32
+ var zlibOptions = {};
33
+ if (self.options.zlibCompressionLevel) {
34
+ zlibOptions.level = self.options.zlibCompressionLevel;
35
+ }
36
+ zlib.deflate(dataToBeCompressed, zlibOptions, callback);
37
+ break;
38
+ default:
39
+ throw new Error(
40
+ 'Attempt to compress message using unknown compressor "' +
41
+ self.options.agreedCompressor +
42
+ '".'
43
+ );
44
+ }
45
+ };
46
+
47
+ // Decompress a message using the given compressor
48
+ var decompress = function(compressorID, compressedData, callback) {
49
+ if (compressorID < 0 || compressorID > compressorIDs.length) {
50
+ throw new Error(
51
+ 'Server sent message compressed using an unsupported compressor. (Received compressor ID ' +
52
+ compressorID +
53
+ ')'
54
+ );
55
+ }
56
+ switch (compressorID) {
57
+ case compressorIDs.snappy:
58
+ Snappy.uncompress(compressedData, callback);
59
+ break;
60
+ case compressorIDs.zlib:
61
+ zlib.inflate(compressedData, callback);
62
+ break;
63
+ default:
64
+ callback(null, compressedData);
65
+ }
66
+ };
67
+
68
+ module.exports = {
69
+ compressorIDs: compressorIDs,
70
+ uncompressibleCommands: uncompressibleCommands,
71
+ compress: compress,
72
+ decompress: decompress
73
+ };
@@ -0,0 +1,13 @@
1
+ 'use strict';
2
+
3
+ const MIN_SUPPORTED_SERVER_VERSION = '2.6';
4
+ const MAX_SUPPORTED_SERVER_VERSION = '4.2';
5
+ const MIN_SUPPORTED_WIRE_VERSION = 2;
6
+ const MAX_SUPPORTED_WIRE_VERSION = 8;
7
+
8
+ module.exports = {
9
+ MIN_SUPPORTED_SERVER_VERSION,
10
+ MAX_SUPPORTED_SERVER_VERSION,
11
+ MIN_SUPPORTED_WIRE_VERSION,
12
+ MAX_SUPPORTED_WIRE_VERSION
13
+ };
@@ -0,0 +1,86 @@
1
+ 'use strict';
2
+
3
+ const GetMore = require('../connection/commands').GetMore;
4
+ const retrieveBSON = require('../connection/utils').retrieveBSON;
5
+ const MongoError = require('../error').MongoError;
6
+ const MongoNetworkError = require('../error').MongoNetworkError;
7
+ const BSON = retrieveBSON();
8
+ const Long = BSON.Long;
9
+ const collectionNamespace = require('./shared').collectionNamespace;
10
+ const maxWireVersion = require('../utils').maxWireVersion;
11
+ const applyCommonQueryOptions = require('./shared').applyCommonQueryOptions;
12
+ const command = require('./command');
13
+
14
+ function getMore(server, ns, cursorState, batchSize, options, callback) {
15
+ options = options || {};
16
+
17
+ const wireVersion = maxWireVersion(server);
18
+ function queryCallback(err, result) {
19
+ if (err) return callback(err);
20
+ const response = result.message;
21
+
22
+ // If we have a timed out query or a cursor that was killed
23
+ if (response.cursorNotFound) {
24
+ return callback(new MongoNetworkError('cursor killed or timed out'), null);
25
+ }
26
+
27
+ if (wireVersion < 4) {
28
+ const cursorId =
29
+ typeof response.cursorId === 'number'
30
+ ? Long.fromNumber(response.cursorId)
31
+ : response.cursorId;
32
+
33
+ cursorState.documents = response.documents;
34
+ cursorState.cursorId = cursorId;
35
+
36
+ callback(null, null, response.connection);
37
+ return;
38
+ }
39
+
40
+ // We have an error detected
41
+ if (response.documents[0].ok === 0) {
42
+ return callback(new MongoError(response.documents[0]));
43
+ }
44
+
45
+ // Ensure we have a Long valid cursor id
46
+ const cursorId =
47
+ typeof response.documents[0].cursor.id === 'number'
48
+ ? Long.fromNumber(response.documents[0].cursor.id)
49
+ : response.documents[0].cursor.id;
50
+
51
+ cursorState.documents = response.documents[0].cursor.nextBatch;
52
+ cursorState.cursorId = cursorId;
53
+
54
+ callback(null, response.documents[0], response.connection);
55
+ }
56
+
57
+ if (wireVersion < 4) {
58
+ const bson = server.s.bson;
59
+ const getMoreOp = new GetMore(bson, ns, cursorState.cursorId, { numberToReturn: batchSize });
60
+ const queryOptions = applyCommonQueryOptions({}, cursorState);
61
+ server.s.pool.write(getMoreOp, queryOptions, queryCallback);
62
+ return;
63
+ }
64
+
65
+ const getMoreCmd = {
66
+ getMore: cursorState.cursorId,
67
+ collection: collectionNamespace(ns),
68
+ batchSize: Math.abs(batchSize)
69
+ };
70
+
71
+ if (cursorState.cmd.tailable && typeof cursorState.cmd.maxAwaitTimeMS === 'number') {
72
+ getMoreCmd.maxTimeMS = cursorState.cmd.maxAwaitTimeMS;
73
+ }
74
+
75
+ const commandOptions = Object.assign(
76
+ {
77
+ returnFieldSelector: null,
78
+ documentsReturnedIn: 'nextBatch'
79
+ },
80
+ options
81
+ );
82
+
83
+ command(server, ns, getMoreCmd, commandOptions, queryCallback);
84
+ }
85
+
86
+ module.exports = getMore;
@@ -0,0 +1,18 @@
1
+ 'use strict';
2
+ const writeCommand = require('./write_command');
3
+
4
+ module.exports = {
5
+ insert: function insert(server, ns, ops, options, callback) {
6
+ writeCommand(server, 'insert', 'documents', ns, ops, options, callback);
7
+ },
8
+ update: function update(server, ns, ops, options, callback) {
9
+ writeCommand(server, 'update', 'updates', ns, ops, options, callback);
10
+ },
11
+ remove: function remove(server, ns, ops, options, callback) {
12
+ writeCommand(server, 'delete', 'deletes', ns, ops, options, callback);
13
+ },
14
+ killCursors: require('./kill_cursors'),
15
+ getMore: require('./get_more'),
16
+ query: require('./query'),
17
+ command: require('./command')
18
+ };
@@ -0,0 +1,70 @@
1
+ 'use strict';
2
+
3
+ const KillCursor = require('../connection/commands').KillCursor;
4
+ const MongoError = require('../error').MongoError;
5
+ const MongoNetworkError = require('../error').MongoNetworkError;
6
+ const collectionNamespace = require('./shared').collectionNamespace;
7
+ const maxWireVersion = require('../utils').maxWireVersion;
8
+ const command = require('./command');
9
+
10
+ function killCursors(server, ns, cursorState, callback) {
11
+ callback = typeof callback === 'function' ? callback : () => {};
12
+ const cursorId = cursorState.cursorId;
13
+
14
+ if (maxWireVersion(server) < 4) {
15
+ const bson = server.s.bson;
16
+ const pool = server.s.pool;
17
+ const killCursor = new KillCursor(bson, ns, [cursorId]);
18
+ const options = {
19
+ immediateRelease: true,
20
+ noResponse: true
21
+ };
22
+
23
+ if (typeof cursorState.session === 'object') {
24
+ options.session = cursorState.session;
25
+ }
26
+
27
+ if (pool && pool.isConnected()) {
28
+ try {
29
+ pool.write(killCursor, options, callback);
30
+ } catch (err) {
31
+ if (typeof callback === 'function') {
32
+ callback(err, null);
33
+ } else {
34
+ console.warn(err);
35
+ }
36
+ }
37
+ }
38
+
39
+ return;
40
+ }
41
+
42
+ const killCursorCmd = {
43
+ killCursors: collectionNamespace(ns),
44
+ cursors: [cursorId]
45
+ };
46
+
47
+ const options = {};
48
+ if (typeof cursorState.session === 'object') options.session = cursorState.session;
49
+
50
+ command(server, ns, killCursorCmd, options, (err, result) => {
51
+ if (err) {
52
+ return callback(err);
53
+ }
54
+
55
+ const response = result.message;
56
+ if (response.cursorNotFound) {
57
+ return callback(new MongoNetworkError('cursor killed or timed out'), null);
58
+ }
59
+
60
+ if (!Array.isArray(response.documents) || response.documents.length === 0) {
61
+ return callback(
62
+ new MongoError(`invalid killCursors result returned for cursor id ${cursorId}`)
63
+ );
64
+ }
65
+
66
+ callback(null, response.documents[0]);
67
+ });
68
+ }
69
+
70
+ module.exports = killCursors;