mirror of
https://github.com/bitwarden/browser
synced 2025-12-17 00:33:44 +00:00
WIP remove validated email& display extension back button
This commit is contained in:
@@ -10,6 +10,7 @@ import { PasswordGenerationServiceAbstraction } from "@bitwarden/generator-legac
|
|||||||
|
|
||||||
import { flagEnabled } from "../../../platform/flags";
|
import { flagEnabled } from "../../../platform/flags";
|
||||||
import { BrowserPlatformUtilsService } from "../../../platform/services/platform-utils/browser-platform-utils.service";
|
import { BrowserPlatformUtilsService } from "../../../platform/services/platform-utils/browser-platform-utils.service";
|
||||||
|
import { ExtensionAnonLayoutWrapperDataService } from "../extension-anon-layout-wrapper/extension-anon-layout-wrapper-data.service";
|
||||||
|
|
||||||
import { ExtensionLoginComponentService } from "./extension-login-component.service";
|
import { ExtensionLoginComponentService } from "./extension-login-component.service";
|
||||||
|
|
||||||
@@ -24,14 +25,14 @@ describe("ExtensionLoginComponentService", () => {
|
|||||||
let passwordGenerationService: MockProxy<PasswordGenerationServiceAbstraction>;
|
let passwordGenerationService: MockProxy<PasswordGenerationServiceAbstraction>;
|
||||||
let platformUtilsService: MockProxy<BrowserPlatformUtilsService>;
|
let platformUtilsService: MockProxy<BrowserPlatformUtilsService>;
|
||||||
let ssoLoginService: MockProxy<SsoLoginServiceAbstraction>;
|
let ssoLoginService: MockProxy<SsoLoginServiceAbstraction>;
|
||||||
|
let extensionAnonLayoutWrapperDataService: MockProxy<ExtensionAnonLayoutWrapperDataService>;
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
cryptoFunctionService = mock<CryptoFunctionService>();
|
cryptoFunctionService = mock<CryptoFunctionService>();
|
||||||
environmentService = mock<EnvironmentService>();
|
environmentService = mock<EnvironmentService>();
|
||||||
passwordGenerationService = mock<PasswordGenerationServiceAbstraction>();
|
passwordGenerationService = mock<PasswordGenerationServiceAbstraction>();
|
||||||
platformUtilsService = mock<BrowserPlatformUtilsService>();
|
platformUtilsService = mock<BrowserPlatformUtilsService>();
|
||||||
ssoLoginService = mock<SsoLoginServiceAbstraction>();
|
ssoLoginService = mock<SsoLoginServiceAbstraction>();
|
||||||
|
extensionAnonLayoutWrapperDataService = mock<ExtensionAnonLayoutWrapperDataService>();
|
||||||
TestBed.configureTestingModule({
|
TestBed.configureTestingModule({
|
||||||
providers: [
|
providers: [
|
||||||
{
|
{
|
||||||
@@ -43,6 +44,7 @@ describe("ExtensionLoginComponentService", () => {
|
|||||||
passwordGenerationService,
|
passwordGenerationService,
|
||||||
platformUtilsService,
|
platformUtilsService,
|
||||||
ssoLoginService,
|
ssoLoginService,
|
||||||
|
extensionAnonLayoutWrapperDataService,
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
{ provide: DefaultLoginComponentService, useExisting: ExtensionLoginComponentService },
|
{ provide: DefaultLoginComponentService, useExisting: ExtensionLoginComponentService },
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import { PlatformUtilsService } from "@bitwarden/common/platform/abstractions/pl
|
|||||||
import { PasswordGenerationServiceAbstraction } from "@bitwarden/generator-legacy";
|
import { PasswordGenerationServiceAbstraction } from "@bitwarden/generator-legacy";
|
||||||
|
|
||||||
import { flagEnabled } from "../../../platform/flags";
|
import { flagEnabled } from "../../../platform/flags";
|
||||||
|
import { ExtensionAnonLayoutWrapperDataService } from "../extension-anon-layout-wrapper/extension-anon-layout-wrapper-data.service";
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class ExtensionLoginComponentService
|
export class ExtensionLoginComponentService
|
||||||
@@ -20,6 +21,7 @@ export class ExtensionLoginComponentService
|
|||||||
passwordGenerationService: PasswordGenerationServiceAbstraction,
|
passwordGenerationService: PasswordGenerationServiceAbstraction,
|
||||||
platformUtilsService: PlatformUtilsService,
|
platformUtilsService: PlatformUtilsService,
|
||||||
ssoLoginService: SsoLoginServiceAbstraction,
|
ssoLoginService: SsoLoginServiceAbstraction,
|
||||||
|
private extensionAnonLayoutWrapperDataService: ExtensionAnonLayoutWrapperDataService,
|
||||||
) {
|
) {
|
||||||
super(
|
super(
|
||||||
cryptoFunctionService,
|
cryptoFunctionService,
|
||||||
@@ -34,4 +36,8 @@ export class ExtensionLoginComponentService
|
|||||||
isLoginViaAuthRequestSupported(): boolean {
|
isLoginViaAuthRequestSupported(): boolean {
|
||||||
return flagEnabled("showPasswordless");
|
return flagEnabled("showPasswordless");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
showBackButton(): void {
|
||||||
|
this.extensionAnonLayoutWrapperDataService.setAnonLayoutWrapperData({ showBackButton: true });
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -602,6 +602,7 @@ const safeProviders: SafeProvider[] = [
|
|||||||
PasswordGenerationServiceAbstraction,
|
PasswordGenerationServiceAbstraction,
|
||||||
PlatformUtilsServiceAbstraction,
|
PlatformUtilsServiceAbstraction,
|
||||||
SsoLoginServiceAbstraction,
|
SsoLoginServiceAbstraction,
|
||||||
|
ExtensionAnonLayoutWrapperDataService,
|
||||||
],
|
],
|
||||||
}),
|
}),
|
||||||
safeProvider({
|
safeProvider({
|
||||||
@@ -619,6 +620,11 @@ const safeProviders: SafeProvider[] = [
|
|||||||
useClass: LoginEmailService,
|
useClass: LoginEmailService,
|
||||||
deps: [AccountService, AuthService, StateProvider],
|
deps: [AccountService, AuthService, StateProvider],
|
||||||
}),
|
}),
|
||||||
|
safeProvider({
|
||||||
|
provide: ExtensionAnonLayoutWrapperDataService,
|
||||||
|
useClass: ExtensionAnonLayoutWrapperDataService,
|
||||||
|
deps: [],
|
||||||
|
}),
|
||||||
];
|
];
|
||||||
|
|
||||||
@NgModule({
|
@NgModule({
|
||||||
|
|||||||
@@ -89,4 +89,11 @@ export class DefaultLoginComponentService implements LoginComponentService {
|
|||||||
encodeURIComponent(email),
|
encodeURIComponent(email),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* No-op implementation of showBackButton
|
||||||
|
*/
|
||||||
|
showBackButton(): void {
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -38,4 +38,9 @@ export abstract class LoginComponentService {
|
|||||||
* - Used by: Browser, Desktop
|
* - Used by: Browser, Desktop
|
||||||
*/
|
*/
|
||||||
launchSsoBrowserWindow: (email: string, clientId: "browser" | "desktop") => Promise<void>;
|
launchSsoBrowserWindow: (email: string, clientId: "browser" | "desktop") => Promise<void>;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Shows the back button.
|
||||||
|
*/
|
||||||
|
showBackButton: () => void;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,7 +11,7 @@
|
|||||||
-->
|
-->
|
||||||
|
|
||||||
<form [bitSubmit]="submit" [formGroup]="formGroup">
|
<form [bitSubmit]="submit" [formGroup]="formGroup">
|
||||||
<ng-container *ngIf="uiState === LoginUiState.EMAIL_ENTRY">
|
<ng-container *ngIf="loginUiState === LoginUiState.EMAIL_ENTRY">
|
||||||
<!-- Email Address input -->
|
<!-- Email Address input -->
|
||||||
<bit-form-field class="!tw-mb-4">
|
<bit-form-field class="!tw-mb-4">
|
||||||
<bit-label>{{ "emailAddress" | i18n }}</bit-label>
|
<bit-label>{{ "emailAddress" | i18n }}</bit-label>
|
||||||
@@ -84,7 +84,7 @@
|
|||||||
</div>
|
</div>
|
||||||
</ng-container>
|
</ng-container>
|
||||||
|
|
||||||
<ng-container *ngIf="uiState === LoginUiState.MASTER_PASSWORD_ENTRY">
|
<ng-container *ngIf="loginUiState === LoginUiState.MASTER_PASSWORD_ENTRY">
|
||||||
<!-- Master Password input -->
|
<!-- Master Password input -->
|
||||||
<bit-form-field class="!tw-mb-1">
|
<bit-form-field class="!tw-mb-1">
|
||||||
<bit-label>{{ "masterPass" | i18n }}</bit-label>
|
<bit-label>{{ "masterPass" | i18n }}</bit-label>
|
||||||
@@ -132,13 +132,13 @@
|
|||||||
</ng-container>
|
</ng-container>
|
||||||
|
|
||||||
<!-- Back button -->
|
<!-- Back button -->
|
||||||
<ng-container *ngIf="showBackButton()">
|
<ng-container *ngIf="shouldShowBackButton()">
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
bitButton
|
bitButton
|
||||||
block
|
block
|
||||||
buttonType="secondary"
|
buttonType="secondary"
|
||||||
(click)="toggleValidateEmail(false)"
|
(click)="toggleLoginUiState(LoginUiState.EMAIL_ENTRY)"
|
||||||
>
|
>
|
||||||
{{ "back" | i18n }}
|
{{ "back" | i18n }}
|
||||||
</button>
|
</button>
|
||||||
|
|||||||
@@ -80,7 +80,7 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
LoginUiState = LoginUiState;
|
LoginUiState = LoginUiState;
|
||||||
registerRoute$ = this.registerRouteService.registerRoute$(); // TODO: remove when email verification flag is removed
|
registerRoute$ = this.registerRouteService.registerRoute$(); // TODO: remove when email verification flag is removed
|
||||||
isKnownDevice = false;
|
isKnownDevice = false;
|
||||||
validatedEmail = false;
|
loginUiState: LoginUiState = LoginUiState.EMAIL_ENTRY;
|
||||||
|
|
||||||
formGroup = this.formBuilder.group(
|
formGroup = this.formBuilder.group(
|
||||||
{
|
{
|
||||||
@@ -98,10 +98,6 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
return this.formGroup.controls.email;
|
return this.formGroup.controls.email;
|
||||||
}
|
}
|
||||||
|
|
||||||
get uiState(): LoginUiState {
|
|
||||||
return this.validatedEmail ? LoginUiState.MASTER_PASSWORD_ENTRY : LoginUiState.EMAIL_ENTRY;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Web properties
|
// Web properties
|
||||||
enforcedPasswordPolicyOptions: MasterPasswordPolicyOptions;
|
enforcedPasswordPolicyOptions: MasterPasswordPolicyOptions;
|
||||||
policies: Policy[];
|
policies: Policy[];
|
||||||
@@ -164,7 +160,7 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
|
|
||||||
submit = async (): Promise<void> => {
|
submit = async (): Promise<void> => {
|
||||||
if (this.clientType === ClientType.Desktop) {
|
if (this.clientType === ClientType.Desktop) {
|
||||||
if (!this.validatedEmail) {
|
if (this.loginUiState !== LoginUiState.MASTER_PASSWORD_ENTRY) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -323,7 +319,7 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
const emailValid = this.formGroup.controls.email.valid;
|
const emailValid = this.formGroup.controls.email.valid;
|
||||||
|
|
||||||
if (emailValid) {
|
if (emailValid) {
|
||||||
this.toggleValidateEmail(true);
|
this.toggleLoginUiState(LoginUiState.MASTER_PASSWORD_ENTRY);
|
||||||
await this.getLoginWithDevice(this.emailFormControl.value);
|
await this.getLoginWithDevice(this.emailFormControl.value);
|
||||||
|
|
||||||
this.anonLayoutWrapperDataService.setAnonLayoutWrapperData({
|
this.anonLayoutWrapperDataService.setAnonLayoutWrapperData({
|
||||||
@@ -334,10 +330,10 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected toggleValidateEmail(value: boolean): void {
|
protected toggleLoginUiState(value: LoginUiState): void {
|
||||||
this.validatedEmail = value;
|
this.loginUiState = value;
|
||||||
|
|
||||||
if (!this.validatedEmail) {
|
if (this.loginUiState !== LoginUiState.MASTER_PASSWORD_ENTRY) {
|
||||||
// Reset master password only when going from validated to not validated so that autofill can work properly
|
// Reset master password only when going from validated to not validated so that autofill can work properly
|
||||||
this.formGroup.controls.masterPassword.reset();
|
this.formGroup.controls.masterPassword.reset();
|
||||||
} else {
|
} else {
|
||||||
@@ -352,6 +348,8 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
this.masterPasswordInputRef?.nativeElement?.focus();
|
this.masterPasswordInputRef?.nativeElement?.focus();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this.loginComponentService.showBackButton();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -551,7 +549,10 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||||||
* Helper function to determine if the back button should be shown.
|
* Helper function to determine if the back button should be shown.
|
||||||
* @returns true if the back button should be shown.
|
* @returns true if the back button should be shown.
|
||||||
*/
|
*/
|
||||||
protected showBackButton(): boolean {
|
protected shouldShowBackButton(): boolean {
|
||||||
return this.validatedEmail && this.clientType !== ClientType.Browser;
|
return (
|
||||||
|
this.loginUiState === LoginUiState.MASTER_PASSWORD_ENTRY &&
|
||||||
|
this.clientType !== ClientType.Browser
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user