Skip to content

Commit

Permalink
Fix: uri parser authSource and dbName bug (#265)
Browse files Browse the repository at this point in the history
* fix: sri parser authSource and dbName bug

* change default db
  • Loading branch information
erfanium authored Oct 8, 2021
1 parent 4aa168d commit 79ac709
Show file tree
Hide file tree
Showing 2 changed files with 72 additions and 29 deletions.
32 changes: 21 additions & 11 deletions src/utils/uri.ts
Original file line number Diff line number Diff line change
Expand Up @@ -122,18 +122,22 @@ export type SrvConnectOptions = Omit<ConnectOptions, "servers"> & {

export function parseSrvUrl(url: string): SrvConnectOptions {
const data = parse_url(url);

const defaultAuthDb = (data.pathname && (data.pathname.length > 1))
? data.pathname!.substring(1)
: null;

const authSource = new URLSearchParams(data.search).get("authSource");

const connectOptions: SrvConnectOptions = {
db: new URLSearchParams(data.search).get("authSource") ??
((data.pathname && data.pathname.length > 1)
? data.pathname.substring(1)
: "admin"),
db: defaultAuthDb ?? "test",
};

if (data.auth) {
connectOptions.credential = <Credential> {
username: data.auth.user,
password: data.auth.password,
db: connectOptions.db,
db: authSource ?? defaultAuthDb ?? "admin",
mechanism: data.search.authMechanism || "SCRAM-SHA-256",
};
}
Expand Down Expand Up @@ -176,7 +180,17 @@ export function parse(url: string): Promise<ConnectOptions> {

function parseNormalUrl(url: string): ConnectOptions {
const data = parse_url(url);
const connectOptions: ConnectOptions = { servers: data.servers!, db: "" };

const defaultAuthDb = (data.pathname && (data.pathname.length > 1))
? data.pathname!.substring(1)
: null;

const authSource = new URLSearchParams(data.search).get("authSource");

const connectOptions: ConnectOptions = {
servers: data.servers!,
db: defaultAuthDb ?? "test",
};

for (const server of connectOptions.servers) {
if (server.host.includes(".sock")) {
Expand All @@ -185,15 +199,11 @@ function parseNormalUrl(url: string): ConnectOptions {
server.port = server.port || 27017;
}

connectOptions.db = new URLSearchParams(data.search).get("authSource") ??
(data.pathname && (data.pathname.length > 1)
? data.pathname.substring(1)
: "admin");
if (data.auth) {
connectOptions.credential = <Credential> {
username: data.auth.user,
password: data.auth.password,
db: connectOptions.db,
db: authSource ?? defaultAuthDb ?? "admin",
mechanism: data.search.authMechanism || "SCRAM-SHA-256",
};
}
Expand Down
69 changes: 51 additions & 18 deletions tests/cases/00_uri.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ export default function uriTests() {
name: "should correctly parse mongodb://localhost",
async fn() {
const options = await parse("mongodb://localhost/");
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
assertEquals(options.servers.length, 1);
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.servers[0].port, 27017);
Expand All @@ -17,7 +17,7 @@ export default function uriTests() {
name: "should correctly parse mongodb://localhost:27017",
async fn() {
const options = await parse("mongodb://localhost:27017/");
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
assertEquals(options.servers.length, 1);
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.servers[0].port, 27017);
Expand All @@ -42,7 +42,7 @@ export default function uriTests() {
const options = await parse(
"mongodb://localhost/?safe=true&readPreference=secondary",
);
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
assertEquals(options.servers.length, 1);
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.servers[0].port, 27017);
Expand All @@ -53,7 +53,7 @@ export default function uriTests() {
name: "should correctly parse mongodb://localhost:28101/",
async fn() {
const options = await parse("mongodb://localhost:28101/");
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
assertEquals(options.servers.length, 1);
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.servers[0].port, 28101);
Expand All @@ -68,6 +68,7 @@ export default function uriTests() {
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foobar");
assertEquals(options.credential!.db, "baz");
},
});

Expand All @@ -80,6 +81,7 @@ export default function uriTests() {
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foo bar");
assertEquals(options.credential!.db, "baz");
},
});

Expand All @@ -89,7 +91,7 @@ export default function uriTests() {
const options = await parse("mongodb://%2Ftmp%2Fmongodb-27017.sock");
assertEquals(options.servers.length, 1);
assertEquals(options.servers[0].domainSocket, "/tmp/mongodb-27017.sock");
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
},
});

Expand All @@ -104,7 +106,7 @@ export default function uriTests() {
assertEquals(options.servers[0].domainSocket, "/tmp/mongodb-27017.sock");
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foo");
assertEquals(options.db, "admin");
assertEquals(options.db, "test");
},
});

Expand All @@ -119,6 +121,7 @@ export default function uriTests() {
assertEquals(options.servers[0].domainSocket, "/tmp/mongodb-27017.sock");
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foo");
assertEquals(options.credential!.db, "somedb");
assertEquals(options.db, "somedb");
},
});
Expand All @@ -134,6 +137,7 @@ export default function uriTests() {
assertEquals(options.servers[0].domainSocket, "/tmp/mongodb-27017.sock");
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foo");
assertEquals(options.credential!.db, "somedb");
assertEquals(options.db, "somedb");
assertEquals(options.safe, true);
},
Expand All @@ -153,23 +157,52 @@ export default function uriTests() {
assertEquals(options.servers[1].port, 28101);
assertEquals(options.credential!.username, "fred");
assertEquals(options.credential!.password, "foobar");
assertEquals(options.credential!.db, "baz");
},
});
// TODO: add more tests (https://github.com/mongodb/node-mongodb-native/blob/3.6/test/functional/url_parser.test.js)

Deno.test({
name:
"should correctly parse mongodb+srv://someUser:somePassword@somesubdomain.somedomain.com/someDatabaseName?retryWrites=true&w=majority",
fn() {
const options = parseSrvUrl(
"mongodb+srv://someUser:somePassword@somesubdomain.somedomain.com/someDatabaseName?retryWrites=true&w=majority",
name: "should correctly parse uris with authSource and dbName",
async fn() {
const options = await parse(
"mongodb://a:b@localhost:27017/dbName?authSource=admin2",
);
assertEquals(options.db, "someDatabaseName");
assertEquals(options.credential?.username, "someUser");
assertEquals(options.credential?.password, "somePassword");
assertEquals(options.retryWrites, true);
// @ts-ignore
assertEquals(options["servers"], undefined);

assertEquals(options.db, "dbName");
assertEquals(options.servers[0].host, "localhost");
assertEquals(options.servers[0].port, 27017);
assertEquals(options.credential!.username, "a");
assertEquals(options.credential!.password, "b");
assertEquals(options.credential!.db, "admin2");
},
});
}),
Deno.test({
name: "should correctly parse uris with authSource and dbName",
fn() {
const options = parseSrvUrl(
"mongodb+srv://a:b@somesubdomain.somedomain.com/dbName?authSource=admin2",
);

assertEquals(options.db, "dbName");
assertEquals(options.credential!.username, "a");
assertEquals(options.credential!.password, "b");
assertEquals(options.credential!.db, "admin2");
},
}),
Deno.test({
name:
"should correctly parse mongodb+srv://someUser:somePassword@somesubdomain.somedomain.com/someDatabaseName?retryWrites=true&w=majority",
fn() {
const options = parseSrvUrl(
"mongodb+srv://someUser:somePassword@somesubdomain.somedomain.com/someDatabaseName?retryWrites=true&w=majority",
);
assertEquals(options.db, "someDatabaseName");
assertEquals(options.credential?.username, "someUser");
assertEquals(options.credential?.password, "somePassword");
assertEquals(options.retryWrites, true);
// @ts-ignore
assertEquals(options["servers"], undefined);
},
});
}

0 comments on commit 79ac709

Please sign in to comment.