Skip to content

Commit 8b2b7fd

Browse files
durranW-A-Jamesbaileympearson
authored
fix(NODE-6340): OIDC reauth uses caches speculative auth result (#4379)
Co-authored-by: Warren James <warren.james@mongodb.com> Co-authored-by: Bailey Pearson <bailey.pearson@mongodb.com>
1 parent 907aac1 commit 8b2b7fd

File tree

2 files changed

+94
-1
lines changed

2 files changed

+94
-1
lines changed

Diff for: src/cmap/auth/mongodb_oidc.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,7 @@ export class MongoDBOIDC extends AuthProvider {
143143
*/
144144
override async auth(authContext: AuthContext): Promise<void> {
145145
const { connection, reauthenticating, response } = authContext;
146-
if (response?.speculativeAuthenticate?.done) {
146+
if (response?.speculativeAuthenticate?.done && !reauthenticating) {
147147
return;
148148
}
149149
const credentials = getCredentials(authContext);

Diff for: test/integration/auth/mongodb_oidc.prose.test.ts

+93
Original file line numberDiff line numberDiff line change
@@ -546,6 +546,99 @@ describe('OIDC Auth Spec Tests', function () {
546546
expect(callbackSpy).to.have.been.calledTwice;
547547
});
548548
});
549+
550+
describe('4.4 Speculative Authentication should be ignored on Reauthentication', function () {
551+
let utilClient: MongoClient;
552+
const callbackSpy = sinon.spy(createCallback());
553+
const saslStarts = [];
554+
// - Create an OIDC configured client.
555+
// - Populate the *Client Cache* with a valid access token to enforce Speculative Authentication.
556+
// - Perform an `insert` operation that succeeds.
557+
// - Assert that the callback was not called.
558+
// - Assert there were no `SaslStart` commands executed.
559+
// - Set a fail point for `insert` commands of the form:
560+
// ```javascript
561+
// {
562+
// configureFailPoint: "failCommand",
563+
// mode: {
564+
// times: 1
565+
// },
566+
// data: {
567+
// failCommands: [
568+
// "insert"
569+
// ],
570+
// errorCode: 391 // ReauthenticationRequired
571+
// }
572+
// }
573+
// ```
574+
// - Perform an `insert` operation that succeeds.
575+
// - Assert that the callback was called once.
576+
// - Assert there were `SaslStart` commands executed.
577+
// - Close the client.
578+
beforeEach(async function () {
579+
utilClient = new MongoClient(uriSingle, {
580+
authMechanismProperties: {
581+
OIDC_CALLBACK: createCallback()
582+
},
583+
retryReads: false
584+
});
585+
586+
client = new MongoClient(uriSingle, {
587+
authMechanismProperties: {
588+
OIDC_CALLBACK: callbackSpy
589+
},
590+
retryReads: false,
591+
monitorCommands: true
592+
});
593+
client.on('commandStarted', event => {
594+
if (event.commandName === 'saslStart') {
595+
saslStarts.push(event);
596+
}
597+
});
598+
599+
const provider = client.s.authProviders.getOrCreateProvider('MONGODB-OIDC', {
600+
OIDC_CALLBACK: callbackSpy
601+
}) as MongoDBOIDC;
602+
const token = await readFile(path.join(process.env.OIDC_TOKEN_DIR, 'test_user1'), {
603+
encoding: 'utf8'
604+
});
605+
606+
provider.workflow.cache.put({ accessToken: token });
607+
collection = client.db('test').collection('test');
608+
});
609+
610+
afterEach(async function () {
611+
await utilClient.db().admin().command({
612+
configureFailPoint: 'failCommand',
613+
mode: 'off'
614+
});
615+
await utilClient.close();
616+
});
617+
618+
it('successfully authenticates', async function () {
619+
await collection.insertOne({ name: 'test' });
620+
expect(callbackSpy).to.not.have.been.called;
621+
expect(saslStarts).to.be.empty;
622+
623+
await utilClient
624+
.db()
625+
.admin()
626+
.command({
627+
configureFailPoint: 'failCommand',
628+
mode: {
629+
times: 1
630+
},
631+
data: {
632+
failCommands: ['insert'],
633+
errorCode: 391
634+
}
635+
});
636+
637+
await collection.insertOne({ name: 'test' });
638+
expect(callbackSpy).to.have.been.calledOnce;
639+
expect(saslStarts.length).to.equal(1);
640+
});
641+
});
549642
});
550643
});
551644

0 commit comments

Comments
 (0)