diff --git a/src/_locales/en/messages.json b/src/_locales/en/messages.json index e42b3f08173..643d21d9135 100644 --- a/src/_locales/en/messages.json +++ b/src/_locales/en/messages.json @@ -1752,5 +1752,14 @@ }, "emailVerificationRequiredDesc": { "message": "You must verify your email to use this feature. You can verify your email in the web vault." + }, + "updatedMasterPassword": { + "message": "Updated Master Password" + }, + "updateMasterPassword": { + "message": "Update Master Password" + }, + "updateMasterPasswordWarning": { + "message": "Your Master Password was recently changed by an administrator in your organization. In order to access the vault, you must update it now. Proceeding will log you out of your current session, requiring you to log back in. Active sessions on other devices may continue to remain active for up to one hour." } } diff --git a/src/popup/accounts/login.component.ts b/src/popup/accounts/login.component.ts index f1152d8aac7..ffcf9c375a5 100644 --- a/src/popup/accounts/login.component.ts +++ b/src/popup/accounts/login.component.ts @@ -10,6 +10,7 @@ import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.se import { StateService } from 'jslib-common/abstractions/state.service'; import { StorageService } from 'jslib-common/abstractions/storage.service'; import { SyncService } from 'jslib-common/abstractions/sync.service'; +import { UserService } from 'jslib-common/abstractions/user.service'; import { LoginComponent as BaseLoginComponent } from 'jslib-angular/components/login.component'; @@ -23,12 +24,19 @@ export class LoginComponent extends BaseLoginComponent { protected stateService: StateService, protected environmentService: EnvironmentService, protected passwordGenerationService: PasswordGenerationService, protected cryptoFunctionService: CryptoFunctionService, storageService: StorageService, - syncService: SyncService) { + syncService: SyncService, private userService: UserService) { super(authService, router, platformUtilsService, i18nService, stateService, environmentService, passwordGenerationService, cryptoFunctionService, storageService); super.onSuccessfulLogin = () => { return syncService.fullSync(true); }; super.successRoute = '/tabs/vault'; + super.onSuccessfulLoginNavigate = async () => { + if (await this.userService.getForcePasswordReset()) { + this.router.navigate(['update-temp-password']); + } else { + this.router.navigate([this.successRoute]); + } + }; } settings() { diff --git a/src/popup/accounts/set-password.component.ts b/src/popup/accounts/set-password.component.ts index 143bb864c86..8e795f9fe57 100644 --- a/src/popup/accounts/set-password.component.ts +++ b/src/popup/accounts/set-password.component.ts @@ -31,6 +31,13 @@ export class SetPasswordComponent extends BaseSetPasswordComponent { syncService: SyncService, route: ActivatedRoute) { super(i18nService, cryptoService, messagingService, userService, passwordGenerationService, platformUtilsService, policyService, router, apiService, syncService, route); + super.onSuccessfulChangePassword = async () => { + if (await this.userService.getForcePasswordReset()) { + this.router.navigate(['update-temp-password']); + } else { + this.router.navigate([this.successRoute]); + } + }; } get masterPasswordScoreWidth() { diff --git a/src/popup/accounts/sso.component.ts b/src/popup/accounts/sso.component.ts index 34b3a77c01a..6536e67068f 100644 --- a/src/popup/accounts/sso.component.ts +++ b/src/popup/accounts/sso.component.ts @@ -15,6 +15,7 @@ import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.se import { StateService } from 'jslib-common/abstractions/state.service'; import { StorageService } from 'jslib-common/abstractions/storage.service'; import { SyncService } from 'jslib-common/abstractions/sync.service'; +import { UserService } from 'jslib-common/abstractions/user.service'; import { SsoComponent as BaseSsoComponent } from 'jslib-angular/components/sso.component'; import { BrowserApi } from '../../browser/browserApi'; @@ -29,7 +30,7 @@ export class SsoComponent extends BaseSsoComponent { storageService: StorageService, stateService: StateService, platformUtilsService: PlatformUtilsService, apiService: ApiService, cryptoFunctionService: CryptoFunctionService, passwordGenerationService: PasswordGenerationService, - syncService: SyncService, environmentService: EnvironmentService) { + syncService: SyncService, environmentService: EnvironmentService, private userService: UserService) { super(authService, router, i18nService, route, storageService, stateService, platformUtilsService, apiService, cryptoFunctionService, environmentService, passwordGenerationService); @@ -44,5 +45,13 @@ export class SsoComponent extends BaseSsoComponent { const thisWindow = window.open('', '_self'); thisWindow.close(); }; + + super.onSuccessfulLoginNavigate = async () => { + if (await this.userService.getForcePasswordReset()) { + this.router.navigate(['update-temp-password']); + } else { + this.router.navigate([this.successRoute]); + } + }; } } diff --git a/src/popup/accounts/two-factor.component.ts b/src/popup/accounts/two-factor.component.ts index 7850daa5d91..409591f10ce 100644 --- a/src/popup/accounts/two-factor.component.ts +++ b/src/popup/accounts/two-factor.component.ts @@ -20,6 +20,7 @@ import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.se import { StateService } from 'jslib-common/abstractions/state.service'; import { StorageService } from 'jslib-common/abstractions/storage.service'; import { SyncService } from 'jslib-common/abstractions/sync.service'; +import { UserService } from 'jslib-common/abstractions/user.service'; import { BroadcasterService } from 'jslib-angular/services/broadcaster.service'; @@ -44,7 +45,8 @@ export class TwoFactorComponent extends BaseTwoFactorComponent { environmentService: EnvironmentService, private ngZone: NgZone, private broadcasterService: BroadcasterService, private changeDetectorRef: ChangeDetectorRef, private popupUtilsService: PopupUtilsService, stateService: StateService, - storageService: StorageService, route: ActivatedRoute, private messagingService: MessagingService) { + storageService: StorageService, route: ActivatedRoute, private messagingService: MessagingService, + private userService: UserService) { super(authService, router, i18nService, apiService, platformUtilsService, window, environmentService, stateService, storageService, route); super.onSuccessfulLogin = () => { @@ -52,6 +54,17 @@ export class TwoFactorComponent extends BaseTwoFactorComponent { }; super.successRoute = '/tabs/vault'; this.webAuthnNewTab = this.platformUtilsService.isFirefox() || this.platformUtilsService.isSafari(); + super.onSuccessfulLoginNavigate = async () => { + if (await this.userService.getForcePasswordReset()) { + this.router.navigate(['update-temp-password']); + } else { + this.router.navigate([this.successRoute], { + queryParams: { + identifier: this.identifier, + }, + }); + } + } } async ngOnInit() { diff --git a/src/popup/accounts/update-temp-password.component.html b/src/popup/accounts/update-temp-password.component.html new file mode 100644 index 00000000000..5154590c8bc --- /dev/null +++ b/src/popup/accounts/update-temp-password.component.html @@ -0,0 +1,100 @@ +
diff --git a/src/popup/accounts/update-temp-password.component.ts b/src/popup/accounts/update-temp-password.component.ts new file mode 100644 index 00000000000..2ae67464648 --- /dev/null +++ b/src/popup/accounts/update-temp-password.component.ts @@ -0,0 +1,27 @@ +import { Component } from '@angular/core'; + +import { ApiService } from 'jslib-common/abstractions/api.service'; +import { CryptoService } from 'jslib-common/abstractions/crypto.service'; +import { I18nService } from 'jslib-common/abstractions/i18n.service'; +import { MessagingService } from 'jslib-common/abstractions/messaging.service'; +import { PasswordGenerationService } from 'jslib-common/abstractions/passwordGeneration.service'; +import { PlatformUtilsService } from 'jslib-common/abstractions/platformUtils.service'; +import { PolicyService } from 'jslib-common/abstractions/policy.service'; +import { UserService } from 'jslib-common/abstractions/user.service'; + +import { UpdateTempPasswordComponent as BaseUpdateTempPasswordComponent } from 'jslib-angular/components/update-temp-password.component'; + +@Component({ + selector: 'app-update-temp-password', + templateUrl: 'update-temp-password.component.html', +}) + +export class UpdateTempPasswordComponent extends BaseUpdateTempPasswordComponent { + constructor(i18nService: I18nService, platformUtilsService: PlatformUtilsService, + passwordGenerationService: PasswordGenerationService, policyService: PolicyService, + cryptoService: CryptoService, userService: UserService, + messagingService: MessagingService, apiService: ApiService) { + super(i18nService, platformUtilsService, passwordGenerationService, policyService, cryptoService, + userService, messagingService, apiService); + } +} diff --git a/src/popup/app-routing.module.ts b/src/popup/app-routing.module.ts index 7fe2ddfeafa..f6558b74845 100644 --- a/src/popup/app-routing.module.ts +++ b/src/popup/app-routing.module.ts @@ -22,6 +22,7 @@ import { SetPasswordComponent } from './accounts/set-password.component'; import { SsoComponent } from './accounts/sso.component'; import { TwoFactorOptionsComponent } from './accounts/two-factor-options.component'; import { TwoFactorComponent } from './accounts/two-factor.component'; +import { UpdateTempPasswordComponent } from './accounts/update-temp-password.component'; import { PasswordGeneratorHistoryComponent } from './generator/password-generator-history.component'; import { PasswordGeneratorComponent } from './generator/password-generator.component'; @@ -261,6 +262,12 @@ const routes: Routes = [ canActivate: [AuthGuardService], data: { state: 'edit-send' }, }, + { + path: 'update-temp-password', + component: UpdateTempPasswordComponent, + canActivate: [AuthGuardService], + data: { state: 'update-temp-password' }, + }, { path: 'tabs', component: TabsComponent, diff --git a/src/popup/app.module.ts b/src/popup/app.module.ts index a36a8a56277..15c8f40a388 100644 --- a/src/popup/app.module.ts +++ b/src/popup/app.module.ts @@ -20,6 +20,7 @@ import { SetPasswordComponent } from './accounts/set-password.component'; import { SsoComponent } from './accounts/sso.component'; import { TwoFactorOptionsComponent } from './accounts/two-factor-options.component'; import { TwoFactorComponent } from './accounts/two-factor.component'; +import { UpdateTempPasswordComponent } from './accounts/update-temp-password.component'; import { PasswordGeneratorHistoryComponent } from './generator/password-generator-history.component'; import { PasswordGeneratorComponent } from './generator/password-generator.component'; @@ -224,8 +225,10 @@ registerLocaleData(localeZhTw, 'zh-TW'); SendGroupingsComponent, SendListComponent, SendTypeComponent, + SetPasswordComponent, SettingsComponent, ShareComponent, + SsoComponent, StopClickDirective, StopPropDirective, SyncComponent, @@ -233,9 +236,8 @@ registerLocaleData(localeZhTw, 'zh-TW'); TrueFalseValueDirective, TwoFactorOptionsComponent, TwoFactorComponent, - SsoComponent, + UpdateTempPasswordComponent, ViewComponent, - SetPasswordComponent, ], entryComponents: [], providers: [