Skip to content

Commit 8bb92f9

Browse files
dariakpnbbeeken
andauthored
fix(NODE-3194): Ignore undefined and null options in MongoClient constructor (#2800)
Co-authored-by: Neal Beeken <[email protected]>
1 parent 29512da commit 8bb92f9

File tree

2 files changed

+43
-6
lines changed

2 files changed

+43
-6
lines changed

src/connection_string.ts

+6-2
Original file line numberDiff line numberDiff line change
@@ -340,7 +340,9 @@ export function parseOptions(
340340
}
341341
}
342342

343-
const objectOptions = new CaseInsensitiveMap(Object.entries(options));
343+
const objectOptions = new CaseInsensitiveMap(
344+
Object.entries(options).filter(([, v]) => (v ?? null) !== null)
345+
);
344346

345347
const allOptions = new CaseInsensitiveMap();
346348

@@ -369,8 +371,10 @@ export function parseOptions(
369371
Array.from(Object.keys(OPTIONS)).map(s => s.toLowerCase())
370372
);
371373
if (unsupportedOptions.size !== 0) {
374+
const optionWord = unsupportedOptions.size > 1 ? 'options' : 'option';
375+
const isOrAre = unsupportedOptions.size > 1 ? 'are' : 'is';
372376
throw new MongoParseError(
373-
`options ${Array.from(unsupportedOptions).join(', ')} are not supported`
377+
`${optionWord} ${Array.from(unsupportedOptions).join(', ')} ${isOrAre} not supported`
374378
);
375379
}
376380

test/unit/mongo_client_options.test.js

+37-4
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ const { WriteConcern } = require('../../src/write_concern');
88
const { ReadPreference } = require('../../src/read_preference');
99
const { Logger } = require('../../src/logger');
1010
const { MongoCredentials } = require('../../src/cmap/auth/mongo_credentials');
11-
const { MongoClient } = require('../../src');
11+
const { MongoClient, MongoParseError } = require('../../src');
1212

1313
describe('MongoOptions', function () {
1414
it('MongoClient should always freeze public options', function () {
@@ -138,9 +138,8 @@ describe('MongoOptions', function () {
138138
zlibCompressionLevel: 2
139139
};
140140

141-
it('All options', function () {
141+
it('should parse all options from the options object', function () {
142142
const options = parseOptions('mongodb://localhost:27017/', ALL_OPTIONS);
143-
144143
// Check consolidated options
145144
expect(options).has.property('writeConcern');
146145
expect(options.writeConcern).has.property('w', 2);
@@ -183,7 +182,7 @@ describe('MongoOptions', function () {
183182
'zlibCompressionLevel=2'
184183
].join('&');
185184

186-
it('All URI options', function () {
185+
it('should parse all options from the URI string', function () {
187186
const options = parseOptions(allURIOptions);
188187
expect(options).has.property('zlibCompressionLevel', 2);
189188

@@ -192,6 +191,40 @@ describe('MongoOptions', function () {
192191
expect(options.writeConcern).has.property('wtimeout', 2);
193192
});
194193

194+
it('should ignore undefined and null values in the options object', function () {
195+
const options = parseOptions('mongodb://localhost:27017/', {
196+
maxPoolSize: null,
197+
servername: undefined,
198+
randomopt: null,
199+
otherrandomopt: undefined
200+
});
201+
202+
// test valid option key with default value
203+
expect(options).to.have.property('maxPoolSize', 100);
204+
205+
// test valid option key without default value
206+
expect(options).not.to.have.property('servername');
207+
208+
// test invalid option keys that are null/undefined
209+
expect(options).not.to.have.property('randomopt');
210+
expect(options).not.to.have.property('otherrandomopt');
211+
});
212+
213+
it('should throw an error on unrecognized keys in the options object if they are defined', function () {
214+
expect(() =>
215+
parseOptions('mongodb://localhost:27017/', {
216+
randomopt: 'test'
217+
})
218+
).to.throw(MongoParseError, 'option randomopt is not supported');
219+
220+
expect(() =>
221+
parseOptions('mongodb://localhost:27017/', {
222+
randomopt: 'test',
223+
randomopt2: 'test'
224+
})
225+
).to.throw(MongoParseError, 'options randomopt, randomopt2 are not supported');
226+
});
227+
195228
it('srvHost saved to options for later resolution', function () {
196229
const options = parseOptions('mongodb+srv://server.example.com/');
197230
expect(options).has.property('srvHost', 'server.example.com');

0 commit comments

Comments
 (0)