Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PM-3369 - TDE - Persist user's choice to trust device to state when user ma… #6000

Original file line number Diff line number Diff line change
Expand Up @@ -93,11 +93,15 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy {
async ngOnInit() {
this.loading = true;

this.setupRememberDeviceValueChanges();

// Persist user choice from state if it exists
await this.setRememberDeviceDefaultValue();

try {
const accountDecryptionOptions: AccountDecryptionOptions =
await this.stateService.getAccountDecryptionOptions();

// TODO: verify that this doesn't also pick up key connector users... can key connector users even get here?
// see sso-login.strategy - to determine if a user is new or not it just checks if there is a key on the token response..
// can we check if they have a user key or master key in crypto service? Would that be sufficient?
if (
Expand All @@ -108,8 +112,6 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy {
// - User does not have admin approval (i.e. has not enrolled into admin reset)
// - AND does not have a master password

// TODO: discuss how this doesn't make any sense to show here

this.loadNewUserData();
} else {
this.loadUntrustedDeviceData(accountDecryptionOptions);
Expand Down Expand Up @@ -138,6 +140,25 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy {
}
}

private async setRememberDeviceDefaultValue() {
const rememberDeviceFromState = await this.deviceTrustCryptoService.getShouldTrustDevice();

const rememberDevice = rememberDeviceFromState ?? true;

this.rememberDevice.setValue(rememberDevice);
}

private setupRememberDeviceValueChanges() {
this.rememberDevice.valueChanges
.pipe(
switchMap((value) =>
defer(() => this.deviceTrustCryptoService.setShouldTrustDevice(value))
jlf0dev marked this conversation as resolved.
Show resolved Hide resolved
),
takeUntil(this.destroy$)
)
.subscribe();
}

async loadNewUserData() {
const autoEnrollStatus$ = defer(() =>
this.stateService.getUserSsoOrganizationIdentifier()
Expand Down Expand Up @@ -215,20 +236,16 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy {
return;
}

await this.deviceTrustCryptoService.setShouldTrustDevice(this.rememberDevice.value);

this.loginService.setEmail(this.data.userEmail);
this.router.navigate(["/login-with-device"]);
}

async requestAdminApproval() {
await this.deviceTrustCryptoService.setShouldTrustDevice(this.rememberDevice.value);
this.loginService.setEmail(this.data.userEmail);
this.router.navigate(["/admin-approval-requested"]);
}

async approveWithMasterPassword() {
await this.deviceTrustCryptoService.setShouldTrustDevice(this.rememberDevice.value);
this.router.navigate(["/lock"], { queryParams: { from: "login-initiated" } });
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ export abstract class DeviceTrustCryptoServiceAbstraction {
* @description Retrieves the users choice to trust the device which can only happen after decryption
* Note: this value should only be used once and then reset
*/
getShouldTrustDevice: () => Promise<boolean>;
getShouldTrustDevice: () => Promise<boolean | null>;
setShouldTrustDevice: (value: boolean) => Promise<void>;

trustDeviceIfRequired: () => Promise<void>;
Expand Down
4 changes: 2 additions & 2 deletions libs/common/src/platform/services/state.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1367,7 +1367,7 @@ export class StateService<
await this.saveAccount(account, options);
}

async getShouldTrustDevice(options?: StorageOptions): Promise<boolean> {
async getShouldTrustDevice(options?: StorageOptions): Promise<boolean | null> {
options = this.reconcileOptions(options, await this.defaultOnDiskLocalOptions());

if (options?.userId == null) {
Expand All @@ -1376,7 +1376,7 @@ export class StateService<

const account = await this.getAccount(options);

return account?.settings?.trustDeviceChoiceForDecryption ?? false;
return account?.settings?.trustDeviceChoiceForDecryption ?? null;
}

async setShouldTrustDevice(value: boolean, options?: StorageOptions): Promise<void> {
Expand Down
Loading