diff --git a/apps/desktop/src/app/app.component.ts b/apps/desktop/src/app/app.component.ts index b5c34cc95a3..10aa7ff9eeb 100644 --- a/apps/desktop/src/app/app.component.ts +++ b/apps/desktop/src/app/app.component.ts @@ -68,6 +68,7 @@ import { CipherService } from "@bitwarden/common/vault/abstractions/cipher.servi import { InternalFolderService } from "@bitwarden/common/vault/abstractions/folder/folder.service.abstraction"; import { SearchService } from "@bitwarden/common/vault/abstractions/search.service"; import { CipherType } from "@bitwarden/common/vault/enums"; +import { RestrictedItemTypesService } from "@bitwarden/common/vault/services/restricted-item-types.service"; import { DialogRef, DialogService, ToastOptions, ToastService } from "@bitwarden/components"; import { CredentialGeneratorHistoryDialogComponent } from "@bitwarden/generator-components"; import { KeyService, BiometricStateService } from "@bitwarden/key-management"; @@ -172,6 +173,7 @@ export class AppComponent implements OnInit, OnDestroy { private userDecryptionOptionsService: UserDecryptionOptionsServiceAbstraction, private readonly destroyRef: DestroyRef, private readonly documentLangSetter: DocumentLangSetter, + private restrictedItemTypesService: RestrictedItemTypesService, ) { this.deviceTrustToastService.setupListeners$.pipe(takeUntilDestroyed()).subscribe(); @@ -523,10 +525,12 @@ export class AppComponent implements OnInit, OnDestroy { private async updateAppMenu() { let updateRequest: MenuUpdateRequest; const stateAccounts = await firstValueFrom(this.accountService.accounts$); + if (stateAccounts == null || Object.keys(stateAccounts).length < 1) { updateRequest = { accounts: null, activeUserId: null, + restrictedCipherTypes: null, }; } else { const accounts: { [userId: string]: MenuAccount } = {}; @@ -557,6 +561,9 @@ export class AppComponent implements OnInit, OnDestroy { activeUserId: await firstValueFrom( this.accountService.activeAccount$.pipe(map((a) => a?.id)), ), + restrictedCipherTypes: ( + await firstValueFrom(this.restrictedItemTypesService.restricted$) + ).map((restrictedItems) => restrictedItems.cipherType), }; } diff --git a/apps/desktop/src/main/menu/menu.file.ts b/apps/desktop/src/main/menu/menu.file.ts index 19ba5e99792..a8cdb347a77 100644 --- a/apps/desktop/src/main/menu/menu.file.ts +++ b/apps/desktop/src/main/menu/menu.file.ts @@ -2,6 +2,7 @@ import { BrowserWindow, MenuItemConstructorOptions } from "electron"; import { I18nService } from "@bitwarden/common/platform/abstractions/i18n.service"; import { MessagingService } from "@bitwarden/common/platform/abstractions/messaging.service"; +import { CipherType } from "@bitwarden/sdk-internal"; import { isMac, isMacAppStore } from "../../utils"; import { UpdaterMain } from "../updater.main"; @@ -54,6 +55,7 @@ export class FileMenu extends FirstMenu implements IMenubarMenu { accounts: { [userId: string]: MenuAccount }, isLocked: boolean, isLockable: boolean, + private restrictedCipherTypes: CipherType[], ) { super(i18nService, messagingService, updater, window, accounts, isLocked, isLockable); } @@ -77,6 +79,23 @@ export class FileMenu extends FirstMenu implements IMenubarMenu { }; } + private mapMenuItemToCipherType(itemId: string): CipherType { + switch (itemId) { + case "typeLogin": + return CipherType.Login; + case "typeCard": + return CipherType.Card; + case "typeIdentity": + return CipherType.Identity; + case "typeSecureNote": + return CipherType.SecureNote; + case "typeSshKey": + return CipherType.SshKey; + default: + throw new Error(`Unknown menu item id: ${itemId}`); + } + } + private get addNewItemSubmenu(): MenuItemConstructorOptions[] { return [ { @@ -109,7 +128,11 @@ export class FileMenu extends FirstMenu implements IMenubarMenu { click: () => this.sendMessage("newSshKey"), accelerator: "CmdOrCtrl+Shift+K", }, - ]; + ].filter((item) => { + return !this.restrictedCipherTypes?.some( + (restrictedType) => restrictedType === this.mapMenuItemToCipherType(item.id), + ); + }); } private get addNewFolder(): MenuItemConstructorOptions { diff --git a/apps/desktop/src/main/menu/menu.updater.ts b/apps/desktop/src/main/menu/menu.updater.ts index 6f82a78384f..8b658049de7 100644 --- a/apps/desktop/src/main/menu/menu.updater.ts +++ b/apps/desktop/src/main/menu/menu.updater.ts @@ -1,8 +1,10 @@ // FIXME: Update this file to be type safe and remove this and next line // @ts-strict-ignore +import { CipherType } from "@bitwarden/common/vault/enums"; export class MenuUpdateRequest { - activeUserId: string; - accounts: { [userId: string]: MenuAccount }; + activeUserId: string | null; + accounts: { [userId: string]: MenuAccount } | null; + restrictedCipherTypes: CipherType[] | null; } export class MenuAccount { diff --git a/apps/desktop/src/main/menu/menubar.ts b/apps/desktop/src/main/menu/menubar.ts index 825afdaa1e8..8ac3a084d95 100644 --- a/apps/desktop/src/main/menu/menubar.ts +++ b/apps/desktop/src/main/menu/menubar.ts @@ -83,6 +83,7 @@ export class Menubar { updateRequest?.accounts, isLocked, isLockable, + updateRequest?.restrictedCipherTypes, ), new EditMenu(i18nService, messagingService, isLocked), new ViewMenu(i18nService, messagingService, isLocked),