mirror of
https://github.com/bitwarden/browser
synced 2025-12-14 07:13:32 +00:00
[PM-7838] [PM-7864] Ensure AuthStatus Changes Before Exiting (#9018)
* Ensure AuthStatus Changes Before Exiting * Do Not Display Account Without Name Or Email * Fix Environment Selectors * Add AccountService.clean to Web
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
import { combineLatest, firstValueFrom, switchMap } from "rxjs";
|
||||
import { combineLatest, filter, firstValueFrom, map, switchMap, timeout } from "rxjs";
|
||||
|
||||
import { SearchService } from "../../abstractions/search.service";
|
||||
import { VaultTimeoutSettingsService } from "../../abstractions/vault-timeout/vault-timeout-settings.service";
|
||||
@@ -80,7 +80,7 @@ export class VaultTimeoutService implements VaultTimeoutServiceAbstraction {
|
||||
);
|
||||
}
|
||||
|
||||
async lock(userId?: string): Promise<void> {
|
||||
async lock(userId?: UserId): Promise<void> {
|
||||
const authed = await this.stateService.getIsAuthenticated({ userId: userId });
|
||||
if (!authed) {
|
||||
return;
|
||||
@@ -94,7 +94,27 @@ export class VaultTimeoutService implements VaultTimeoutServiceAbstraction {
|
||||
await this.logOut(userId);
|
||||
}
|
||||
|
||||
const currentUserId = (await firstValueFrom(this.accountService.activeAccount$)).id;
|
||||
const currentUserId = await firstValueFrom(
|
||||
this.accountService.activeAccount$.pipe(map((a) => a?.id)),
|
||||
);
|
||||
|
||||
const lockingUserId = userId ?? currentUserId;
|
||||
|
||||
// HACK: Start listening for the transition of the locking user from something to the locked state.
|
||||
// This is very much a hack to ensure that the authentication status to retrievable right after
|
||||
// it does its work. Particularly the `lockedCallback` and `"locked"` message. Instead
|
||||
// lockedCallback should be deprecated and people should subscribe and react to `authStatusFor$` themselves.
|
||||
const lockPromise = firstValueFrom(
|
||||
this.authService.authStatusFor$(lockingUserId).pipe(
|
||||
filter((authStatus) => authStatus === AuthenticationStatus.Locked),
|
||||
timeout({
|
||||
first: 5_000,
|
||||
with: () => {
|
||||
throw new Error("The lock process did not complete in a reasonable amount of time.");
|
||||
},
|
||||
}),
|
||||
),
|
||||
);
|
||||
|
||||
if (userId == null || userId === currentUserId) {
|
||||
await this.searchService.clearIndex();
|
||||
@@ -102,19 +122,21 @@ export class VaultTimeoutService implements VaultTimeoutServiceAbstraction {
|
||||
await this.collectionService.clearActiveUserCache();
|
||||
}
|
||||
|
||||
await this.masterPasswordService.clearMasterKey((userId ?? currentUserId) as UserId);
|
||||
await this.masterPasswordService.clearMasterKey(lockingUserId);
|
||||
|
||||
await this.stateService.setUserKeyAutoUnlock(null, { userId: userId });
|
||||
await this.stateService.setCryptoMasterKeyAuto(null, { userId: userId });
|
||||
await this.stateService.setUserKeyAutoUnlock(null, { userId: lockingUserId });
|
||||
await this.stateService.setCryptoMasterKeyAuto(null, { userId: lockingUserId });
|
||||
|
||||
await this.cipherService.clearCache(userId);
|
||||
await this.cipherService.clearCache(lockingUserId);
|
||||
|
||||
await this.stateEventRunnerService.handleEvent("lock", (userId ?? currentUserId) as UserId);
|
||||
await this.stateEventRunnerService.handleEvent("lock", lockingUserId);
|
||||
|
||||
// FIXME: We should send the userId of the user that was locked, in the case of this method being passed
|
||||
// undefined then it should give back the currentUserId. Better yet, this method shouldn't take
|
||||
// an undefined userId at all. All receivers need to be checked for how they handle getting undefined.
|
||||
this.messagingService.send("locked", { userId: userId });
|
||||
// HACK: Sit here and wait for the the auth status to transition to `Locked`
|
||||
// to ensure the message and lockedCallback will get the correct status
|
||||
// if/when they call it.
|
||||
await lockPromise;
|
||||
|
||||
this.messagingService.send("locked", { userId: lockingUserId });
|
||||
|
||||
if (this.lockedCallback != null) {
|
||||
await this.lockedCallback(userId);
|
||||
@@ -162,7 +184,7 @@ export class VaultTimeoutService implements VaultTimeoutServiceAbstraction {
|
||||
return diffSeconds >= vaultTimeoutSeconds;
|
||||
}
|
||||
|
||||
private async executeTimeoutAction(userId: string): Promise<void> {
|
||||
private async executeTimeoutAction(userId: UserId): Promise<void> {
|
||||
const timeoutAction = await firstValueFrom(
|
||||
this.vaultTimeoutSettingsService.vaultTimeoutAction$(userId),
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user