diff --git a/libs/angular/src/auth/components/base-login-decryption-options.component.ts b/libs/angular/src/auth/components/base-login-decryption-options.component.ts index dc15ce4d14bf..0e3dfb4fb672 100644 --- a/libs/angular/src/auth/components/base-login-decryption-options.component.ts +++ b/libs/angular/src/auth/components/base-login-decryption-options.component.ts @@ -7,7 +7,6 @@ import { switchMap, Subject, catchError, - forkJoin, from, of, finalize, @@ -22,11 +21,6 @@ import { OrganizationApiServiceAbstraction } from "@bitwarden/common/admin-conso import { DeviceTrustCryptoServiceAbstraction } from "@bitwarden/common/auth/abstractions/device-trust-crypto.service.abstraction"; import { LoginService } from "@bitwarden/common/auth/abstractions/login.service"; import { TokenService } from "@bitwarden/common/auth/abstractions/token.service"; -import { - DesktopDeviceTypes, - DeviceType, - MobileDeviceTypes, -} from "@bitwarden/common/enums/device-type.enum"; import { KeysRequest } from "@bitwarden/common/models/request/keys.request"; import { CryptoService } from "@bitwarden/common/platform/abstractions/crypto.service"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; @@ -170,23 +164,6 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy { loadUntrustedDeviceData(accountDecryptionOptions: AccountDecryptionOptions) { this.loading = true; - const mobileAndDesktopDeviceTypes: DeviceType[] = Array.from(MobileDeviceTypes).concat( - Array.from(DesktopDeviceTypes) - ); - - // Note: Each obs must handle error here and protect inner observable b/c we are using forkJoin below - // as per RxJs docs: if any given observable errors at some point, then - // forkJoin will error as well and immediately unsubscribe from the other observables. - const mobileOrDesktopDevicesExistence$ = this.devicesService - .getDevicesExistenceByTypes$(mobileAndDesktopDeviceTypes) - .pipe( - catchError((err: unknown) => { - this.validationService.showError(err); - return of(undefined); - }), - takeUntil(this.destroy$) - ); - const email$ = from(this.stateService.getEmail()).pipe( catchError((err: unknown) => { this.validationService.showError(err); @@ -195,18 +172,16 @@ export class BaseLoginDecryptionOptionsComponent implements OnInit, OnDestroy { takeUntil(this.destroy$) ); - forkJoin({ - mobileOrDesktopDevicesExistence: mobileOrDesktopDevicesExistence$, - email: email$, - }) + email$ .pipe( takeUntil(this.destroy$), finalize(() => { this.loading = false; }) ) - .subscribe(({ mobileOrDesktopDevicesExistence, email }) => { - const showApproveFromOtherDeviceBtn = mobileOrDesktopDevicesExistence || false; + .subscribe((email) => { + const showApproveFromOtherDeviceBtn = + accountDecryptionOptions?.trustedDeviceOption?.hasLoginApprovingDevice || false; const showReqAdminApprovalBtn = !!accountDecryptionOptions?.trustedDeviceOption?.hasAdminApproval || false; diff --git a/libs/common/src/abstractions/devices/devices-api.service.abstraction.ts b/libs/common/src/abstractions/devices/devices-api.service.abstraction.ts index 726c6a414527..eb32c762fd2a 100644 --- a/libs/common/src/abstractions/devices/devices-api.service.abstraction.ts +++ b/libs/common/src/abstractions/devices/devices-api.service.abstraction.ts @@ -1,4 +1,3 @@ -import { DeviceType } from "../../enums"; import { ListResponse } from "../../models/response/list.response"; import { DeviceResponse } from "./responses/device.response"; @@ -9,7 +8,6 @@ export abstract class DevicesApiServiceAbstraction { getDeviceByIdentifier: (deviceIdentifier: string) => Promise; getDevices: () => Promise>; - getDevicesExistenceByTypes: (deviceTypes: DeviceType[]) => Promise; updateTrustedDeviceKeys: ( deviceIdentifier: string, diff --git a/libs/common/src/abstractions/devices/devices.service.abstraction.ts b/libs/common/src/abstractions/devices/devices.service.abstraction.ts index ac20d0aef45c..ca803f924226 100644 --- a/libs/common/src/abstractions/devices/devices.service.abstraction.ts +++ b/libs/common/src/abstractions/devices/devices.service.abstraction.ts @@ -1,12 +1,9 @@ import { Observable } from "rxjs"; -import { DeviceType } from "../../enums"; - import { DeviceView } from "./views/device.view"; export abstract class DevicesServiceAbstraction { getDevices$: () => Observable>; - getDevicesExistenceByTypes$: (deviceTypes: DeviceType[]) => Observable; getDeviceByIdentifier$: (deviceIdentifier: string) => Observable; isDeviceKnownForUser$: (email: string, deviceIdentifier: string) => Observable; updateTrustedDeviceKeys$: ( diff --git a/libs/common/src/auth/login-strategies/sso-login.strategy.spec.ts b/libs/common/src/auth/login-strategies/sso-login.strategy.spec.ts index 75d31817df74..29797e0e7248 100644 --- a/libs/common/src/auth/login-strategies/sso-login.strategy.spec.ts +++ b/libs/common/src/auth/login-strategies/sso-login.strategy.spec.ts @@ -148,6 +148,7 @@ describe("SsoLogInStrategy", () => { HasMasterPassword: true, TrustedDeviceOption: { HasAdminApproval: true, + HasLoginApprovingDevice: true, EncryptedPrivateKey: mockEncDevicePrivateKey, EncryptedUserKey: mockEncUserKey, }, diff --git a/libs/common/src/auth/models/domain/user-decryption-options/trusted-device-user-decryption-option.ts b/libs/common/src/auth/models/domain/user-decryption-options/trusted-device-user-decryption-option.ts index 1b6fc0ce6afd..9d8fc3ed5f25 100644 --- a/libs/common/src/auth/models/domain/user-decryption-options/trusted-device-user-decryption-option.ts +++ b/libs/common/src/auth/models/domain/user-decryption-options/trusted-device-user-decryption-option.ts @@ -1,3 +1,3 @@ export class TrustedDeviceUserDecryptionOption { - constructor(public hasAdminApproval: boolean) {} + constructor(public hasAdminApproval: boolean, public hasLoginApprovingDevice: boolean) {} } diff --git a/libs/common/src/auth/models/response/user-decryption-options/trusted-device-user-decryption-option.response.ts b/libs/common/src/auth/models/response/user-decryption-options/trusted-device-user-decryption-option.response.ts index b46f35d84900..af29e3b3a430 100644 --- a/libs/common/src/auth/models/response/user-decryption-options/trusted-device-user-decryption-option.response.ts +++ b/libs/common/src/auth/models/response/user-decryption-options/trusted-device-user-decryption-option.response.ts @@ -3,12 +3,14 @@ import { EncString } from "../../../../platform/models/domain/enc-string"; export interface ITrustedDeviceUserDecryptionOptionServerResponse { HasAdminApproval: boolean; + HasLoginApprovingDevice: boolean; EncryptedPrivateKey?: string; EncryptedUserKey?: string; } export class TrustedDeviceUserDecryptionOptionResponse extends BaseResponse { hasAdminApproval: boolean; + hasLoginApprovingDevice: boolean; encryptedPrivateKey: EncString; encryptedUserKey: EncString; @@ -16,6 +18,8 @@ export class TrustedDeviceUserDecryptionOptionResponse extends BaseResponse { super(response); this.hasAdminApproval = this.getResponseProperty("HasAdminApproval"); + this.hasLoginApprovingDevice = this.getResponseProperty("HasLoginApprovingDevice"); + if (response.EncryptedPrivateKey) { this.encryptedPrivateKey = new EncString(this.getResponseProperty("EncryptedPrivateKey")); } diff --git a/libs/common/src/platform/models/domain/account.ts b/libs/common/src/platform/models/domain/account.ts index c596774e1a5f..6bdf47035b27 100644 --- a/libs/common/src/platform/models/domain/account.ts +++ b/libs/common/src/platform/models/domain/account.ts @@ -322,7 +322,8 @@ export class AccountDecryptionOptions { if (response.trustedDeviceOption) { accountDecryptionOptions.trustedDeviceOption = new TrustedDeviceUserDecryptionOption( - response.trustedDeviceOption.hasAdminApproval + response.trustedDeviceOption.hasAdminApproval, + response.trustedDeviceOption.hasLoginApprovingDevice ); } @@ -344,7 +345,8 @@ export class AccountDecryptionOptions { if (obj.trustedDeviceOption) { accountDecryptionOptions.trustedDeviceOption = new TrustedDeviceUserDecryptionOption( - obj.trustedDeviceOption.hasAdminApproval + obj.trustedDeviceOption.hasAdminApproval, + obj.trustedDeviceOption.hasLoginApprovingDevice ); } diff --git a/libs/common/src/services/devices/devices-api.service.implementation.ts b/libs/common/src/services/devices/devices-api.service.implementation.ts index af8c3b117217..7ef2694923c5 100644 --- a/libs/common/src/services/devices/devices-api.service.implementation.ts +++ b/libs/common/src/services/devices/devices-api.service.implementation.ts @@ -1,7 +1,6 @@ import { ApiService } from "../../abstractions/api.service"; import { DevicesApiServiceAbstraction } from "../../abstractions/devices/devices-api.service.abstraction"; import { DeviceResponse } from "../../abstractions/devices/responses/device.response"; -import { DeviceType } from "../../enums"; import { ListResponse } from "../../models/response/list.response"; import { Utils } from "../../platform/misc/utils"; @@ -46,18 +45,6 @@ export class DevicesApiServiceImplementation implements DevicesApiServiceAbstrac return new ListResponse(r, DeviceResponse); } - async getDevicesExistenceByTypes(deviceTypes: DeviceType[]): Promise { - const r = await this.apiService.send( - "POST", - "/devices/exist-by-types", - deviceTypes, - true, - true, - null - ); - return Boolean(r); - } - async updateTrustedDeviceKeys( deviceIdentifier: string, devicePublicKeyEncryptedUserKey: string, diff --git a/libs/common/src/services/devices/devices.service.implementation.ts b/libs/common/src/services/devices/devices.service.implementation.ts index 23ab5fa390a2..0bc0e7f478b7 100644 --- a/libs/common/src/services/devices/devices.service.implementation.ts +++ b/libs/common/src/services/devices/devices.service.implementation.ts @@ -4,7 +4,6 @@ import { DevicesApiServiceAbstraction } from "../../abstractions/devices/devices import { DevicesServiceAbstraction } from "../../abstractions/devices/devices.service.abstraction"; import { DeviceResponse } from "../../abstractions/devices/responses/device.response"; import { DeviceView } from "../../abstractions/devices/views/device.view"; -import { DeviceType } from "../../enums"; import { ListResponse } from "../../models/response/list.response"; /** @@ -31,13 +30,6 @@ export class DevicesServiceImplementation implements DevicesServiceAbstraction { ); } - /** - * @description Returns whether the user has any devices of the specified types. - */ - getDevicesExistenceByTypes$(deviceTypes: DeviceType[]): Observable { - return defer(() => this.devicesApiService.getDevicesExistenceByTypes(deviceTypes)); - } - /** * @description Gets the device with the specified identifier. */