Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -1052,7 +1052,7 @@ describe('Store', () => {

it('sets the driverUrl', (done) => {
const driverUrl =
'mongodb://server.example.com:27017/?readPreference=primary&ssl=false';
'mongodb://server.example.com:27017/?readPreference=primary&directConnection=true&ssl=false';
const unsubscribe = Store.listen((state) => {
try {
unsubscribe();
Expand Down
19 changes: 18 additions & 1 deletion packages/connection-model/lib/connect.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,22 @@ async function waitForTunnelError(tunnel) {
throw error;
}

function addDirectConnectionWhenNeeded(options, model) {
if (
model.directConnection === undefined &&
model.hosts.length === 1 &&
!model.isSrvRecord &&
(model.replicaSet === undefined || model.replicaSet === '')
) {
return {
...options,
directConnection: true
};
}

return options;
}

async function connect(model, setupListeners) {
if (model.serialize === undefined) {
// note this is only here for testing reasons and would not be
Expand All @@ -68,7 +84,7 @@ async function connect(model, setupListeners) {

const url = removeGssapiServiceName(model.driverUrlWithSsh);
const options = {
...model.driverOptions
...addDirectConnectionWhenNeeded(model.driverOptions, model)
};

// if `auth` is passed then username and password must be present,
Expand Down Expand Up @@ -124,3 +140,4 @@ module.exports = (model, setupListeners, done) => connect(model, setupListeners)
(res) => process.nextTick(() => done(null, ...res)),
(err) => process.nextTick(() => done(err))
);

4 changes: 1 addition & 3 deletions packages/connection-model/lib/model.js
Original file line number Diff line number Diff line change
Expand Up @@ -169,9 +169,7 @@ const CONNECTION_STRING_OPTIONS = {
],
default: undefined
},
// Driver brought this behaviour back in v3.6.3+ (but will remove in v4), we don't need to handle directConnection ourselves
// See https://github.com/mongodb/node-mongodb-native/pull/2719
// directConnection: { type: 'boolean', default: undefined }
directConnection: { type: 'boolean', default: undefined }
};

assign(props, CONNECTION_STRING_OPTIONS);
Expand Down
63 changes: 40 additions & 23 deletions packages/connection-model/test/connect.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,22 +27,31 @@ describe('connection model connector', () => {
model,
setupListeners,
(connectErr, client, _tunnel, { url, options }) => {
if (connectErr) throw connectErr;

assert.strictEqual(
url,
'mongodb://localhost:27018/?readPreference=primary&ssl=false'
);

assert.deepStrictEqual(options, {
// Driver brought this behaviour back in v3.6.3+ (but will remove in v4), we don't need to handle directConnection ourselves
// See https://github.com/mongodb/node-mongodb-native/pull/2719
// directConnection: true,
readPreference: 'primary'
});

client.close(true);
done();
if (connectErr) {
return done(connectErr);
}

try {
assert.strictEqual(
url,
'mongodb://localhost:27018/?readPreference=primary&directConnection=true&ssl=false'
);

assert.deepStrictEqual(options, {
// this is never truly added at the moment since Connection.from
// already adds this to the model and query string when necessary:
// directConnection: true,
readPreference: 'primary'
});

done();
} catch (e) {
done(e);
} finally {
if (client) {
client.close(true);
}
}
}
);
});
Expand All @@ -51,20 +60,28 @@ describe('connection model connector', () => {
it('should connect to `localhost:27018 with model`', (done) => {
Connection.from('mongodb://localhost:27018', (parseErr, model) => {
assert.equal(parseErr, null);
connect(model, setupListeners, (connectErr, client) => {
assert.equal(connectErr, null);
client.close(true);
done();
});
connect(model, setupListeners,
(connectErr, client) => {
if (connectErr) {
return done(connectErr);
}

client.close(true);
done();
}
);
});
});

it('should connect to `localhost:27018 with object`', (done) => {
connect(
{ port: 27018, host: 'localhost' },
setupListeners,
(err, client) => {
assert.equal(err, null);
(connectErr, client) => {
if (connectErr) {
return done(connectErr);
}

client.close(true);
done();
}
Expand Down
32 changes: 18 additions & 14 deletions packages/connection-model/test/parse-and-build-uri.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,20 +31,20 @@ const tests = [
description: 'with socketTimeoutMS',
connectionString:
'mongodb://localhost:27017/sampleDb' +
'?socketTimeoutMS=30000&w=majority&readPreference=primary&ssl=false'
'?socketTimeoutMS=30000&w=majority&readPreference=primary&directConnection=true&ssl=false'
// only: true // Uncomment this line to run only one test debugging purpose
},
{
description: 'with compression',
connectionString:
'mongodb://localhost:27017/?compressors=snappy%2Czlib&' +
'readPreference=primary&ssl=false'
'readPreference=primary&directConnection=true&ssl=false'
},
{
description: 'with zlibCompressionLevel',
connectionString:
'mongodb://localhost:27017/?zlibCompressionLevel=9&' +
'readPreference=primary&ssl=false'
'readPreference=primary&directConnection=true&ssl=false'
},
{
description:
Expand All @@ -59,7 +59,7 @@ const tests = [
connectionString:
'mongodb://localhost:27017/test?' +
'maxPoolSize=50&minPoolSize=5&maxIdleTimeMS=1000&waitQueueMultiple=200&waitQueueTimeoutMS=100&' +
'w=1&wTimeoutMS=2000&journal=true&readPreference=primary&ssl=false'
'w=1&wTimeoutMS=2000&journal=true&readPreference=primary&directConnection=true&ssl=false'
},
{
description: 'with readConcernLevel',
Expand All @@ -84,13 +84,13 @@ const tests = [
description: 'with authSource and authMechanism (SCRAM-SHA-1)',
connectionString:
'mongodb://%40rlo:w%40of@localhost:27017/dogdb?authSource=catdb&' +
'readPreference=primary&authMechanism=SCRAM-SHA-1&ssl=false'
'readPreference=primary&authMechanism=SCRAM-SHA-1&directConnection=true&ssl=false'
},
{
description: 'with authSource and authMechanism (SCRAM-SHA-256)',
connectionString:
'mongodb://%40rlo:w%40of@localhost:27017/dogdb?authSource=catdb&' +
'authMechanism=SCRAM-SHA-256&readPreference=primary&ssl=false'
'authMechanism=SCRAM-SHA-256&readPreference=primary&directConnection=true&ssl=false'
},
{
description: 'with password which is ignored for GSSAPI',
Expand All @@ -101,15 +101,15 @@ const tests = [
expectedConnectionString:
'mongodb://%40rlo@localhost:27017/?' +
'authMechanism=GSSAPI&readPreference=primary&' +
'authSource=%24external&ssl=false&authSource=$external'
'authSource=%24external&directConnection=true&ssl=false&authSource=$external'
},
{
description: 'with authMechanismProperties and gssapiServiceName',
connectionString:
'mongodb://%40rlo@localhost:27017/?' +
'authMechanism=GSSAPI&readPreference=primary&' +
'authSource=%24external&authMechanismProperties=CANONICALIZE_HOST_NAME%3Atrue&' +
'gssapiCanonicalizeHostName=true&ssl=false&authSource=$external'
'gssapiCanonicalizeHostName=true&directConnection=true&ssl=false&authSource=$external'
},
{
description:
Expand All @@ -123,22 +123,22 @@ const tests = [
description: 'with serverSelectionTryOnce',
connectionString:
'mongodb://a:27017/?readPreference=primary&' +
'serverSelectionTryOnce=false&ssl=false'
'serverSelectionTryOnce=false&directConnection=true&ssl=false'
},
{
description: 'with appName',
connectionString:
'mongodb://localhost:27017/?readPreference=primary&appname=foo&ssl=false'
'mongodb://localhost:27017/?readPreference=primary&appname=foo&directConnection=true&ssl=false'
},
{
description: 'with retryWrites',
connectionString:
'mongodb://hostname:27017/?readPreference=primary&retryWrites=true&ssl=false'
'mongodb://hostname:27017/?readPreference=primary&retryWrites=true&directConnection=true&ssl=false'
},
{
description: 'with uuidRepresentation',
connectionString:
'mongodb://foo:27017/?readPreference=primary&uuidRepresentation=csharpLegacy&ssl=false'
'mongodb://foo:27017/?readPreference=primary&uuidRepresentation=csharpLegacy&directConnection=true&ssl=false'
}
];

Expand All @@ -151,8 +151,12 @@ describe('connection model', () => {

const c = new Connection(result.toJSON());

expect(c.driverUrl).to.be.equal(test.expectedConnectionString || test.connectionString);
done();
try {
expect(c.driverUrl).to.be.equal(test.expectedConnectionString || test.connectionString);
done();
} catch (e) {
done(e);
}
});
const runMode = test.only ? it.only : it;
runMode(test.description, runTest);
Expand Down
33 changes: 25 additions & 8 deletions packages/connection-model/test/parse-uri-components.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -549,16 +549,33 @@ describe('connection model partser should parse URI components such as', () => {
);
});

// Driver brought this behaviour back in v3.6.3+ (but will remove in v4), we don't need to handle directConnection ourselves
// See https://github.com/mongodb/node-mongodb-native/pull/2719
describe.skip('directConnection', () => {
it('defaults directConnection undefined', (done) => {
describe('directConnection', () => {
it('defaults directConnection undefined for srv records', (done) => {
Connection.from(
'mongodb://localhost:27017',
'mongodb+srv://user:password@compass-data-sets.e06dc.mongodb.net',
(error, result) => {
expect(error).to.not.exist;
expect(result.directConnection).to.be.equal(undefined);
done();
try {
expect(error).to.not.exist;
expect(result.directConnection).to.be.equal(undefined);
done();
} catch (e) {
done(e);
}
}
);
});

it('defaults directConnection undefined for multiple hosts', (done) => {
Connection.from(
'mongodb://host1,host2,host3',
(error, result) => {
try {
expect(error).to.not.exist;
expect(result.directConnection).to.be.equal(undefined);
done();
} catch (e) {
done(e);
}
}
);
});
Expand Down