Skip to content

Commit d6b7c1f

Browse files
committed
sign out - wip
1 parent ca01d0f commit d6b7c1f

2 files changed

Lines changed: 36 additions & 36 deletions

File tree

packages/atlas-service/src/main.ts

Lines changed: 35 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -64,8 +64,6 @@ export class CompassAuthService {
6464

6565
private static signInPromise: Promise<AtlasUserInfo> | null = null;
6666

67-
private static userInfo: AtlasUserInfo | null = null;
68-
6967
private static fetch = async (
7068
url: string,
7169
init: RequestInit = {}
@@ -151,7 +149,7 @@ export class CompassAuthService {
151149
allowedFlows: this.getAllowedAuthFlows.bind(this),
152150
logger: this.oidcPluginLogger,
153151
serializedState,
154-
customFetch: this.httpClient
152+
customFetch: this
155153
.fetch as unknown as MongoDBOIDCPluginOptions['customFetch'],
156154
});
157155
oidcPluginHookLoggerToMongoLogWriter(
@@ -261,18 +259,20 @@ export class CompassAuthService {
261259

262260
try {
263261
const tokens = await this.requestOAuthToken({ signal });
264-
this.userInfo = this.getUserInfoFromAccessToken(tokens.accessToken);
262+
this.currentUser = this.getUserInfoFromAccessToken(
263+
tokens.accessToken
264+
);
265265
log.info(
266266
mongoLogId(1_001_000_219),
267267
'AtlasService',
268268
'Signed in successfully'
269269
);
270-
const { auid } = getTrackingUserInfo(this.userInfo);
270+
const { auid } = getTrackingUserInfo(this.currentUser);
271271
track('Atlas Sign In Success', { auid });
272272
await this.preferences.savePreferences({
273273
telemetryAtlasUserId: auid,
274274
});
275-
return this.userInfo;
275+
return this.currentUser;
276276
} catch (err) {
277277
track('Atlas Sign In Error', {
278278
error: (err as Error).message,
@@ -296,17 +296,10 @@ export class CompassAuthService {
296296
if (!this.currentUser) {
297297
throw new Error("Can't sign out if not signed in yet");
298298
}
299-
// Reset and recreate event emitter first so that we don't accidentally
300-
// react on any old plugin instance events
301-
this.oidcPluginLogger.removeAllListeners();
302-
this.oidcPluginLogger = new OidcPluginLogger();
303-
this.attachOidcPluginLoggerEvents();
304-
// Destroy old plugin and setup new one
305-
await this.plugin?.destroy();
306-
this.setupPlugin();
307-
// Revoke tokens. Revoking refresh token will also revoke associated access
308-
// tokens
309-
// https://developer.okta.com/docs/guides/revoke-tokens/main/#revoke-an-access-token-or-a-refresh-token
299+
// Revoke tokens BEFORE destroying the plugin — otherwise maybeGetToken
300+
// reads from a fresh, empty plugin and posts an empty token, which the
301+
// revocation endpoint rejects with 400. Revoking the refresh token also
302+
// invalidates the associated access token (RFC 7009 §2.1).
310303
try {
311304
await this.revoke({ tokenType: 'refreshToken' });
312305
} catch (err) {
@@ -317,15 +310,20 @@ export class CompassAuthService {
317310
// this is not a failed state for the app, we already cleaned up token
318311
// from everywhere, so we just ignore this
319312
}
313+
// Reset and recreate event emitter so that we don't accidentally react on
314+
// any old plugin instance events
315+
this.oidcPluginLogger.removeAllListeners();
316+
this.oidcPluginLogger = new OidcPluginLogger();
317+
this.attachOidcPluginLoggerEvents();
318+
// Destroy old plugin and setup new one
319+
await this.plugin?.destroy();
320+
this.setupPlugin();
320321
// Keep a copy of current user info for tracking
321322
const userInfo = this.currentUser;
322323
// Reset service state
323324
this.currentUser = null;
324325
this.oidcPluginLogger.emit('atlas-service-signed-out');
325-
// Open Atlas sign out page to end the browser session created for sign in
326-
const signOutUrl = new URL(this.config.authPortalUrl);
327-
signOutUrl.searchParams.set('signedOut', 'true');
328-
void this.openExternal(signOutUrl.toString());
326+
329327
track('Atlas Sign Out', getTrackingUserInfo(userInfo));
330328
}
331329

@@ -386,7 +384,7 @@ export class CompassAuthService {
386384

387385
const token = await this.maybeGetToken({ signal, tokenType });
388386

389-
const res = await this.fetch(url.toString(), {
387+
const res = await this.httpClient.fetch(url.toString(), {
390388
method: 'POST',
391389
body: new URLSearchParams([
392390
['token', token ?? ''],
@@ -414,18 +412,20 @@ export class CompassAuthService {
414412
throwIfAborted(signal);
415413
this.throwIfNetworkTrafficDisabled();
416414

417-
const url = new URL(`${this.config.atlasLogin.issuer}/v1/revoke`);
418-
url.searchParams.set('client_id', this.config.atlasLogin.clientId);
415+
// TODO: check if we should use the discovery endpoint instead of hardcoding this
416+
const url = new URL(`${this.config.atlasLogin.issuer}/tokens/revoke`);
419417

420418
tokenType ??= 'accessToken';
421419

420+
console.log('[sign out] revoking token', tokenType);
422421
const token = await this.maybeGetToken({ signal, tokenType });
423422

424-
const res = await this.fetch(url.toString(), {
423+
const res = await this.httpClient.fetch(url.toString(), {
425424
method: 'POST',
426425
body: new URLSearchParams([
427426
['token', token ?? ''],
428427
['token_type_hint', TOKEN_TYPE_TO_HINT[tokenType]],
428+
['client_id', this.config.atlasLogin.clientId],
429429
]),
430430
headers: {
431431
Accept: 'application/json',
@@ -434,6 +434,16 @@ export class CompassAuthService {
434434
signal: signal,
435435
});
436436

437+
if (!res.ok) {
438+
const body = await res.text().catch(() => '<unreadable>');
439+
console.log(
440+
'[sign out] revocation failed',
441+
res.status,
442+
res.statusText,
443+
body
444+
);
445+
}
446+
437447
await throwIfNotOk(res);
438448
}
439449

packages/atlas-service/src/util.ts

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -112,10 +112,6 @@ export type AtlasServiceConfig = {
112112
clientId: string;
113113
issuer: string;
114114
};
115-
/**
116-
* Atlas Account Portal UI base url
117-
*/
118-
authPortalUrl: string;
119115
/**
120116
* Assistant API base url
121117
*/
@@ -144,7 +140,6 @@ const config = Object.create({
144140
clientId: '124d5a79-2063-4f76-8655-8133e98e25c9',
145141
issuer: 'https://authorize-dev.mongodb.com',
146142
},
147-
authPortalUrl: 'https://account-local.mongodb.com/account/login',
148143
assistantApiBaseUrl: 'https://knowledge-dev.mongodb.com/api/v1',
149144
userDataBaseUrl: 'https://cloud-local.mmscloudteam.com/ui/userData',
150145
},
@@ -160,7 +155,6 @@ const config = Object.create({
160155
clientId: '124d5a79-2063-4f76-8655-8133e98e25c9',
161156
issuer: 'https://authorize-dev.mongodb.com',
162157
},
163-
authPortalUrl: 'https://account-dev.mongodb.com/account/login',
164158
assistantApiBaseUrl: 'https://knowledge-dev.mongodb.com/api/v1',
165159
userDataBaseUrl: 'https://cloud-dev.mongodb.com/ui/userData',
166160
},
@@ -176,7 +170,6 @@ const config = Object.create({
176170
clientId: '124d5a79-2063-4f76-8655-8133e98e25c9',
177171
issuer: 'https://authorize-qa.mongodb.com',
178172
},
179-
authPortalUrl: 'https://account-qa.mongodb.com/account/login',
180173
assistantApiBaseUrl: 'https://knowledge-dev.mongodb.com/api/v1',
181174
userDataBaseUrl: 'https://cloud-qa.mongodb.com/ui/userData',
182175
},
@@ -192,7 +185,6 @@ const config = Object.create({
192185
clientId: '124d5a79-2063-4f76-8655-8133e98e25c9',
193186
issuer: 'https://authorize-stage.mongodb.com',
194187
},
195-
authPortalUrl: 'https://account-stage.mongodb.com/account/login',
196188
assistantApiBaseUrl: 'https://knowledge-staging.mongodb.com/api/v1',
197189
userDataBaseUrl: 'https://cloud-stage.mongodb.com/ui/userData',
198190
},
@@ -208,7 +200,6 @@ const config = Object.create({
208200
clientId: '124d5a79-2063-4f76-8655-8133e98e25c9',
209201
issuer: 'https://authorize.mongodb.com',
210202
},
211-
authPortalUrl: 'https://account.mongodb.com/account/login',
212203
assistantApiBaseUrl: 'https://knowledge.mongodb.com/api/v1',
213204
userDataBaseUrl: 'https://cloud.mongodb.com/ui/userData',
214205
},
@@ -225,14 +216,13 @@ export function getAtlasConfig(
225216
clientId: process.env.COMPASS_CLIENT_ID_OVERRIDE,
226217
issuer: process.env.COMPASS_OIDC_ISSUER_OVERRIDE,
227218
},
228-
authPortalUrl: process.env.COMPASS_ATLAS_AUTH_PORTAL_URL_OVERRIDE,
229219
assistantApiBaseUrl: process.env.COMPASS_ASSISTANT_BASE_URL_OVERRIDE,
230220
userDataBaseUrl: process.env.COMPASS_USER_DATA_BASE_URL_OVERRIDE,
231221
};
232222
return defaultsDeep(
233223
envConfig,
234224
config[
235-
process.env.COMPASS_ATLAS_SERVICE_BACKEND_PRESET ??
225+
process.env.COMPASS_ATLAS_SERVICE_BACKEND_PRESET_OVERRIDE ??
236226
atlasServiceBackendPreset
237227
]
238228
) as AtlasServiceConfig;

0 commit comments

Comments
 (0)