From 07abd01f06e11665cb4142b80abf9a1f21d5e419 Mon Sep 17 00:00:00 2001 From: Asher Date: Tue, 30 Jul 2024 09:18:11 -0800 Subject: [PATCH 01/19] s/readAllUsers/viewAllUsers Seems like all the other frontend variables use the `view` syntax. Arguably we should use `read` to match the backend, but `view` does seem more UI-like. --- site/src/contexts/auth/permissions.tsx | 4 ++-- site/src/modules/dashboard/Navbar/Navbar.tsx | 2 +- site/src/testHelpers/entities.ts | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/site/src/contexts/auth/permissions.tsx b/site/src/contexts/auth/permissions.tsx index 6e39286edbbaa..443d5acc3b7d2 100644 --- a/site/src/contexts/auth/permissions.tsx +++ b/site/src/contexts/auth/permissions.tsx @@ -1,5 +1,5 @@ export const checks = { - readAllUsers: "readAllUsers", + viewAllUsers: "viewAllUsers", updateUsers: "updateUsers", createUser: "createUser", createTemplates: "createTemplates", @@ -15,7 +15,7 @@ export const checks = { } as const; export const permissionsToCheck = { - [checks.readAllUsers]: { + [checks.viewAllUsers]: { object: { resource_type: "user", }, diff --git a/site/src/modules/dashboard/Navbar/Navbar.tsx b/site/src/modules/dashboard/Navbar/Navbar.tsx index b480f6a20891c..51ef2b1b5235a 100644 --- a/site/src/modules/dashboard/Navbar/Navbar.tsx +++ b/site/src/modules/dashboard/Navbar/Navbar.tsx @@ -21,7 +21,7 @@ export const Navbar: FC = () => { const canViewOrganizations = featureVisibility.multiple_organizations && experiments.includes("multi-organization"); - const canViewAllUsers = Boolean(permissions.readAllUsers); + const canViewAllUsers = Boolean(permissions.viewAllUsers); const proxyContextValue = useProxy(); const canViewHealth = canViewDeployment; diff --git a/site/src/testHelpers/entities.ts b/site/src/testHelpers/entities.ts index 0254093481f0d..615c71776ca8d 100644 --- a/site/src/testHelpers/entities.ts +++ b/site/src/testHelpers/entities.ts @@ -2477,7 +2477,7 @@ export const MockPermissions: Permissions = { createUser: true, deleteTemplates: true, updateTemplates: true, - readAllUsers: true, + viewAllUsers: true, updateUsers: true, viewAuditLog: true, viewDeploymentValues: true, From bd52becfe1b9c2a9963f5f3883f23430759af8cf Mon Sep 17 00:00:00 2001 From: Asher Date: Tue, 30 Jul 2024 09:43:25 -0800 Subject: [PATCH 02/19] Check license for organizations All the checks now require both the experiment and license. I also renamed the variable canViewOrganizations everywhere for consistency. --- site/src/pages/AuditPage/AuditPage.tsx | 13 +++++++------ .../DeploySettingsPage/DeploySettingsLayout.tsx | 7 +++++-- .../GroupsPage/GroupsPage.tsx | 17 ++++++----------- .../ManagementSettingsLayout.tsx | 7 +++++-- site/src/pages/UsersPage/UsersLayout.tsx | 9 +++++---- site/src/pages/UsersPage/UsersPage.tsx | 12 ++++++------ site/src/pages/UsersPage/UsersPageView.tsx | 6 +++--- 7 files changed, 37 insertions(+), 34 deletions(-) diff --git a/site/src/pages/AuditPage/AuditPage.tsx b/site/src/pages/AuditPage/AuditPage.tsx index ed81e36f19ded..34eff1cc899b0 100644 --- a/site/src/pages/AuditPage/AuditPage.tsx +++ b/site/src/pages/AuditPage/AuditPage.tsx @@ -17,10 +17,9 @@ import { import { AuditPageView } from "./AuditPageView"; const AuditPage: FC = () => { - const { audit_log: isAuditLogVisible } = useFeatureVisibility(); + const feats = useFeatureVisibility(); const { experiments } = useDashboard(); const location = useLocation(); - const isMultiOrg = experiments.includes("multi-organization"); /** * There is an implicit link between auditsQuery and filter via the @@ -75,7 +74,9 @@ const AuditPage: FC = () => { // TODO: Once multi-org is stable, we should place this redirect into the // router directly, if we still need to maintain it (for users who are // typing the old URL manually or have it bookmarked). - if (isMultiOrg && location.pathname !== "/deployment/audit") { + const canViewOrganizations = + feats.multiple_organizations && experiments.includes("multi-organization"); + if (canViewOrganizations && location.pathname !== "/deployment/audit") { return ; } @@ -88,10 +89,10 @@ const AuditPage: FC = () => { { user: userMenu, action: actionMenu, resourceType: resourceTypeMenu, - organization: isMultiOrg ? organizationsMenu : undefined, + organization: canViewOrganizations ? organizationsMenu : undefined, }, }} /> diff --git a/site/src/pages/DeploySettingsPage/DeploySettingsLayout.tsx b/site/src/pages/DeploySettingsPage/DeploySettingsLayout.tsx index bed83a9ee820f..68fb3adc17ddd 100644 --- a/site/src/pages/DeploySettingsPage/DeploySettingsLayout.tsx +++ b/site/src/pages/DeploySettingsPage/DeploySettingsLayout.tsx @@ -9,6 +9,7 @@ import { Stack } from "components/Stack/Stack"; import { useAuthenticated } from "contexts/auth/RequireAuth"; import { RequirePermission } from "contexts/auth/RequirePermission"; import { useDashboard } from "modules/dashboard/useDashboard"; +import { useFeatureVisibility } from "modules/dashboard/useFeatureVisibility"; import { ManagementSettingsLayout } from "pages/ManagementSettingsPage/ManagementSettingsLayout"; import { Sidebar } from "./Sidebar"; @@ -33,9 +34,11 @@ export const useDeploySettings = (): DeploySettingsContextValue => { export const DeploySettingsLayout: FC = () => { const { experiments } = useDashboard(); - const multiOrgExperimentEnabled = experiments.includes("multi-organization"); + const feats = useFeatureVisibility(); + const canViewOrganizations = + feats.multiple_organizations && experiments.includes("multi-organization"); - return multiOrgExperimentEnabled ? ( + return canViewOrganizations ? ( ) : ( diff --git a/site/src/pages/ManagementSettingsPage/GroupsPage/GroupsPage.tsx b/site/src/pages/ManagementSettingsPage/GroupsPage/GroupsPage.tsx index d8c756645363d..cdba4273b7bfe 100644 --- a/site/src/pages/ManagementSettingsPage/GroupsPage/GroupsPage.tsx +++ b/site/src/pages/ManagementSettingsPage/GroupsPage/GroupsPage.tsx @@ -24,10 +24,7 @@ import GroupsPageView from "./GroupsPageView"; export const GroupsPage: FC = () => { const { permissions } = useAuthenticated(); const { createGroup: canCreateGroup } = permissions; - const { - multiple_organizations: organizationsEnabled, - template_rbac: isTemplateRBACEnabled, - } = useFeatureVisibility(); + const feats = useFeatureVisibility(); const { experiments } = useDashboard(); const location = useLocation(); const { organization = "default" } = useParams() as { organization: string }; @@ -42,11 +39,9 @@ export const GroupsPage: FC = () => { } }, [groupsQuery.error]); - if ( - organizationsEnabled && - experiments.includes("multi-organization") && - location.pathname === "/deployment/groups" - ) { + const canViewOrganizations = + feats.multiple_organizations && experiments.includes("multi-organization"); + if (canViewOrganizations && location.pathname === "/deployment/groups") { const defaultName = getOrganizationNameByDefault(organizations) ?? "default"; return ; @@ -61,7 +56,7 @@ export const GroupsPage: FC = () => { - {canCreateGroup && isTemplateRBACEnabled && ( + {canCreateGroup && feats.template_rbac && ( )} - {canCreateGroup && isTemplateRBACEnabled && ( + {canCreateGroup && feats.template_rbac && ( )} - {canCreateGroup && feats.template_rbac && ( + {permissionsQuery.data?.createGroup && feats.template_rbac && ( )} - {permissionsQuery.data?.createGroup && feats.template_rbac && ( + {permissions.createGroup && feats.template_rbac && (