mirror of
https://github.com/bitwarden/browser
synced 2026-02-11 05:53:42 +00:00
[Account Recovery][PM-18721] handle cross-component submit process
This commit is contained in:
@@ -9,27 +9,19 @@
|
||||
[message]="'resetPasswordMasterPasswordPolicyInEffect'"
|
||||
[masterPasswordPolicyOptions]="masterPasswordPolicyOptions$ | async"
|
||||
(onPasswordFormSubmit)="handlePasswordFormSubmit($event)"
|
||||
(isSubmitting)="handleIsSubmittingChange($event)"
|
||||
></auth-input-password>
|
||||
</ng-container>
|
||||
|
||||
<ng-container bitDialogFooter>
|
||||
<button
|
||||
class="tw-relative"
|
||||
type="button"
|
||||
bitButton
|
||||
buttonType="primary"
|
||||
[disabled]="submitting"
|
||||
[disabled]="submitting$ | async"
|
||||
(click)="handlePrimaryButtonClick()"
|
||||
>
|
||||
<span
|
||||
[ngClass]="{ 'tw-invisible': !submitting }"
|
||||
class="tw-absolute tw-inset-0 tw-flex tw-items-center tw-justify-center"
|
||||
>
|
||||
<i class="bwi bwi-spinner bwi-lg bwi-spin" aria-hidden="true"></i>
|
||||
</span>
|
||||
<span [ngClass]="{ 'tw-invisible': submitting }">
|
||||
{{ "save" | i18n }}
|
||||
</span>
|
||||
{{ "save" | i18n }}
|
||||
</button>
|
||||
<button type="button" bitButton buttonType="secondary" bitDialogClose>
|
||||
{{ "cancel" | i18n }}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { CommonModule } from "@angular/common";
|
||||
import { Component, Inject, ViewChild } from "@angular/core";
|
||||
import { switchMap } from "rxjs";
|
||||
import { BehaviorSubject, combineLatest, map, switchMap } from "rxjs";
|
||||
|
||||
import {
|
||||
InputPasswordComponent,
|
||||
@@ -82,15 +82,23 @@ export class AccountRecoveryDialogComponent {
|
||||
@ViewChild(InputPasswordComponent)
|
||||
inputPasswordComponent!: InputPasswordComponent;
|
||||
|
||||
inputPasswordFlow = InputPasswordFlow.ChangePasswordDelegation;
|
||||
receivedPasswordInputResult = false;
|
||||
submitting = false;
|
||||
private parentSubmittingBehaviorSubject = new BehaviorSubject(false);
|
||||
parentSubmitting$ = this.parentSubmittingBehaviorSubject.asObservable();
|
||||
|
||||
private childSubmittingBehaviorSubject = new BehaviorSubject(false);
|
||||
childSubmitting$ = this.childSubmittingBehaviorSubject.asObservable();
|
||||
|
||||
submitting$ = combineLatest([this.parentSubmitting$, this.childSubmitting$]).pipe(
|
||||
map(([parentIsSubmitting, childIsSubmitting]) => parentIsSubmitting || childIsSubmitting),
|
||||
);
|
||||
|
||||
masterPasswordPolicyOptions$ = this.accountService.activeAccount$.pipe(
|
||||
getUserId,
|
||||
switchMap((userId) => this.policyService.masterPasswordPolicyOptions$(userId)),
|
||||
);
|
||||
|
||||
inputPasswordFlow = InputPasswordFlow.ChangePasswordDelegation;
|
||||
|
||||
get loggedOutWarningName() {
|
||||
return this.dialogData.name != null ? this.dialogData.name : this.i18nService.t("thisUser");
|
||||
}
|
||||
@@ -107,23 +115,11 @@ export class AccountRecoveryDialogComponent {
|
||||
) {}
|
||||
|
||||
handlePrimaryButtonClick = async () => {
|
||||
try {
|
||||
this.submitting = true;
|
||||
await this.inputPasswordComponent.submit();
|
||||
} catch {
|
||||
// Flip to false if submit() throws an error
|
||||
this.submitting = false;
|
||||
}
|
||||
|
||||
// Flip to false if submit() returns early without a PasswordInputResult
|
||||
// emission due to form validation errors or new password doesn't meet org policy reqs.
|
||||
if (!this.receivedPasswordInputResult) {
|
||||
this.submitting = false;
|
||||
}
|
||||
await this.inputPasswordComponent.submit();
|
||||
};
|
||||
|
||||
async handlePasswordFormSubmit(passwordInputResult: PasswordInputResult) {
|
||||
this.receivedPasswordInputResult = Boolean(passwordInputResult);
|
||||
this.parentSubmittingBehaviorSubject.next(true);
|
||||
|
||||
try {
|
||||
await this.resetPasswordService.resetMasterPassword(
|
||||
@@ -140,11 +136,17 @@ export class AccountRecoveryDialogComponent {
|
||||
});
|
||||
} catch (e) {
|
||||
this.logService.error(e);
|
||||
} finally {
|
||||
this.parentSubmittingBehaviorSubject.next(false);
|
||||
}
|
||||
|
||||
this.dialogRef.close(AccountRecoveryDialogResultTypes.Ok);
|
||||
}
|
||||
|
||||
protected handleIsSubmittingChange(isSubmitting: boolean) {
|
||||
this.childSubmittingBehaviorSubject.next(isSubmitting);
|
||||
}
|
||||
|
||||
/**
|
||||
* Strongly typed helper to open an `AccountRecoveryDialogComponent`
|
||||
* @param dialogService Instance of the dialog service that will be used to open the dialog
|
||||
|
||||
Reference in New Issue
Block a user