Skip to content

[PM-37807] Implement VaultBatchBarComponent on organization vault#21345

Open
gbubemismith wants to merge 6 commits into
mainfrom
vault/PM-37807
Open

[PM-37807] Implement VaultBatchBarComponent on organization vault#21345
gbubemismith wants to merge 6 commits into
mainfrom
vault/PM-37807

Conversation

@gbubemismith

@gbubemismith gbubemismith commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

🎟️ Tracking

https://bitwarden.atlassian.net/browse/PM-37807

📔 Objective

Enable admin console users to perform bulk collection operations through the floating batch bar.

📸 Screenshots

Screen.Recording.2026-06-17.at.14.46.46.mov

@gbubemismith gbubemismith marked this pull request as ready for review June 17, 2026 19:01
@gbubemismith gbubemismith requested review from a team as code owners June 17, 2026 19:01
@github-actions

github-actions Bot commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

🤖 Bitwarden Claude Code Review

Overall Assessment: APPROVE

Reviewed the wiring of VaultBatchBarComponent into the admin console organization vault (vault.component.ts, vault-v2.component.ts), the new bulkEditCollectionAccess flow in VaultBatchBarService, the new web dialog adapter and injection token, and the selectability changes in vault-items.component.ts. The change is feature-flagged behind PM37785_VaultBatchBar, follows the existing adapter/SafeInjectionToken pattern used for the assign-collections and bulk-delete dialogs, and is well covered by unit tests.

Code Review Details

No blocking findings.

Notes confirmed during review:

  • The editAccess and missingPermissions i18n keys exist in apps/web/src/locales/en/messages.json, the only app consuming VaultBatchActionComponent.
  • Admin permission handling is correct: org-vault collections resolve to CollectionAdminView, so canEdit(org) honors admin overrides.
  • The Unassigned pseudo-collection cannot reach bulkEditCollectionAccess because canEditCollection/canDeleteCollection exclude it, so it is never selectable.
  • The selected.lengthselectedCiphers.length change in canAssignToCollections and the organization?.canEditAllCiphers null-safety fix are correct and test-covered.
  • New combineLatest subscriptions are torn down via takeUntil(this.destroy$).

@codecov

codecov Bot commented Jun 18, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 67.08861% with 26 lines in your changes missing coverage. Please review.
✅ Project coverage is 49.21%. Comparing base (c59ef9b) to head (b239a7b).
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
...le/organizations/collections/vault-v2.component.ts 0.00% 13 Missing ⚠️
libs/vault/src/services/vault-batch-bar.service.ts 76.00% 3 Missing and 3 partials ⚠️
.../bulk-edit-collection-access-web-dialog.adapter.ts 60.00% 4 Missing ⚠️
...lt/components/vault-items/vault-items.component.ts 0.00% 2 Missing ⚠️
...nsole/organizations/collections/vault.component.ts 93.33% 1 Missing ⚠️
Additional details and impacted files
@@           Coverage Diff           @@
##             main   #21345   +/-   ##
=======================================
  Coverage   49.20%   49.21%           
=======================================
  Files        4074     4076    +2     
  Lines      127814   127884   +70     
  Branches    19566    19574    +8     
=======================================
+ Hits        62897    62943   +46     
- Misses      60264    60280   +16     
- Partials     4653     4661    +8     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@BTreston BTreston left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 questions about the interface for the config of this batch bar service

Comment on lines +413 to +422
combineLatest([this.organization$, this.allCollections$, this.ciphers$])
.pipe(takeUntil(this.destroy$))
.subscribe(([organization, allCollections, ciphers]) => {
this.vaultBatchBarService.setConfig({
isOrgVault: true,
organization,
allCollections,
hasCiphers: ciphers.length > 0,
});
});

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why do we need isOrgVault? would organization being Organization | undefined not satisfy that? Also it feels a bit backward to be managing the service state from the component. I think it would be clearer to derive the config internally in VaultBatchBarService from our existing services (OrganizationService and VaultCollectionService). I understand that ciphers$ here is still managed internally by our component and not a dedicated service which, complicates this. But a lift and shift of the ciphers logic might just resolve that. Any thoughts on that? We should really strive for truly presentational components, and all the business logic should live in the services.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

isOrgVault feeds cipherAuthorizationService.canDeleteCipher$/canRestoreCipher$ which checks if an action is performed from admin console, it gates the elevated admin permission paths. That's why I'd keep it explicit rather than infer it from organization != null; on the individual vault, we always go through the member path, even for ciphers that belong to an org. So presence of an organization isn't the same question as is this an admin-console action?. I'll prefer we keep this separate

@gbubemismith gbubemismith requested a review from BTreston June 19, 2026 14:17
@sonarqubecloud

Copy link
Copy Markdown

@BTreston BTreston left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM 🌱 The component managing the service's state is not ideal, but non blocking. We can revisit this tech-debt on the AC side in the future as we continue to clean up our org vault component.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants