diff --git a/apps/browser/src/autofill/popup/fido2/fido2-cipher-row.component.ts b/apps/browser/src/autofill/popup/fido2/fido2-cipher-row.component.ts index adabae2c31d..ace314c6a84 100644 --- a/apps/browser/src/autofill/popup/fido2/fido2-cipher-row.component.ts +++ b/apps/browser/src/autofill/popup/fido2/fido2-cipher-row.component.ts @@ -1,5 +1,3 @@ -// FIXME: Update this file to be type safe and remove this and next line -// @ts-strict-ignore import { CommonModule } from "@angular/common"; import { Component, EventEmitter, Input, Output, ChangeDetectionStrategy } from "@angular/core"; @@ -33,13 +31,10 @@ export class Fido2CipherRowComponent { @Output() onSelected = new EventEmitter(); // FIXME(https://bitwarden.atlassian.net/browse/CL-903): Migrate to Signals // eslint-disable-next-line @angular-eslint/prefer-signals - @Input() cipher: CipherView; + @Input({ required: true }) cipher!: CipherView; // FIXME(https://bitwarden.atlassian.net/browse/CL-903): Migrate to Signals // eslint-disable-next-line @angular-eslint/prefer-signals - @Input() last: boolean; - // FIXME(https://bitwarden.atlassian.net/browse/CL-903): Migrate to Signals - // eslint-disable-next-line @angular-eslint/prefer-signals - @Input() title: string; + @Input({ required: true }) title!: string; protected selectCipher(c: CipherView) { this.onSelected.emit(c); diff --git a/apps/web/src/app/dirt/reports/pages/breach-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/breach-report.component.spec.ts index 886267e3189..6a26d8abd74 100644 --- a/apps/web/src/app/dirt/reports/pages/breach-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/breach-report.component.spec.ts @@ -1,17 +1,17 @@ -// FIXME: Update this file to be type safe and remove this and next line -// @ts-strict-ignore +import { Component, ChangeDetectionStrategy } from "@angular/core"; import { ComponentFixture, TestBed } from "@angular/core/testing"; import { ReactiveFormsModule } from "@angular/forms"; import { mock, MockProxy } from "jest-mock-extended"; import { BehaviorSubject } from "rxjs"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { AuditService } from "@bitwarden/common/abstractions/audit.service"; import { AccountInfo, AccountService } from "@bitwarden/common/auth/abstractions/account.service"; import { BreachAccountResponse } from "@bitwarden/common/dirt/models/response/breach-account.response"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; import { mockAccountInfoWith } from "@bitwarden/common/spec"; import { UserId } from "@bitwarden/common/types/guid"; +import { AsyncActionsModule, ButtonModule, FormFieldModule } from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { BreachReportComponent } from "./breach-report.component"; @@ -32,6 +32,21 @@ const breachedAccounts = [ }), ]; +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "app-header", + template: "
", + standalone: false, +}) +class MockHeaderComponent {} +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "bit-container", + template: "
", + standalone: false, +}) +class MockBitContainerComponent {} + describe("BreachReportComponent", () => { let component: BreachReportComponent; let fixture: ComponentFixture; @@ -51,8 +66,8 @@ describe("BreachReportComponent", () => { accountService.activeAccount$ = activeAccountSubject; await TestBed.configureTestingModule({ - declarations: [BreachReportComponent, I18nPipe], - imports: [ReactiveFormsModule], + declarations: [BreachReportComponent, MockHeaderComponent, MockBitContainerComponent], + imports: [ReactiveFormsModule, I18nPipe, AsyncActionsModule, ButtonModule, FormFieldModule], providers: [ { provide: AuditService, @@ -67,9 +82,7 @@ describe("BreachReportComponent", () => { useValue: mock(), }, ], - // FIXME(PM-18598): Replace unknownElements and unknownProperties with actual imports - errorOnUnknownElements: false, - errorOnUnknownProperties: false, + schemas: [], }).compileComponents(); }); diff --git a/apps/web/src/app/dirt/reports/pages/exposed-passwords-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/exposed-passwords-report.component.spec.ts index 560245bdc34..e056ec44af5 100644 --- a/apps/web/src/app/dirt/reports/pages/exposed-passwords-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/exposed-passwords-report.component.spec.ts @@ -1,8 +1,8 @@ +import { Component, ChangeDetectionStrategy } from "@angular/core"; import { ComponentFixture, TestBed } from "@angular/core/testing"; import { mock, MockProxy } from "jest-mock-extended"; import { of } from "rxjs"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { AuditService } from "@bitwarden/common/abstractions/audit.service"; import { OrganizationService } from "@bitwarden/common/admin-console/abstractions/organization/organization.service.abstraction"; import { AccountService } from "@bitwarden/common/auth/abstractions/account.service"; @@ -12,7 +12,13 @@ import { FakeAccountService, mockAccountServiceWith } from "@bitwarden/common/sp import { UserId } from "@bitwarden/common/types/guid"; import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.service"; import { SyncService } from "@bitwarden/common/vault/abstractions/sync/sync.service.abstraction"; -import { DialogService } from "@bitwarden/components"; +import { + DialogService, + AsyncActionsModule, + ButtonModule, + FormFieldModule, +} from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { CipherFormConfigService, PasswordRepromptService } from "@bitwarden/vault"; import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/services/admin-console-cipher-form-config.service"; @@ -20,6 +26,22 @@ import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/se import { ExposedPasswordsReportComponent } from "./exposed-passwords-report.component"; import { cipherData } from "./reports-ciphers.mock"; +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "app-header", + template: "
", + standalone: false, +}) +class MockHeaderComponent {} + +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "bit-container", + template: "
", + standalone: false, +}) +class MockBitContainerComponent {} + describe("ExposedPasswordsReportComponent", () => { let component: ExposedPasswordsReportComponent; let fixture: ComponentFixture; @@ -30,16 +52,19 @@ describe("ExposedPasswordsReportComponent", () => { const userId = Utils.newGuid() as UserId; const accountService: FakeAccountService = mockAccountServiceWith(userId); - beforeEach(() => { + beforeEach(async () => { let cipherFormConfigServiceMock: MockProxy; syncServiceMock = mock(); auditService = mock(); organizationService = mock(); organizationService.organizations$.mockReturnValue(of([])); - // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling. - // eslint-disable-next-line @typescript-eslint/no-floating-promises - TestBed.configureTestingModule({ - declarations: [ExposedPasswordsReportComponent, I18nPipe], + await TestBed.configureTestingModule({ + declarations: [ + ExposedPasswordsReportComponent, + MockHeaderComponent, + MockBitContainerComponent, + ], + imports: [I18nPipe, AsyncActionsModule, ButtonModule, FormFieldModule], providers: [ { provide: CipherService, @@ -83,9 +108,6 @@ describe("ExposedPasswordsReportComponent", () => { }, ], schemas: [], - // FIXME(PM-18598): Replace unknownElements and unknownProperties with actual imports - errorOnUnknownElements: false, - errorOnUnknownProperties: false, }).compileComponents(); }); diff --git a/apps/web/src/app/dirt/reports/pages/inactive-two-factor-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/inactive-two-factor-report.component.spec.ts index 64a851e120e..12453ea3b88 100644 --- a/apps/web/src/app/dirt/reports/pages/inactive-two-factor-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/inactive-two-factor-report.component.spec.ts @@ -3,7 +3,6 @@ import { ComponentFixture, TestBed } from "@angular/core/testing"; import { MockProxy, mock } from "jest-mock-extended"; import { of } from "rxjs"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { OrganizationService } from "@bitwarden/common/admin-console/abstractions/organization/organization.service.abstraction"; import { AccountService } from "@bitwarden/common/auth/abstractions/account.service"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; @@ -14,6 +13,7 @@ import { UserId } from "@bitwarden/common/types/guid"; import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.service"; import { SyncService } from "@bitwarden/common/vault/abstractions/sync/sync.service.abstraction"; import { DialogService } from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { CipherFormConfigService, PasswordRepromptService } from "@bitwarden/vault"; import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/services/admin-console-cipher-form-config.service"; @@ -37,7 +37,8 @@ describe("InactiveTwoFactorReportComponent", () => { syncServiceMock = mock(); await TestBed.configureTestingModule({ - declarations: [InactiveTwoFactorReportComponent, I18nPipe], + declarations: [InactiveTwoFactorReportComponent], + imports: [I18nPipe], providers: [ { provide: CipherService, diff --git a/apps/web/src/app/dirt/reports/pages/reused-passwords-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/reused-passwords-report.component.spec.ts index 5933d2ce293..1b7006d0c68 100644 --- a/apps/web/src/app/dirt/reports/pages/reused-passwords-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/reused-passwords-report.component.spec.ts @@ -1,8 +1,8 @@ +import { ChangeDetectionStrategy, Component } from "@angular/core"; import { ComponentFixture, TestBed } from "@angular/core/testing"; import { MockProxy, mock } from "jest-mock-extended"; import { of } from "rxjs"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { OrganizationService } from "@bitwarden/common/admin-console/abstractions/organization/organization.service.abstraction"; import { AccountService } from "@bitwarden/common/auth/abstractions/account.service"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; @@ -12,6 +12,7 @@ import { UserId } from "@bitwarden/common/types/guid"; import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.service"; import { SyncService } from "@bitwarden/common/vault/abstractions/sync/sync.service.abstraction"; import { DialogService } from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { CipherFormConfigService, PasswordRepromptService } from "@bitwarden/vault"; import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/services/admin-console-cipher-form-config.service"; @@ -19,6 +20,22 @@ import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/se import { cipherData } from "./reports-ciphers.mock"; import { ReusedPasswordsReportComponent } from "./reused-passwords-report.component"; +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "app-header", + template: "
", + standalone: false, +}) +class MockHeaderComponent {} + +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "bit-container", + template: "
", + standalone: false, +}) +class MockBitContainerComponent {} + describe("ReusedPasswordsReportComponent", () => { let component: ReusedPasswordsReportComponent; let fixture: ComponentFixture; @@ -28,15 +45,18 @@ describe("ReusedPasswordsReportComponent", () => { const userId = Utils.newGuid() as UserId; const accountService: FakeAccountService = mockAccountServiceWith(userId); - beforeEach(() => { + beforeEach(async () => { let cipherFormConfigServiceMock: MockProxy; organizationService = mock(); organizationService.organizations$.mockReturnValue(of([])); syncServiceMock = mock(); - // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling. - // eslint-disable-next-line @typescript-eslint/no-floating-promises - TestBed.configureTestingModule({ - declarations: [ReusedPasswordsReportComponent, I18nPipe], + await TestBed.configureTestingModule({ + declarations: [ + ReusedPasswordsReportComponent, + MockHeaderComponent, + MockBitContainerComponent, + ], + imports: [I18nPipe], providers: [ { provide: CipherService, @@ -76,8 +96,6 @@ describe("ReusedPasswordsReportComponent", () => { }, ], schemas: [], - // FIXME(PM-18598): Replace unknownElements and unknownProperties with actual imports - errorOnUnknownElements: false, }).compileComponents(); }); diff --git a/apps/web/src/app/dirt/reports/pages/unsecured-websites-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/unsecured-websites-report.component.spec.ts index 040d73a0d66..2107e0c8df7 100644 --- a/apps/web/src/app/dirt/reports/pages/unsecured-websites-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/unsecured-websites-report.component.spec.ts @@ -1,9 +1,9 @@ +import { ChangeDetectionStrategy, Component } from "@angular/core"; import { ComponentFixture, TestBed } from "@angular/core/testing"; import { MockProxy, mock } from "jest-mock-extended"; import { of } from "rxjs"; import { CollectionService } from "@bitwarden/admin-console/common"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { OrganizationService } from "@bitwarden/common/admin-console/abstractions/organization/organization.service.abstraction"; import { AccountService } from "@bitwarden/common/auth/abstractions/account.service"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; @@ -13,6 +13,7 @@ import { UserId } from "@bitwarden/common/types/guid"; import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.service"; import { SyncService } from "@bitwarden/common/vault/abstractions/sync/sync.service.abstraction"; import { DialogService } from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { CipherFormConfigService, PasswordRepromptService } from "@bitwarden/vault"; import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/services/admin-console-cipher-form-config.service"; @@ -20,6 +21,22 @@ import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/se import { cipherData } from "./reports-ciphers.mock"; import { UnsecuredWebsitesReportComponent } from "./unsecured-websites-report.component"; +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "app-header", + template: "
", + standalone: false, +}) +class MockHeaderComponent {} + +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "bit-container", + template: "
", + standalone: false, +}) +class MockBitContainerComponent {} + describe("UnsecuredWebsitesReportComponent", () => { let component: UnsecuredWebsitesReportComponent; let fixture: ComponentFixture; @@ -30,7 +47,7 @@ describe("UnsecuredWebsitesReportComponent", () => { const userId = Utils.newGuid() as UserId; const accountService: FakeAccountService = mockAccountServiceWith(userId); - beforeEach(() => { + beforeEach(async () => { let cipherFormConfigServiceMock: MockProxy; organizationService = mock(); organizationService.organizations$.mockReturnValue(of([])); @@ -38,10 +55,13 @@ describe("UnsecuredWebsitesReportComponent", () => { collectionService = mock(); adminConsoleCipherFormConfigService = mock(); - // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling. - // eslint-disable-next-line @typescript-eslint/no-floating-promises - TestBed.configureTestingModule({ - declarations: [UnsecuredWebsitesReportComponent, I18nPipe], + await TestBed.configureTestingModule({ + declarations: [ + UnsecuredWebsitesReportComponent, + MockHeaderComponent, + MockBitContainerComponent, + ], + imports: [I18nPipe], providers: [ { provide: CipherService, @@ -85,8 +105,6 @@ describe("UnsecuredWebsitesReportComponent", () => { }, ], schemas: [], - // FIXME(PM-18598): Replace unknownElements and unknownProperties with actual imports - errorOnUnknownElements: false, }).compileComponents(); }); diff --git a/apps/web/src/app/dirt/reports/pages/weak-passwords-report.component.spec.ts b/apps/web/src/app/dirt/reports/pages/weak-passwords-report.component.spec.ts index d78dc7e3ceb..a63723dc688 100644 --- a/apps/web/src/app/dirt/reports/pages/weak-passwords-report.component.spec.ts +++ b/apps/web/src/app/dirt/reports/pages/weak-passwords-report.component.spec.ts @@ -1,8 +1,8 @@ +import { ChangeDetectionStrategy, Component } from "@angular/core"; import { ComponentFixture, TestBed } from "@angular/core/testing"; import { mock, MockProxy } from "jest-mock-extended"; import { of } from "rxjs"; -import { I18nPipe } from "@bitwarden/angular/platform/pipes/i18n.pipe"; import { OrganizationService } from "@bitwarden/common/admin-console/abstractions/organization/organization.service.abstraction"; import { AccountService } from "@bitwarden/common/auth/abstractions/account.service"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; @@ -13,6 +13,7 @@ import { UserId } from "@bitwarden/common/types/guid"; import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.service"; import { SyncService } from "@bitwarden/common/vault/abstractions/sync/sync.service.abstraction"; import { DialogService } from "@bitwarden/components"; +import { I18nPipe } from "@bitwarden/ui-common"; import { CipherFormConfigService, PasswordRepromptService } from "@bitwarden/vault"; import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/services/admin-console-cipher-form-config.service"; @@ -20,6 +21,22 @@ import { AdminConsoleCipherFormConfigService } from "../../../vault/org-vault/se import { cipherData } from "./reports-ciphers.mock"; import { WeakPasswordsReportComponent } from "./weak-passwords-report.component"; +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "app-header", + template: "
", + standalone: false, +}) +class MockHeaderComponent {} + +@Component({ + changeDetection: ChangeDetectionStrategy.OnPush, + selector: "bit-container", + template: "
", + standalone: false, +}) +class MockBitContainerComponent {} + describe("WeakPasswordsReportComponent", () => { let component: WeakPasswordsReportComponent; let fixture: ComponentFixture; @@ -30,16 +47,16 @@ describe("WeakPasswordsReportComponent", () => { const userId = Utils.newGuid() as UserId; const accountService: FakeAccountService = mockAccountServiceWith(userId); - beforeEach(() => { + beforeEach(async () => { let cipherFormConfigServiceMock: MockProxy; syncServiceMock = mock(); passwordStrengthService = mock(); organizationService = mock(); organizationService.organizations$.mockReturnValue(of([])); - // FIXME: Verify that this floating promise is intentional. If it is, add an explanatory comment and ensure there is proper error handling. - // eslint-disable-next-line @typescript-eslint/no-floating-promises - TestBed.configureTestingModule({ - declarations: [WeakPasswordsReportComponent, I18nPipe], + + await TestBed.configureTestingModule({ + declarations: [WeakPasswordsReportComponent, MockHeaderComponent, MockBitContainerComponent], + imports: [I18nPipe], providers: [ { provide: CipherService, @@ -84,8 +101,6 @@ describe("WeakPasswordsReportComponent", () => { }, ], schemas: [], - // FIXME(PM-18598): Replace unknownElements and unknownProperties with actual imports - errorOnUnknownElements: false, }).compileComponents(); }); diff --git a/apps/web/src/app/vault/components/vault-item-dialog/vault-item-dialog.component.html b/apps/web/src/app/vault/components/vault-item-dialog/vault-item-dialog.component.html index 3dce773c7c1..640febf41d2 100644 --- a/apps/web/src/app/vault/components/vault-item-dialog/vault-item-dialog.component.html +++ b/apps/web/src/app/vault/components/vault-item-dialog/vault-item-dialog.component.html @@ -106,15 +106,17 @@ > } } - + @if (cipher) { + + } } diff --git a/libs/admin-console/src/common/collections/models/collection-admin.view.ts b/libs/admin-console/src/common/collections/models/collection-admin.view.ts index 4e4ebae964e..d5effaad3aa 100644 --- a/libs/admin-console/src/common/collections/models/collection-admin.view.ts +++ b/libs/admin-console/src/common/collections/models/collection-admin.view.ts @@ -121,13 +121,13 @@ export class CollectionAdminView extends CollectionView { try { view.name = await encryptService.decryptString(new EncString(view.name), orgKey); } catch (e) { - view.name = "[error: cannot decrypt]"; // Note: This should be replaced by the owning team with appropriate, domain-specific behavior. // eslint-disable-next-line no-console console.error( "[CollectionAdminView/fromCollectionAccessDetails] Error decrypting collection name", e, ); + throw e; } view.assigned = collection.assigned; view.readOnly = collection.readOnly; diff --git a/libs/admin-console/src/common/collections/models/collection.view.ts b/libs/admin-console/src/common/collections/models/collection.view.ts index 64b6e2a9d1e..2991e8bb171 100644 --- a/libs/admin-console/src/common/collections/models/collection.view.ts +++ b/libs/admin-console/src/common/collections/models/collection.view.ts @@ -126,14 +126,7 @@ export class CollectionView implements View, ITreeNodeObject { ): Promise { const view = new CollectionView({ ...collection, name: "" }); - try { - view.name = await encryptService.decryptString(collection.name, key); - } catch (e) { - view.name = "[error: cannot decrypt]"; - // eslint-disable-next-line no-console - console.error("[CollectionView] Error decrypting collection name", e); - } - + view.name = await encryptService.decryptString(collection.name, key); view.assigned = true; view.externalId = collection.externalId; view.readOnly = collection.readOnly; @@ -154,10 +147,10 @@ export class CollectionView implements View, ITreeNodeObject { try { view.name = await encryptService.decryptString(new EncString(collection.name), orgKey); } catch (e) { - view.name = "[error: cannot decrypt]"; // Note: This should be replaced by the owning team with appropriate, domain-specific behavior. // eslint-disable-next-line no-console console.error("[CollectionView] Error decrypting collection name", e); + throw e; } view.externalId = collection.externalId;