diff --git a/apps/web/src/app/admin-console/organizations/layouts/organization-layout.component.html b/apps/web/src/app/admin-console/organizations/layouts/organization-layout.component.html index aaba492dff8..a42e8236228 100644 --- a/apps/web/src/app/admin-console/organizations/layouts/organization-layout.component.html +++ b/apps/web/src/app/admin-console/organizations/layouts/organization-layout.component.html @@ -4,7 +4,7 @@ ; hideNewOrgButton$: Observable; organizationIsUnmanaged$: Observable; - isAccessIntelligenceFeatureEnabled = false; private _destroy = new Subject(); @@ -67,10 +65,6 @@ export class OrganizationLayoutComponent implements OnInit, OnDestroy { async ngOnInit() { document.body.classList.remove("layout_frontend"); - this.isAccessIntelligenceFeatureEnabled = await this.configService.getFeatureFlag( - FeatureFlag.AccessIntelligence, - ); - this.organization$ = this.route.params .pipe(takeUntil(this._destroy)) .pipe(map((p) => p.organizationId)) @@ -139,4 +133,8 @@ export class OrganizationLayoutComponent implements OnInit, OnDestroy { getReportTabLabel(organization: Organization): string { return organization.useEvents ? "reporting" : "reports"; } + + canShowAccessIntelligenceTab(organization: Organization): boolean { + return organization.useRiskInsights; + } } diff --git a/apps/web/src/app/tools/access-intelligence/access-intelligence-routing.module.ts b/apps/web/src/app/tools/access-intelligence/access-intelligence-routing.module.ts index c13cc0efae8..91a8f012787 100644 --- a/apps/web/src/app/tools/access-intelligence/access-intelligence-routing.module.ts +++ b/apps/web/src/app/tools/access-intelligence/access-intelligence-routing.module.ts @@ -1,15 +1,14 @@ import { NgModule } from "@angular/core"; import { RouterModule, Routes } from "@angular/router"; -import { canAccessFeature } from "@bitwarden/angular/platform/guard/feature-flag.guard"; -import { FeatureFlag } from "@bitwarden/common/enums/feature-flag.enum"; +import { organizationPermissionsGuard } from "../../admin-console/organizations/guards/org-permissions.guard"; import { RiskInsightsComponent } from "./risk-insights.component"; const routes: Routes = [ { path: "risk-insights", - canActivate: [canAccessFeature(FeatureFlag.AccessIntelligence)], + canActivate: [organizationPermissionsGuard((o) => o.useRiskInsights)], component: RiskInsightsComponent, data: { titleId: "RiskInsights", diff --git a/libs/common/src/admin-console/models/data/organization.data.spec.ts b/libs/common/src/admin-console/models/data/organization.data.spec.ts index 0b3d512817b..4983594c947 100644 --- a/libs/common/src/admin-console/models/data/organization.data.spec.ts +++ b/libs/common/src/admin-console/models/data/organization.data.spec.ts @@ -58,6 +58,7 @@ describe("ORGANIZATIONS state", () => { allowAdminAccessToAllCollectionItems: false, familySponsorshipLastSyncDate: new Date(), userIsManagedByOrganization: false, + useRiskInsights: false, }, }; const result = sut.deserializer(JSON.parse(JSON.stringify(expectedResult))); diff --git a/libs/common/src/admin-console/models/data/organization.data.ts b/libs/common/src/admin-console/models/data/organization.data.ts index 0c0dedad256..5b1be5c7a11 100644 --- a/libs/common/src/admin-console/models/data/organization.data.ts +++ b/libs/common/src/admin-console/models/data/organization.data.ts @@ -58,6 +58,7 @@ export class OrganizationData { limitCollectionCreationDeletion: boolean; allowAdminAccessToAllCollectionItems: boolean; userIsManagedByOrganization: boolean; + useRiskInsights: boolean; constructor( response?: ProfileOrganizationResponse, @@ -120,6 +121,7 @@ export class OrganizationData { this.limitCollectionCreationDeletion = response.limitCollectionCreationDeletion; this.allowAdminAccessToAllCollectionItems = response.allowAdminAccessToAllCollectionItems; this.userIsManagedByOrganization = response.userIsManagedByOrganization; + this.useRiskInsights = response.useRiskInsights; this.isMember = options.isMember; this.isProviderUser = options.isProviderUser; diff --git a/libs/common/src/admin-console/models/domain/organization.ts b/libs/common/src/admin-console/models/domain/organization.ts index 070617b9e5f..335fdce2edc 100644 --- a/libs/common/src/admin-console/models/domain/organization.ts +++ b/libs/common/src/admin-console/models/domain/organization.ts @@ -83,6 +83,7 @@ export class Organization { * matches one of the verified domains of that organization, and the user is a member of it. */ userIsManagedByOrganization: boolean; + useRiskInsights: boolean; constructor(obj?: OrganizationData) { if (obj == null) { @@ -141,6 +142,7 @@ export class Organization { this.limitCollectionCreationDeletion = obj.limitCollectionCreationDeletion; this.allowAdminAccessToAllCollectionItems = obj.allowAdminAccessToAllCollectionItems; this.userIsManagedByOrganization = obj.userIsManagedByOrganization; + this.useRiskInsights = obj.useRiskInsights; } get canAccess() { diff --git a/libs/common/src/admin-console/models/response/organization.response.ts b/libs/common/src/admin-console/models/response/organization.response.ts index aaa28e48a5c..da66d8e724b 100644 --- a/libs/common/src/admin-console/models/response/organization.response.ts +++ b/libs/common/src/admin-console/models/response/organization.response.ts @@ -37,6 +37,7 @@ export class OrganizationResponse extends BaseResponse { // Deprecated: https://bitwarden.atlassian.net/browse/PM-10863 limitCollectionCreationDeletion: boolean; allowAdminAccessToAllCollectionItems: boolean; + useRiskInsights: boolean; constructor(response: any) { super(response); @@ -81,5 +82,6 @@ export class OrganizationResponse extends BaseResponse { this.allowAdminAccessToAllCollectionItems = this.getResponseProperty( "AllowAdminAccessToAllCollectionItems", ); + this.useRiskInsights = this.getResponseProperty("UseRiskInsights"); } } diff --git a/libs/common/src/admin-console/models/response/profile-organization.response.ts b/libs/common/src/admin-console/models/response/profile-organization.response.ts index 4d9366e6627..542c8aaded7 100644 --- a/libs/common/src/admin-console/models/response/profile-organization.response.ts +++ b/libs/common/src/admin-console/models/response/profile-organization.response.ts @@ -55,6 +55,7 @@ export class ProfileOrganizationResponse extends BaseResponse { limitCollectionCreationDeletion: boolean; allowAdminAccessToAllCollectionItems: boolean; userIsManagedByOrganization: boolean; + useRiskInsights: boolean; constructor(response: any) { super(response); @@ -123,5 +124,6 @@ export class ProfileOrganizationResponse extends BaseResponse { "AllowAdminAccessToAllCollectionItems", ); this.userIsManagedByOrganization = this.getResponseProperty("UserIsManagedByOrganization"); + this.useRiskInsights = this.getResponseProperty("UseRiskInsights"); } } diff --git a/libs/common/src/enums/feature-flag.enum.ts b/libs/common/src/enums/feature-flag.enum.ts index 69298db654e..9a501073cfe 100644 --- a/libs/common/src/enums/feature-flag.enum.ts +++ b/libs/common/src/enums/feature-flag.enum.ts @@ -31,7 +31,6 @@ export enum FeatureFlag { CipherKeyEncryption = "cipher-key-encryption", VerifiedSsoDomainEndpoint = "pm-12337-refactor-sso-details-endpoint", PM11901_RefactorSelfHostingLicenseUploader = "PM-11901-refactor-self-hosting-license-uploader", - AccessIntelligence = "pm-13227-access-intelligence", Pm13322AddPolicyDefinitions = "pm-13322-add-policy-definitions", LimitCollectionCreationDeletionSplit = "pm-10863-limit-collection-creation-deletion-split", CriticalApps = "pm-14466-risk-insights-critical-application", @@ -80,10 +79,9 @@ export const DefaultFeatureFlagValue = { [FeatureFlag.CipherKeyEncryption]: FALSE, [FeatureFlag.VerifiedSsoDomainEndpoint]: FALSE, [FeatureFlag.PM11901_RefactorSelfHostingLicenseUploader]: FALSE, - [FeatureFlag.AccessIntelligence]: FALSE, [FeatureFlag.Pm13322AddPolicyDefinitions]: FALSE, [FeatureFlag.LimitCollectionCreationDeletionSplit]: FALSE, - [FeatureFlag.CriticalApps]: FALSE, + [FeatureFlag.CriticalApps]: true, [FeatureFlag.TrialPaymentOptional]: FALSE, [FeatureFlag.SecurityTasks]: FALSE, [FeatureFlag.NewDeviceVerificationTemporaryDismiss]: FALSE,