@openedx/frontend-app-admin-console 1.0.0-alpha.7 → 1.0.0-alpha.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (26) hide show
  1. package/dist/authz-module/audit-user/index.js +1 -1
  2. package/dist/authz-module/audit-user/index.js.map +1 -1
  3. package/dist/authz-module/authz-home/index.js +1 -1
  4. package/dist/authz-module/authz-home/index.js.map +1 -1
  5. package/dist/authz-module/components/AuthZLayout.js +1 -1
  6. package/dist/authz-module/components/AuthZLayout.js.map +1 -1
  7. package/dist/authz-module/components/AuthZTitle.d.ts +2 -1
  8. package/dist/authz-module/components/AuthZTitle.js +2 -2
  9. package/dist/authz-module/components/AuthZTitle.js.map +1 -1
  10. package/dist/authz-module/components/PermissionTable.js +1 -1
  11. package/dist/authz-module/components/PermissionTable.js.map +1 -1
  12. package/dist/authz-module/components/TableControlBar/MultipleChoiceFilter.d.ts +1 -1
  13. package/dist/authz-module/components/TableControlBar/MultipleChoiceFilter.js +4 -3
  14. package/dist/authz-module/components/TableControlBar/MultipleChoiceFilter.js.map +1 -1
  15. package/dist/authz-module/components/TableControlBar/SearchFilter.d.ts +2 -1
  16. package/dist/authz-module/components/TableControlBar/SearchFilter.js +2 -1
  17. package/dist/authz-module/components/TableControlBar/SearchFilter.js.map +1 -1
  18. package/dist/authz-module/components/TableControlBar/types.d.ts +1 -0
  19. package/dist/authz-module/components/TableControlBar/types.js.map +1 -1
  20. package/dist/authz-module/index.scss +28 -2
  21. package/dist/authz-module/roles-permissions/RolesPermissions.js +2 -2
  22. package/dist/authz-module/roles-permissions/RolesPermissions.js.map +1 -1
  23. package/dist/authz-module/utils.d.ts +1 -0
  24. package/dist/authz-module/utils.js +2 -0
  25. package/dist/authz-module/utils.js.map +1 -1
  26. package/package.json +1 -1
@@ -181,7 +181,7 @@ const AuditUserPage = () => {
181
181
  rolesCount: count || 0,
182
182
  } }), _jsx(AuthZLayout, { navLinks: navLinks, activeLabel: (user === null || user === void 0 ? void 0 : user.username) || '', pageTitle: (user === null || user === void 0 ? void 0 : user.username) || '', pageSubtitle: (user === null || user === void 0 ? void 0 : user.email) || '', actions: [
183
183
  _jsx(AddRoleButton, { presetUsername: user === null || user === void 0 ? void 0 : user.username }, "add-role-button"),
184
- ], children: _jsx("div", { className: "page-band py-5", children: _jsxs(DataTable, { isPaginated: true, isFilterable: true, isSortable: true, manualPagination: true, data: rowsWithPermissions, manualFilters: true, manualSortBy: true, fetchData: fetchData, itemCount: count, pageCount: pageCount, initialState: { pageSize: TABLE_DEFAULT_PAGE_SIZE }, additionalColumns: additionalColumns, columns: columns, isLoading: isLoadingUserAssignments, isExpandable: true, renderRowSubComponent: ({ row }) => (_jsx(UserPermissions, { row: row })), children: [_jsx(TableControlBar, { onFilterChange: setColumnsWithFiltersApplied }), _jsx(DataTable.Table, {}), _jsx(TableFooter, {})] }) }) })] }));
184
+ ], showDivider: true, children: _jsx("div", { className: "page-band py-3", children: _jsxs(DataTable, { isPaginated: true, isFilterable: true, isSortable: true, manualPagination: true, data: rowsWithPermissions, manualFilters: true, manualSortBy: true, fetchData: fetchData, itemCount: count, pageCount: pageCount, initialState: { pageSize: TABLE_DEFAULT_PAGE_SIZE }, additionalColumns: additionalColumns, columns: columns, isLoading: isLoadingUserAssignments, isExpandable: true, renderRowSubComponent: ({ row }) => (_jsx(UserPermissions, { row: row })), children: [_jsx(TableControlBar, { onFilterChange: setColumnsWithFiltersApplied }), _jsx(DataTable.Table, {}), _jsx(TableFooter, {})] }) }) })] }));
185
185
  };
186
186
  export default AuditUserPage;
187
187
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/authz-module/audit-user/index.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n useCallback,\n useContext, useEffect, useMemo, useState,\n} from 'react';\nimport { SiteContext, useIntl } from '@openedx/frontend-base';\nimport { DataTable } from '@openedx/paragon';\nimport TableFooter from '@src/authz-module/components/TableFooter/TableFooter';\nimport {\n AUTHZ_HOME_PATH, TABLE_DEFAULT_PAGE_SIZE,\n} from '@src/authz-module/constants';\nimport AuthZLayout from '@src/authz-module/components/AuthZLayout';\nimport { useNavigate, useParams } from 'react-router-dom';\nimport { useUserAccount, useValidateUserPermissionsNonSuspense } from '@src/data/hooks';\nimport { LIBRARY_ROLE_KEYS } from '@src/authz-module/roles-permissions';\nimport { useViewTeamPermissions } from '@src/authz-module/hooks/useViewTeamPermissions';\nimport { getHttpErrorStatus } from '@src/data/utils';\nimport baseMessages from '@src/authz-module/messages';\nimport AddRoleButton from '@src/authz-module/components/AddRoleButton';\nimport {\n OrgCell, RoleCell, ScopeCell, PermissionsCell, ViewAllPermissionsCell,\n createActionsCell,\n} from '@src/authz-module/components/TableCells';\nimport { useQuerySettings } from '@src/authz-module/hooks/useQuerySettings';\nimport { useCourseAuthoringFlag } from '@src/authz-module/hooks/useCourseAuthoringFlag';\nimport { useRevokeUserRoles, useUserAssignedRoles } from '@src/authz-module/data/hooks';\nimport type { RevokeUserRolesRequest } from '@src/authz-module/data/api';\nimport { RoleToDelete } from '@src/types';\nimport { useToastManager } from '@src/components/ToastManager/ToastManagerContext';\nimport UserPermissions from '@src/authz-module/components/UserPermissions';\nimport OrgFilter from '@src/authz-module/components/TableControlBar/OrgFilter';\nimport RolesFilter from '@src/authz-module/components/TableControlBar/RolesFilter';\nimport TableControlBar from '@src/authz-module/components/TableControlBar/TableControlBar';\nimport messages from './messages';\nimport ConfirmDeletionModal from '@src/authz-module/components/ConfirmDeletionModal';\nimport { getCellHeader, getScopeManageActionPermission } from '@src/authz-module/utils';\n\nconst AuditUserPage = () => {\n const { formatMessage } = useIntl();\n const [columnsWithFiltersApplied, setColumnsWithFiltersApplied] = useState<string[]>([]);\n const { username } = useParams();\n const { authenticatedUser } = useContext(SiteContext);\n const navigate = useNavigate();\n const {\n isLoading: isLoadingUser, data: user, isError: isErrorUser, error: errorUser,\n } = useUserAccount(username);\n const { querySettings, handleTableFetch } = useQuerySettings();\n\n const { isCourseViewAllowed } = useViewTeamPermissions();\n const { isCourseEnabled } = useCourseAuthoringFlag();\n\n const effectiveQuerySettings = useMemo(() => {\n if (isCourseViewAllowed || querySettings.roles) return querySettings;\n return { ...querySettings, roles: LIBRARY_ROLE_KEYS };\n }, [isCourseViewAllowed, querySettings]);\n\n const {\n isLoading: isLoadingUserAssignments, data: { results: userAssignments, count } = { results: [], count: 0 },\n } = useUserAssignedRoles(username, effectiveQuerySettings);\n const [roleToDelete, setRoleToDelete] = useState<RoleToDelete | null>(null);\n const [showConfirmDeletionModal, setShowConfirmDeletionModal] = useState(false);\n const {\n showToast, showErrorToast, Bold, Br,\n } = useToastManager();\n const { mutate: revokeUserRoles, isPending: isRevokingUserRolePending } = useRevokeUserRoles();\n\n const deletePermissions = useMemo(() => {\n const uniqueScopes = [...new Set(userAssignments.map(assignment => assignment.scope))];\n return uniqueScopes.map(scope => getScopeManageActionPermission(scope));\n }, [userAssignments]);\n\n const {\n data: permissionsToManageScope,\n } = useValidateUserPermissionsNonSuspense(deletePermissions);\n\n const rowsWithPermissions = useMemo(() => {\n if (!permissionsToManageScope) return userAssignments;\n\n return userAssignments.map(assignment => {\n const canManageScope = permissionsToManageScope.some(\n permission => permission.scope === assignment.scope && permission.allowed,\n );\n return {\n ...assignment,\n canManageScope,\n };\n });\n }, [userAssignments, permissionsToManageScope]);\n\n const fetchData = useMemo(() => handleTableFetch, [handleTableFetch]);\n\n useEffect(() => {\n if (!user && !isLoadingUser) {\n if (!isErrorUser || getHttpErrorStatus(errorUser) === 404) {\n navigate(AUTHZ_HOME_PATH);\n }\n }\n }, [user, isLoadingUser, navigate, isErrorUser, errorUser]);\n\n const handleShowConfirmDeletionModal = useCallback((role: RoleToDelete) => {\n if (isRevokingUserRolePending) return;\n\n setRoleToDelete(role);\n setShowConfirmDeletionModal(true);\n }, [isRevokingUserRolePending]);\n\n const navLinks = useMemo(() => [\n {\n label: formatMessage(baseMessages['authz.management.home.nav.link']),\n to: AUTHZ_HOME_PATH,\n },\n ], [formatMessage]);\n\n const additionalColumns = useMemo(() => [\n {\n id: 'view_permissions',\n Header: '',\n Cell: ViewAllPermissionsCell,\n },\n {\n id: 'action',\n Header: formatMessage(messages['authz.user.table.action.column.header']),\n Cell: createActionsCell({\n onClickDeleteButton: handleShowConfirmDeletionModal,\n isUserAuthenticatedPage: username === authenticatedUser?.username,\n isCourseEnabled,\n }),\n },\n ], [authenticatedUser?.username, formatMessage, handleShowConfirmDeletionModal, username, isCourseEnabled]);\n\n const columns = useMemo(() => [\n {\n Header: getCellHeader('role', formatMessage(messages['authz.user.table.role.column.header']), columnsWithFiltersApplied),\n accessor: 'role',\n Cell: RoleCell,\n filter: 'includesValue',\n Filter: RolesFilter,\n filterButtonText: formatMessage(messages['authz.user.table.role.column.header']),\n filterOrder: 2,\n },\n {\n Header: getCellHeader('org', formatMessage(messages['authz.user.table.organization.column.header']), columnsWithFiltersApplied),\n accessor: 'org',\n Cell: OrgCell,\n filter: 'includesValue',\n Filter: OrgFilter,\n filterButtonText: formatMessage(messages['authz.user.table.organization.column.header']),\n filterOrder: 1,\n },\n {\n Header: getCellHeader('scope', formatMessage(messages['authz.user.table.scope.column.header']), columnsWithFiltersApplied),\n accessor: 'scope',\n Cell: ScopeCell,\n disableFilters: true,\n\n },\n {\n Header: formatMessage(messages['authz.user.table.permissions.column.header']),\n Cell: PermissionsCell,\n disableFilters: true,\n disableSortBy: true,\n },\n ], [formatMessage, columnsWithFiltersApplied]);\n\n const pageCount = Math.ceil(count / TABLE_DEFAULT_PAGE_SIZE);\n\n const handleCloseConfirmDeletionModal = () => {\n setRoleToDelete(null);\n setShowConfirmDeletionModal(false);\n };\n\n const handleRevokeUserRole = () => {\n if (!user || !roleToDelete) return;\n\n const data = {\n users: user.username,\n role: roleToDelete.role,\n scope: roleToDelete.scope,\n };\n\n const runRevokeRole = (variables: { data: RevokeUserRolesRequest }) => {\n const variablesData = {\n data: {\n ...variables.data,\n querySettings,\n },\n\n };\n revokeUserRoles(variablesData, {\n onSuccess: (response) => {\n const { errors } = response;\n\n if (errors.length) {\n showToast({\n type: 'error',\n message: formatMessage(\n baseMessages['authz.team.toast.default.error.message'],\n { Bold, Br },\n ),\n });\n return;\n }\n\n const remainingRolesCount = count ? count - 1 : 0;\n showToast({\n message: formatMessage(\n baseMessages['authz.team.remove.user.toast.success.description'],\n {\n role: roleToDelete.name ?? roleToDelete.role,\n rolesCount: remainingRolesCount,\n },\n ),\n type: 'success',\n });\n handleCloseConfirmDeletionModal();\n if (remainingRolesCount === 0) {\n navigate(AUTHZ_HOME_PATH);\n }\n },\n onError: (error, retryVariables) => {\n showErrorToast(error, () => runRevokeRole(retryVariables));\n },\n });\n };\n\n runRevokeRole({ data });\n };\n\n return (\n <>\n <ConfirmDeletionModal\n isOpen={showConfirmDeletionModal}\n close={handleCloseConfirmDeletionModal}\n onSave={handleRevokeUserRole}\n isDeleting={isRevokingUserRolePending}\n context={{\n userName: user?.username || '',\n scope: roleToDelete?.scope || '',\n role: roleToDelete?.role || '',\n name: roleToDelete?.name || '',\n rolesCount: count || 0,\n }}\n />\n <AuthZLayout\n navLinks={navLinks}\n activeLabel={user?.username || ''}\n pageTitle={user?.username || ''}\n pageSubtitle={user?.email || ''}\n actions={\n [\n <AddRoleButton presetUsername={user?.username} key=\"add-role-button\" />,\n ]\n }\n >\n <div className=\"page-band py-5\">\n <DataTable\n isPaginated\n isFilterable\n isSortable\n manualPagination\n data={rowsWithPermissions}\n manualFilters\n manualSortBy\n fetchData={fetchData}\n itemCount={count}\n pageCount={pageCount}\n initialState={{ pageSize: TABLE_DEFAULT_PAGE_SIZE }}\n additionalColumns={additionalColumns}\n columns={columns}\n isLoading={isLoadingUserAssignments}\n isExpandable\n renderRowSubComponent={({ row }) => (\n <UserPermissions row={row} />\n )}\n >\n <TableControlBar onFilterChange={setColumnsWithFiltersApplied} />\n <DataTable.Table />\n <TableFooter />\n </DataTable>\n </div>\n </AuthZLayout>\n </>\n );\n};\n\nexport default AuditUserPage;\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/authz-module/audit-user/index.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n useCallback,\n useContext, useEffect, useMemo, useState,\n} from 'react';\nimport { SiteContext, useIntl } from '@openedx/frontend-base';\nimport { DataTable } from '@openedx/paragon';\nimport TableFooter from '@src/authz-module/components/TableFooter/TableFooter';\nimport {\n AUTHZ_HOME_PATH, TABLE_DEFAULT_PAGE_SIZE,\n} from '@src/authz-module/constants';\nimport AuthZLayout from '@src/authz-module/components/AuthZLayout';\nimport { useNavigate, useParams } from 'react-router-dom';\nimport { useUserAccount, useValidateUserPermissionsNonSuspense } from '@src/data/hooks';\nimport { LIBRARY_ROLE_KEYS } from '@src/authz-module/roles-permissions';\nimport { useViewTeamPermissions } from '@src/authz-module/hooks/useViewTeamPermissions';\nimport { getHttpErrorStatus } from '@src/data/utils';\nimport baseMessages from '@src/authz-module/messages';\nimport AddRoleButton from '@src/authz-module/components/AddRoleButton';\nimport {\n OrgCell, RoleCell, ScopeCell, PermissionsCell, ViewAllPermissionsCell,\n createActionsCell,\n} from '@src/authz-module/components/TableCells';\nimport { useQuerySettings } from '@src/authz-module/hooks/useQuerySettings';\nimport { useCourseAuthoringFlag } from '@src/authz-module/hooks/useCourseAuthoringFlag';\nimport { useRevokeUserRoles, useUserAssignedRoles } from '@src/authz-module/data/hooks';\nimport type { RevokeUserRolesRequest } from '@src/authz-module/data/api';\nimport { RoleToDelete } from '@src/types';\nimport { useToastManager } from '@src/components/ToastManager/ToastManagerContext';\nimport UserPermissions from '@src/authz-module/components/UserPermissions';\nimport OrgFilter from '@src/authz-module/components/TableControlBar/OrgFilter';\nimport RolesFilter from '@src/authz-module/components/TableControlBar/RolesFilter';\nimport TableControlBar from '@src/authz-module/components/TableControlBar/TableControlBar';\nimport messages from './messages';\nimport ConfirmDeletionModal from '@src/authz-module/components/ConfirmDeletionModal';\nimport { getCellHeader, getScopeManageActionPermission } from '@src/authz-module/utils';\n\nconst AuditUserPage = () => {\n const { formatMessage } = useIntl();\n const [columnsWithFiltersApplied, setColumnsWithFiltersApplied] = useState<string[]>([]);\n const { username } = useParams();\n const { authenticatedUser } = useContext(SiteContext);\n const navigate = useNavigate();\n const {\n isLoading: isLoadingUser, data: user, isError: isErrorUser, error: errorUser,\n } = useUserAccount(username);\n const { querySettings, handleTableFetch } = useQuerySettings();\n\n const { isCourseViewAllowed } = useViewTeamPermissions();\n const { isCourseEnabled } = useCourseAuthoringFlag();\n\n const effectiveQuerySettings = useMemo(() => {\n if (isCourseViewAllowed || querySettings.roles) return querySettings;\n return { ...querySettings, roles: LIBRARY_ROLE_KEYS };\n }, [isCourseViewAllowed, querySettings]);\n\n const {\n isLoading: isLoadingUserAssignments, data: { results: userAssignments, count } = { results: [], count: 0 },\n } = useUserAssignedRoles(username, effectiveQuerySettings);\n const [roleToDelete, setRoleToDelete] = useState<RoleToDelete | null>(null);\n const [showConfirmDeletionModal, setShowConfirmDeletionModal] = useState(false);\n const {\n showToast, showErrorToast, Bold, Br,\n } = useToastManager();\n const { mutate: revokeUserRoles, isPending: isRevokingUserRolePending } = useRevokeUserRoles();\n\n const deletePermissions = useMemo(() => {\n const uniqueScopes = [...new Set(userAssignments.map(assignment => assignment.scope))];\n return uniqueScopes.map(scope => getScopeManageActionPermission(scope));\n }, [userAssignments]);\n\n const {\n data: permissionsToManageScope,\n } = useValidateUserPermissionsNonSuspense(deletePermissions);\n\n const rowsWithPermissions = useMemo(() => {\n if (!permissionsToManageScope) return userAssignments;\n\n return userAssignments.map(assignment => {\n const canManageScope = permissionsToManageScope.some(\n permission => permission.scope === assignment.scope && permission.allowed,\n );\n return {\n ...assignment,\n canManageScope,\n };\n });\n }, [userAssignments, permissionsToManageScope]);\n\n const fetchData = useMemo(() => handleTableFetch, [handleTableFetch]);\n\n useEffect(() => {\n if (!user && !isLoadingUser) {\n if (!isErrorUser || getHttpErrorStatus(errorUser) === 404) {\n navigate(AUTHZ_HOME_PATH);\n }\n }\n }, [user, isLoadingUser, navigate, isErrorUser, errorUser]);\n\n const handleShowConfirmDeletionModal = useCallback((role: RoleToDelete) => {\n if (isRevokingUserRolePending) return;\n\n setRoleToDelete(role);\n setShowConfirmDeletionModal(true);\n }, [isRevokingUserRolePending]);\n\n const navLinks = useMemo(() => [\n {\n label: formatMessage(baseMessages['authz.management.home.nav.link']),\n to: AUTHZ_HOME_PATH,\n },\n ], [formatMessage]);\n\n const additionalColumns = useMemo(() => [\n {\n id: 'view_permissions',\n Header: '',\n Cell: ViewAllPermissionsCell,\n },\n {\n id: 'action',\n Header: formatMessage(messages['authz.user.table.action.column.header']),\n Cell: createActionsCell({\n onClickDeleteButton: handleShowConfirmDeletionModal,\n isUserAuthenticatedPage: username === authenticatedUser?.username,\n isCourseEnabled,\n }),\n },\n ], [authenticatedUser?.username, formatMessage, handleShowConfirmDeletionModal, username, isCourseEnabled]);\n\n const columns = useMemo(() => [\n {\n Header: getCellHeader('role', formatMessage(messages['authz.user.table.role.column.header']), columnsWithFiltersApplied),\n accessor: 'role',\n Cell: RoleCell,\n filter: 'includesValue',\n Filter: RolesFilter,\n filterButtonText: formatMessage(messages['authz.user.table.role.column.header']),\n filterOrder: 2,\n },\n {\n Header: getCellHeader('org', formatMessage(messages['authz.user.table.organization.column.header']), columnsWithFiltersApplied),\n accessor: 'org',\n Cell: OrgCell,\n filter: 'includesValue',\n Filter: OrgFilter,\n filterButtonText: formatMessage(messages['authz.user.table.organization.column.header']),\n filterOrder: 1,\n },\n {\n Header: getCellHeader('scope', formatMessage(messages['authz.user.table.scope.column.header']), columnsWithFiltersApplied),\n accessor: 'scope',\n Cell: ScopeCell,\n disableFilters: true,\n\n },\n {\n Header: formatMessage(messages['authz.user.table.permissions.column.header']),\n Cell: PermissionsCell,\n disableFilters: true,\n disableSortBy: true,\n },\n ], [formatMessage, columnsWithFiltersApplied]);\n\n const pageCount = Math.ceil(count / TABLE_DEFAULT_PAGE_SIZE);\n\n const handleCloseConfirmDeletionModal = () => {\n setRoleToDelete(null);\n setShowConfirmDeletionModal(false);\n };\n\n const handleRevokeUserRole = () => {\n if (!user || !roleToDelete) return;\n\n const data = {\n users: user.username,\n role: roleToDelete.role,\n scope: roleToDelete.scope,\n };\n\n const runRevokeRole = (variables: { data: RevokeUserRolesRequest }) => {\n const variablesData = {\n data: {\n ...variables.data,\n querySettings,\n },\n\n };\n revokeUserRoles(variablesData, {\n onSuccess: (response) => {\n const { errors } = response;\n\n if (errors.length) {\n showToast({\n type: 'error',\n message: formatMessage(\n baseMessages['authz.team.toast.default.error.message'],\n { Bold, Br },\n ),\n });\n return;\n }\n\n const remainingRolesCount = count ? count - 1 : 0;\n showToast({\n message: formatMessage(\n baseMessages['authz.team.remove.user.toast.success.description'],\n {\n role: roleToDelete.name ?? roleToDelete.role,\n rolesCount: remainingRolesCount,\n },\n ),\n type: 'success',\n });\n handleCloseConfirmDeletionModal();\n if (remainingRolesCount === 0) {\n navigate(AUTHZ_HOME_PATH);\n }\n },\n onError: (error, retryVariables) => {\n showErrorToast(error, () => runRevokeRole(retryVariables));\n },\n });\n };\n\n runRevokeRole({ data });\n };\n\n return (\n <>\n <ConfirmDeletionModal\n isOpen={showConfirmDeletionModal}\n close={handleCloseConfirmDeletionModal}\n onSave={handleRevokeUserRole}\n isDeleting={isRevokingUserRolePending}\n context={{\n userName: user?.username || '',\n scope: roleToDelete?.scope || '',\n role: roleToDelete?.role || '',\n name: roleToDelete?.name || '',\n rolesCount: count || 0,\n }}\n />\n <AuthZLayout\n navLinks={navLinks}\n activeLabel={user?.username || ''}\n pageTitle={user?.username || ''}\n pageSubtitle={user?.email || ''}\n actions={\n [\n <AddRoleButton presetUsername={user?.username} key=\"add-role-button\" />,\n ]\n }\n showDivider\n >\n <div className=\"page-band py-3\">\n <DataTable\n isPaginated\n isFilterable\n isSortable\n manualPagination\n data={rowsWithPermissions}\n manualFilters\n manualSortBy\n fetchData={fetchData}\n itemCount={count}\n pageCount={pageCount}\n initialState={{ pageSize: TABLE_DEFAULT_PAGE_SIZE }}\n additionalColumns={additionalColumns}\n columns={columns}\n isLoading={isLoadingUserAssignments}\n isExpandable\n renderRowSubComponent={({ row }) => (\n <UserPermissions row={row} />\n )}\n >\n <TableControlBar onFilterChange={setColumnsWithFiltersApplied} />\n <DataTable.Table />\n <TableFooter />\n </DataTable>\n </div>\n </AuthZLayout>\n </>\n );\n};\n\nexport default AuditUserPage;\n"]}
@@ -36,7 +36,7 @@ const AuthzHome = () => {
36
36
  if (!isCourseViewAllowed && !isLibraryViewAllowed) {
37
37
  throw new Error(CustomErrors.NO_ACCESS);
38
38
  }
39
- return (_jsx(AuthZLayout, { pageTitle: pageTitle, actions: [_jsx(AddRoleButton, {}, "add-role-button")], children: _jsxs(Tabs, { variant: "tabs", defaultActiveKey: hash ? 'permissionsRoles' : 'team', className: "page-band bg-light-100", children: [_jsx(Tab, { eventKey: "team", title: intl.formatMessage(messages['authz.tabs.team']), className: "page-band py-5", children: _jsx(TeamMembersTable, { presetScope: presetScope }) }), _jsx(Tab, { id: "libraries-permissions-roles-tab", eventKey: "permissionsRoles", title: intl.formatMessage(messages['authz.tabs.permissionsRoles']), className: "page-band py-5", children: _jsx(RolesPermissions, {}) })] }) }));
39
+ return (_jsx(AuthZLayout, { pageTitle: pageTitle, actions: [_jsx(AddRoleButton, {}, "add-role-button")], children: _jsxs(Tabs, { variant: "tabs", defaultActiveKey: hash ? 'permissionsRoles' : 'team', className: "page-band bg-light-100", children: [_jsx(Tab, { eventKey: "team", title: intl.formatMessage(messages['authz.tabs.team']), className: "page-band py-3", children: _jsx(TeamMembersTable, { presetScope: presetScope }) }), _jsx(Tab, { id: "libraries-permissions-roles-tab", eventKey: "permissionsRoles", title: intl.formatMessage(messages['authz.tabs.permissionsRoles']), className: "page-band py-3", children: _jsx(RolesPermissions, {}) })] }) }));
40
40
  };
41
41
  export default AuthzHome;
42
42
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/authz-module/authz-home/index.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAC7C,OAAO,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAChE,OAAO,EAAE,gBAAgB,EAAE,MAAM,gCAAgC,CAAC;AAClE,OAAO,aAAa,MAAM,4CAA4C,CAAC;AACvE,OAAO,EAAE,sBAAsB,EAAE,MAAM,gDAAgD,CAAC;AACxF,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC9C,OAAO,WAAW,MAAM,6BAA6B,CAAC;AACtD,OAAO,gBAAgB,MAAM,sDAAsD,CAAC;AACpF,OAAO,WAAW,MAAM,0CAA0C,CAAC;AAEnE,OAAO,QAAQ,MAAM,YAAY,CAAC;AAElC,MAAM,SAAS,GAAG,GAAG,EAAE;;IACrB,MAAM,EAAE,IAAI,EAAE,GAAG,WAAW,EAAE,CAAC;IAC/B,MAAM,IAAI,GAAG,OAAO,EAAE,CAAC;IACvB,MAAM,CAAC,YAAY,CAAC,GAAG,eAAe,EAAE,CAAC;IAEzC;;MAEE;IACF,MAAM,WAAW,GAAG,CAAA,MAAA,YAAY,CAAC,GAAG,CAAC,OAAO,CAAC,0CAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,KAAI,SAAS,CAAC;IAEhF,MAAM,SAAS,GAAG,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,yBAAyB,CAAC,CAAC,CAAC;IAE1E,MAAM,EACJ,mBAAmB,EAAE,oBAAoB,EAAE,SAAS,EAAE,oBAAoB,GAC3E,GAAG,sBAAsB,EAAE,CAAC;IAE7B;;;;;;;;OAQG;IACH,IAAI,oBAAoB,EAAE,CAAC;QACzB,OAAO,KAAC,WAAW,KAAG,CAAC;IACzB,CAAC;IAED,IAAI,CAAC,mBAAmB,IAAI,CAAC,oBAAoB,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;IAC1C,CAAC;IAED,OAAO,CACL,KAAC,WAAW,IACV,SAAS,EAAE,SAAS,EACpB,OAAO,EACL,CAAC,KAAC,aAAa,MAAK,iBAAiB,CAAG,CAAC,YAG3C,MAAC,IAAI,IACH,OAAO,EAAC,MAAM,EACd,gBAAgB,EAAE,IAAI,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,MAAM,EACpD,SAAS,EAAC,wBAAwB,aAElC,KAAC,GAAG,IAAC,QAAQ,EAAC,MAAM,EAAC,KAAK,EAAE,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,iBAAiB,CAAC,CAAC,EAAE,SAAS,EAAC,gBAAgB,YACrG,KAAC,gBAAgB,IAAC,WAAW,EAAE,WAAW,GAAI,GAC1C,EACN,KAAC,GAAG,IAAC,EAAE,EAAC,iCAAiC,EAAC,QAAQ,EAAC,kBAAkB,EAAC,KAAK,EAAE,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,6BAA6B,CAAC,CAAC,EAAE,SAAS,EAAC,gBAAgB,YAClK,KAAC,gBAAgB,KAAG,GAChB,IACD,GACK,CACf,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,SAAS,CAAC","sourcesContent":["import { useIntl } from '@openedx/frontend-base';\nimport { Tab, Tabs } from '@openedx/paragon';\nimport { useLocation, useSearchParams } from 'react-router-dom';\nimport { TeamMembersTable } from '@src/authz-module/team-members';\nimport AddRoleButton from '@src/authz-module/components/AddRoleButton';\nimport { useViewTeamPermissions } from '@src/authz-module/hooks/useViewTeamPermissions';\nimport { CustomErrors } from '@src/constants';\nimport LoadingPage from '@src/components/LoadingPage';\nimport RolesPermissions from '@src/authz-module/roles-permissions/RolesPermissions';\nimport AuthZLayout from '@src/authz-module/components/AuthZLayout';\n\nimport messages from './messages';\n\nconst AuthzHome = () => {\n const { hash } = useLocation();\n const intl = useIntl();\n const [searchParams] = useSearchParams();\n\n /* In the authoring repository the scope is encoded but this is to Replace spaces with '+'\n to match URL encoding format in case the 'scope' parameter is provided with spaces instead of '+'\n */\n const presetScope = searchParams.get('scope')?.replace(/\\s/g, '+') || undefined;\n\n const pageTitle = intl.formatMessage(messages['authz.manage.page.title']);\n\n const {\n isCourseViewAllowed, isLibraryViewAllowed, isLoading: isLoadingPermissions,\n } = useViewTeamPermissions();\n\n /**\n * It gates the whole page whether the user is allowed to view the team members. If\n * the user is not allowed, an error is thrown to display the access denied message.\n *\n * Rendering is held until the check settles rather than started optimistically, so a\n * user who turns out to be denied never fires the listing and filter requests behind\n * the page. Both flags read false while it is in flight, which would otherwise deny\n * everyone for a frame.\n */\n if (isLoadingPermissions) {\n return <LoadingPage />;\n }\n\n if (!isCourseViewAllowed && !isLibraryViewAllowed) {\n throw new Error(CustomErrors.NO_ACCESS);\n }\n\n return (\n <AuthZLayout\n pageTitle={pageTitle}\n actions={\n [<AddRoleButton key=\"add-role-button\" />]\n }\n >\n <Tabs\n variant=\"tabs\"\n defaultActiveKey={hash ? 'permissionsRoles' : 'team'}\n className=\"page-band bg-light-100\"\n >\n <Tab eventKey=\"team\" title={intl.formatMessage(messages['authz.tabs.team'])} className=\"page-band py-5\">\n <TeamMembersTable presetScope={presetScope} />\n </Tab>\n <Tab id=\"libraries-permissions-roles-tab\" eventKey=\"permissionsRoles\" title={intl.formatMessage(messages['authz.tabs.permissionsRoles'])} className=\"page-band py-5\">\n <RolesPermissions />\n </Tab>\n </Tabs>\n </AuthZLayout>\n );\n};\n\nexport default AuthzHome;\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/authz-module/authz-home/index.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAC7C,OAAO,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAChE,OAAO,EAAE,gBAAgB,EAAE,MAAM,gCAAgC,CAAC;AAClE,OAAO,aAAa,MAAM,4CAA4C,CAAC;AACvE,OAAO,EAAE,sBAAsB,EAAE,MAAM,gDAAgD,CAAC;AACxF,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC9C,OAAO,WAAW,MAAM,6BAA6B,CAAC;AACtD,OAAO,gBAAgB,MAAM,sDAAsD,CAAC;AACpF,OAAO,WAAW,MAAM,0CAA0C,CAAC;AAEnE,OAAO,QAAQ,MAAM,YAAY,CAAC;AAElC,MAAM,SAAS,GAAG,GAAG,EAAE;;IACrB,MAAM,EAAE,IAAI,EAAE,GAAG,WAAW,EAAE,CAAC;IAC/B,MAAM,IAAI,GAAG,OAAO,EAAE,CAAC;IACvB,MAAM,CAAC,YAAY,CAAC,GAAG,eAAe,EAAE,CAAC;IAEzC;;MAEE;IACF,MAAM,WAAW,GAAG,CAAA,MAAA,YAAY,CAAC,GAAG,CAAC,OAAO,CAAC,0CAAE,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,KAAI,SAAS,CAAC;IAEhF,MAAM,SAAS,GAAG,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,yBAAyB,CAAC,CAAC,CAAC;IAE1E,MAAM,EACJ,mBAAmB,EAAE,oBAAoB,EAAE,SAAS,EAAE,oBAAoB,GAC3E,GAAG,sBAAsB,EAAE,CAAC;IAE7B;;;;;;;;OAQG;IACH,IAAI,oBAAoB,EAAE,CAAC;QACzB,OAAO,KAAC,WAAW,KAAG,CAAC;IACzB,CAAC;IAED,IAAI,CAAC,mBAAmB,IAAI,CAAC,oBAAoB,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;IAC1C,CAAC;IAED,OAAO,CACL,KAAC,WAAW,IACV,SAAS,EAAE,SAAS,EACpB,OAAO,EACL,CAAC,KAAC,aAAa,MAAK,iBAAiB,CAAG,CAAC,YAG3C,MAAC,IAAI,IACH,OAAO,EAAC,MAAM,EACd,gBAAgB,EAAE,IAAI,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,MAAM,EACpD,SAAS,EAAC,wBAAwB,aAElC,KAAC,GAAG,IAAC,QAAQ,EAAC,MAAM,EAAC,KAAK,EAAE,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,iBAAiB,CAAC,CAAC,EAAE,SAAS,EAAC,gBAAgB,YACrG,KAAC,gBAAgB,IAAC,WAAW,EAAE,WAAW,GAAI,GAC1C,EACN,KAAC,GAAG,IAAC,EAAE,EAAC,iCAAiC,EAAC,QAAQ,EAAC,kBAAkB,EAAC,KAAK,EAAE,IAAI,CAAC,aAAa,CAAC,QAAQ,CAAC,6BAA6B,CAAC,CAAC,EAAE,SAAS,EAAC,gBAAgB,YAClK,KAAC,gBAAgB,KAAG,GAChB,IACD,GACK,CACf,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,SAAS,CAAC","sourcesContent":["import { useIntl } from '@openedx/frontend-base';\nimport { Tab, Tabs } from '@openedx/paragon';\nimport { useLocation, useSearchParams } from 'react-router-dom';\nimport { TeamMembersTable } from '@src/authz-module/team-members';\nimport AddRoleButton from '@src/authz-module/components/AddRoleButton';\nimport { useViewTeamPermissions } from '@src/authz-module/hooks/useViewTeamPermissions';\nimport { CustomErrors } from '@src/constants';\nimport LoadingPage from '@src/components/LoadingPage';\nimport RolesPermissions from '@src/authz-module/roles-permissions/RolesPermissions';\nimport AuthZLayout from '@src/authz-module/components/AuthZLayout';\n\nimport messages from './messages';\n\nconst AuthzHome = () => {\n const { hash } = useLocation();\n const intl = useIntl();\n const [searchParams] = useSearchParams();\n\n /* In the authoring repository the scope is encoded but this is to Replace spaces with '+'\n to match URL encoding format in case the 'scope' parameter is provided with spaces instead of '+'\n */\n const presetScope = searchParams.get('scope')?.replace(/\\s/g, '+') || undefined;\n\n const pageTitle = intl.formatMessage(messages['authz.manage.page.title']);\n\n const {\n isCourseViewAllowed, isLibraryViewAllowed, isLoading: isLoadingPermissions,\n } = useViewTeamPermissions();\n\n /**\n * It gates the whole page whether the user is allowed to view the team members. If\n * the user is not allowed, an error is thrown to display the access denied message.\n *\n * Rendering is held until the check settles rather than started optimistically, so a\n * user who turns out to be denied never fires the listing and filter requests behind\n * the page. Both flags read false while it is in flight, which would otherwise deny\n * everyone for a frame.\n */\n if (isLoadingPermissions) {\n return <LoadingPage />;\n }\n\n if (!isCourseViewAllowed && !isLibraryViewAllowed) {\n throw new Error(CustomErrors.NO_ACCESS);\n }\n\n return (\n <AuthZLayout\n pageTitle={pageTitle}\n actions={\n [<AddRoleButton key=\"add-role-button\" />]\n }\n >\n <Tabs\n variant=\"tabs\"\n defaultActiveKey={hash ? 'permissionsRoles' : 'team'}\n className=\"page-band bg-light-100\"\n >\n <Tab eventKey=\"team\" title={intl.formatMessage(messages['authz.tabs.team'])} className=\"page-band py-3\">\n <TeamMembersTable presetScope={presetScope} />\n </Tab>\n <Tab id=\"libraries-permissions-roles-tab\" eventKey=\"permissionsRoles\" title={intl.formatMessage(messages['authz.tabs.permissionsRoles'])} className=\"page-band py-3\">\n <RolesPermissions />\n </Tab>\n </Tabs>\n </AuthZLayout>\n );\n};\n\nexport default AuthzHome;\n"]}
@@ -19,7 +19,7 @@ import AuthZTitle from './AuthZTitle';
19
19
  */
20
20
  const AuthZLayout = (_a) => {
21
21
  var { children } = _a, titleProps = __rest(_a, ["children"]);
22
- return (_jsxs("div", { className: "authz-module", children: [_jsx(AuthZTitle, Object.assign({}, titleProps)), _jsx("div", { className: "bg-light-200", children: children })] }));
22
+ return (_jsxs("div", { className: "authz-module", children: [_jsx(AuthZTitle, Object.assign({}, titleProps)), children] }));
23
23
  };
24
24
  export default AuthZLayout;
25
25
  //# sourceMappingURL=AuthZLayout.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"AuthZLayout.js","sourceRoot":"","sources":["../../../src/authz-module/components/AuthZLayout.tsx"],"names":[],"mappings":";;;;;;;;;;;;AACA,OAAO,UAA+B,MAAM,cAAc,CAAC;AAM3D;;;;;GAKG;AACH,MAAM,WAAW,GAAG,CAAC,EAA6C,EAAE,EAAE;QAAjD,EAAE,QAAQ,OAAmC,EAA9B,UAAU,cAAzB,YAA2B,CAAF;IAAyB,OAAA,CACrE,eAAK,SAAS,EAAC,cAAc,aAC3B,KAAC,UAAU,oBAAK,UAAU,EAAI,EAC9B,cAAK,SAAS,EAAC,cAAc,YAC1B,QAAQ,GACL,IACF,CACP,CAAA;CAAA,CAAC;AAEF,eAAe,WAAW,CAAC","sourcesContent":["import { ReactNode } from 'react';\nimport AuthZTitle, { AuthZTitleProps } from './AuthZTitle';\n\ninterface AuthZLayoutProps extends AuthZTitleProps {\n children: ReactNode;\n}\n\n/**\n * Page chrome for the authz module: the title band, then the body below it.\n * The body only paints its colour, edge to edge. Each page marks the parts of its\n * content that should line up with the header using `page-band`, so anything meant\n * to bleed across the full width -- a stepper header, a toolbar -- simply omits it.\n */\nconst AuthZLayout = ({ children, ...titleProps }: AuthZLayoutProps) => (\n <div className=\"authz-module\">\n <AuthZTitle {...titleProps} />\n <div className=\"bg-light-200\">\n {children}\n </div>\n </div>\n);\n\nexport default AuthZLayout;\n"]}
1
+ {"version":3,"file":"AuthZLayout.js","sourceRoot":"","sources":["../../../src/authz-module/components/AuthZLayout.tsx"],"names":[],"mappings":";;;;;;;;;;;;AACA,OAAO,UAA+B,MAAM,cAAc,CAAC;AAM3D;;;;;GAKG;AACH,MAAM,WAAW,GAAG,CAAC,EAA6C,EAAE,EAAE;QAAjD,EAAE,QAAQ,OAAmC,EAA9B,UAAU,cAAzB,YAA2B,CAAF;IAAyB,OAAA,CACrE,eAAK,SAAS,EAAC,cAAc,aAC3B,KAAC,UAAU,oBAAK,UAAU,EAAI,EAC7B,QAAQ,IACL,CACP,CAAA;CAAA,CAAC;AAEF,eAAe,WAAW,CAAC","sourcesContent":["import { ReactNode } from 'react';\nimport AuthZTitle, { AuthZTitleProps } from './AuthZTitle';\n\ninterface AuthZLayoutProps extends AuthZTitleProps {\n children: ReactNode;\n}\n\n/**\n * Page chrome for the authz module: the title band, then the body below it.\n * The body only paints its colour, edge to edge. Each page marks the parts of its\n * content that should line up with the header using `page-band`, so anything meant\n * to bleed across the full width -- a stepper header, a toolbar -- simply omits it.\n */\nconst AuthZLayout = ({ children, ...titleProps }: AuthZLayoutProps) => (\n <div className=\"authz-module\">\n <AuthZTitle {...titleProps} />\n {children}\n </div>\n);\n\nexport default AuthZLayout;\n"]}
@@ -14,7 +14,8 @@ export interface AuthZTitleProps {
14
14
  pageSubtitle?: string | ReactNode;
15
15
  navLinks?: BreadcrumbLink[];
16
16
  actions?: (Action | ReactNode)[];
17
+ showDivider?: boolean;
17
18
  }
18
19
  export declare const ActionButton: ({ label, icon, onClick }: Action) => import("react").JSX.Element;
19
- declare const AuthZTitle: ({ activeLabel, navLinks, pageTitle, pageSubtitle, actions, }: AuthZTitleProps) => import("react").JSX.Element;
20
+ declare const AuthZTitle: ({ activeLabel, navLinks, pageTitle, pageSubtitle, actions, showDivider, }: AuthZTitleProps) => import("react").JSX.Element;
20
21
  export default AuthZTitle;
@@ -3,10 +3,10 @@ import { isValidElement, Fragment, } from 'react';
3
3
  import { Link } from 'react-router-dom';
4
4
  import { Breadcrumb, Col, Row, Button, Stack, useMediaQuery, breakpoints, } from '@openedx/paragon';
5
5
  export const ActionButton = ({ label, icon, onClick }) => (_jsx(Button, { size: "sm", iconBefore: icon, onClick: onClick, children: label }));
6
- const AuthZTitle = ({ activeLabel, navLinks = [], pageTitle, pageSubtitle, actions = [], }) => {
6
+ const AuthZTitle = ({ activeLabel, navLinks = [], pageTitle, pageSubtitle, actions = [], showDivider = false, }) => {
7
7
  const shouldRenderBreadcrumb = activeLabel || (navLinks === null || navLinks === void 0 ? void 0 : navLinks.length) > 0;
8
8
  const isDesktop = useMediaQuery({ minWidth: breakpoints.large.minWidth });
9
- return (_jsxs("div", { className: "page-band py-4 bg-light-100", children: [shouldRenderBreadcrumb
9
+ return (_jsxs("div", { className: `page-band py-4 bg-light-100${showDivider ? ' title-border-bottom' : ''}`, children: [shouldRenderBreadcrumb
10
10
  && (_jsx(Breadcrumb, { linkAs: Link, links: navLinks, activeLabel: activeLabel })), _jsxs(Row, { children: [_jsx(Col, { xs: 12, md: 7, children: _jsxs("div", { className: "d-flex align-items-center flex-column-sm mb-3 mb-md-0", children: [_jsx("h2", { className: "text-primary mb-0", children: pageTitle }), pageSubtitle && (_jsxs(_Fragment, { children: [_jsx("hr", { className: "authz-action-divider mx-lg-3 my-md-0 mx-md-3" }), typeof pageSubtitle === 'string'
11
11
  ? _jsx("h3", { className: "mb-0 font-weight-light text-gray-700", children: pageSubtitle })
12
12
  : _jsx("div", { className: "mb-0", children: pageSubtitle })] }))] }) }), _jsx(Col, { xs: 12, md: 5, children: _jsx(Stack, { className: "justify-content-end", direction: isDesktop ? 'horizontal' : 'vertical', children: actions.map((action, index) => {
@@ -1 +1 @@
1
- {"version":3,"file":"AuthZTitle.js","sourceRoot":"","sources":["../../../src/authz-module/components/AuthZTitle.tsx"],"names":[],"mappings":";AAAA,OAAO,EACU,cAAc,EAAa,QAAQ,GACnD,MAAM,OAAO,CAAC;AACf,OAAO,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AACxC,OAAO,EACL,UAAU,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,EAC5B,KAAK,EACL,aAAa,EACb,WAAW,GACZ,MAAM,kBAAkB,CAAC;AAqB1B,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,OAAO,EAAU,EAAE,EAAE,CAAC,CAChE,KAAC,MAAM,IACL,IAAI,EAAC,IAAI,EACT,UAAU,EAAE,IAAI,EAChB,OAAO,EAAE,OAAO,YAEf,KAAK,GACC,CACV,CAAC;AAEF,MAAM,UAAU,GAAG,CAAC,EAClB,WAAW,EAAE,QAAQ,GAAG,EAAE,EAAE,SAAS,EAAE,YAAY,EAAE,OAAO,GAAG,EAAE,GACjD,EAAE,EAAE;IACpB,MAAM,sBAAsB,GAAG,WAAW,IAAI,CAAA,QAAQ,aAAR,QAAQ,uBAAR,QAAQ,CAAE,MAAM,IAAG,CAAC,CAAC;IACnE,MAAM,SAAS,GAAG,aAAa,CAAC,EAAE,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC;IAC1E,OAAO,CACL,eAAK,SAAS,EAAC,6BAA6B,aACxC,sBAAsB;mBACrB,CACD,KAAC,UAAU,IACT,MAAM,EAAE,IAAI,EACZ,KAAK,EAAE,QAAQ,EACf,WAAW,EAAE,WAAW,GACxB,CACH,EACD,MAAC,GAAG,eACF,KAAC,GAAG,IAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,YAChB,eAAK,SAAS,EAAC,uDAAuD,aACpE,aAAI,SAAS,EAAC,mBAAmB,YAAE,SAAS,GAAM,EACjD,YAAY,IAAI,CACf,8BACE,aAAI,SAAS,EAAC,8CAA8C,GAAG,EAC9D,OAAO,YAAY,KAAK,QAAQ;4CAC/B,CAAC,CAAC,aAAI,SAAS,EAAC,sCAAsC,YAAE,YAAY,GAAM;4CAC1E,CAAC,CAAC,cAAK,SAAS,EAAC,MAAM,YAAE,YAAY,GAAO,IAC7C,CACJ,IAEG,GACF,EACN,KAAC,GAAG,IAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,YAChB,KAAC,KAAK,IAAC,SAAS,EAAC,qBAAqB,EAAC,SAAS,EAAE,SAAS,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,UAAU,YAEnF,OAAO,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,EAAE;gCAC5B,MAAM,OAAO,GAAG,cAAc,CAAC,MAAM,CAAC;oCACpC,CAAC,CAAC,MAAM;oCACR,CAAC,CAAC,KAAC,YAAY,oBAAK,MAAgB,EAAI,CAAC;gCAC3C,MAAM,GAAG,GAAG,cAAc,CAAC,MAAM,CAAC;oCAChC,CAAC,CAAC,MAAM,CAAC,GAAG;oCACZ,CAAC,CAAE,MAAiB,CAAC,KAAK,CAAC;gCAC7B,OAAO,CACL,MAAC,QAAQ,eACN,OAAO,EACP,CAAC,KAAK,KAAK,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI;4CACpC,CAAC,CAAC,CAAC,aAAI,SAAS,EAAC,8BAA8B,GAAG,CAAC,KAHxC,uBAAuB,GAAG,EAAE,CAIhC,CACZ,CAAC;4BACJ,CAAC,CAAC,GAEE,GACJ,IACF,IACF,CACP,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC","sourcesContent":["import {\n ComponentType, isValidElement, ReactNode, Fragment,\n} from 'react';\nimport { Link } from 'react-router-dom';\nimport {\n Breadcrumb, Col, Row, Button,\n Stack,\n useMediaQuery,\n breakpoints,\n} from '@openedx/paragon';\n\ninterface BreadcrumbLink {\n label: string;\n to?: string;\n}\n\ninterface Action {\n label: string;\n icon?: ComponentType;\n onClick: () => void;\n}\n\nexport interface AuthZTitleProps {\n activeLabel?: string;\n pageTitle: string;\n pageSubtitle?: string | ReactNode;\n navLinks?: BreadcrumbLink[];\n actions?: (Action | ReactNode)[];\n}\n\nexport const ActionButton = ({ label, icon, onClick }: Action) => (\n <Button\n size=\"sm\"\n iconBefore={icon}\n onClick={onClick}\n >\n {label}\n </Button>\n);\n\nconst AuthZTitle = ({\n activeLabel, navLinks = [], pageTitle, pageSubtitle, actions = [],\n}: AuthZTitleProps) => {\n const shouldRenderBreadcrumb = activeLabel || navLinks?.length > 0;\n const isDesktop = useMediaQuery({ minWidth: breakpoints.large.minWidth });\n return (\n <div className=\"page-band py-4 bg-light-100\">\n { shouldRenderBreadcrumb\n && (\n <Breadcrumb\n linkAs={Link}\n links={navLinks}\n activeLabel={activeLabel}\n />\n )}\n <Row>\n <Col xs={12} md={7}>\n <div className=\"d-flex align-items-center flex-column-sm mb-3 mb-md-0\">\n <h2 className=\"text-primary mb-0\">{pageTitle}</h2>\n {pageSubtitle && (\n <>\n <hr className=\"authz-action-divider mx-lg-3 my-md-0 mx-md-3\" />\n {typeof pageSubtitle === 'string'\n ? <h3 className=\"mb-0 font-weight-light text-gray-700\">{pageSubtitle}</h3>\n : <div className=\"mb-0\">{pageSubtitle}</div>}\n </>\n )}\n\n </div>\n </Col>\n <Col xs={12} md={5}>\n <Stack className=\"justify-content-end\" direction={isDesktop ? 'horizontal' : 'vertical'}>\n {\n actions.map((action, index) => {\n const content = isValidElement(action)\n ? action\n : <ActionButton {...action as Action} />;\n const key = isValidElement(action)\n ? action.key\n : (action as Action).label;\n return (\n <Fragment key={`authz-header-action-${key}`}>\n {content}\n {(index === actions.length - 1) ? null\n : (<hr className=\"authz-action-divider mx-lg-5\" />)}\n </Fragment>\n );\n })\n }\n </Stack>\n </Col>\n </Row>\n </div>\n );\n};\n\nexport default AuthZTitle;\n"]}
1
+ {"version":3,"file":"AuthZTitle.js","sourceRoot":"","sources":["../../../src/authz-module/components/AuthZTitle.tsx"],"names":[],"mappings":";AAAA,OAAO,EACU,cAAc,EAAa,QAAQ,GACnD,MAAM,OAAO,CAAC;AACf,OAAO,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AACxC,OAAO,EACL,UAAU,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,EAC5B,KAAK,EACL,aAAa,EACb,WAAW,GACZ,MAAM,kBAAkB,CAAC;AAsB1B,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,OAAO,EAAU,EAAE,EAAE,CAAC,CAChE,KAAC,MAAM,IACL,IAAI,EAAC,IAAI,EACT,UAAU,EAAE,IAAI,EAChB,OAAO,EAAE,OAAO,YAEf,KAAK,GACC,CACV,CAAC;AAEF,MAAM,UAAU,GAAG,CAAC,EAClB,WAAW,EAAE,QAAQ,GAAG,EAAE,EAAE,SAAS,EAAE,YAAY,EAAE,OAAO,GAAG,EAAE,EAAE,WAAW,GAAG,KAAK,GACtE,EAAE,EAAE;IACpB,MAAM,sBAAsB,GAAG,WAAW,IAAI,CAAA,QAAQ,aAAR,QAAQ,uBAAR,QAAQ,CAAE,MAAM,IAAG,CAAC,CAAC;IACnE,MAAM,SAAS,GAAG,aAAa,CAAC,EAAE,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC;IAC1E,OAAO,CACL,eAAK,SAAS,EAAE,8BAA8B,WAAW,CAAC,CAAC,CAAC,sBAAsB,CAAC,CAAC,CAAC,EAAE,EAAE,aACrF,sBAAsB;mBACrB,CACD,KAAC,UAAU,IACT,MAAM,EAAE,IAAI,EACZ,KAAK,EAAE,QAAQ,EACf,WAAW,EAAE,WAAW,GACxB,CACH,EACD,MAAC,GAAG,eACF,KAAC,GAAG,IAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,YAChB,eAAK,SAAS,EAAC,uDAAuD,aACpE,aAAI,SAAS,EAAC,mBAAmB,YAAE,SAAS,GAAM,EACjD,YAAY,IAAI,CACf,8BACE,aAAI,SAAS,EAAC,8CAA8C,GAAG,EAC9D,OAAO,YAAY,KAAK,QAAQ;4CAC/B,CAAC,CAAC,aAAI,SAAS,EAAC,sCAAsC,YAAE,YAAY,GAAM;4CAC1E,CAAC,CAAC,cAAK,SAAS,EAAC,MAAM,YAAE,YAAY,GAAO,IAC7C,CACJ,IAEG,GACF,EACN,KAAC,GAAG,IAAC,EAAE,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC,YAChB,KAAC,KAAK,IAAC,SAAS,EAAC,qBAAqB,EAAC,SAAS,EAAE,SAAS,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,UAAU,YAEnF,OAAO,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,EAAE;gCAC5B,MAAM,OAAO,GAAG,cAAc,CAAC,MAAM,CAAC;oCACpC,CAAC,CAAC,MAAM;oCACR,CAAC,CAAC,KAAC,YAAY,oBAAK,MAAgB,EAAI,CAAC;gCAC3C,MAAM,GAAG,GAAG,cAAc,CAAC,MAAM,CAAC;oCAChC,CAAC,CAAC,MAAM,CAAC,GAAG;oCACZ,CAAC,CAAE,MAAiB,CAAC,KAAK,CAAC;gCAC7B,OAAO,CACL,MAAC,QAAQ,eACN,OAAO,EACP,CAAC,KAAK,KAAK,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI;4CACpC,CAAC,CAAC,CAAC,aAAI,SAAS,EAAC,8BAA8B,GAAG,CAAC,KAHxC,uBAAuB,GAAG,EAAE,CAIhC,CACZ,CAAC;4BACJ,CAAC,CAAC,GAEE,GACJ,IACF,IACF,CACP,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC","sourcesContent":["import {\n ComponentType, isValidElement, ReactNode, Fragment,\n} from 'react';\nimport { Link } from 'react-router-dom';\nimport {\n Breadcrumb, Col, Row, Button,\n Stack,\n useMediaQuery,\n breakpoints,\n} from '@openedx/paragon';\n\ninterface BreadcrumbLink {\n label: string;\n to?: string;\n}\n\ninterface Action {\n label: string;\n icon?: ComponentType;\n onClick: () => void;\n}\n\nexport interface AuthZTitleProps {\n activeLabel?: string;\n pageTitle: string;\n pageSubtitle?: string | ReactNode;\n navLinks?: BreadcrumbLink[];\n actions?: (Action | ReactNode)[];\n showDivider?: boolean;\n}\n\nexport const ActionButton = ({ label, icon, onClick }: Action) => (\n <Button\n size=\"sm\"\n iconBefore={icon}\n onClick={onClick}\n >\n {label}\n </Button>\n);\n\nconst AuthZTitle = ({\n activeLabel, navLinks = [], pageTitle, pageSubtitle, actions = [], showDivider = false,\n}: AuthZTitleProps) => {\n const shouldRenderBreadcrumb = activeLabel || navLinks?.length > 0;\n const isDesktop = useMediaQuery({ minWidth: breakpoints.large.minWidth });\n return (\n <div className={`page-band py-4 bg-light-100${showDivider ? ' title-border-bottom' : ''}`}>\n { shouldRenderBreadcrumb\n && (\n <Breadcrumb\n linkAs={Link}\n links={navLinks}\n activeLabel={activeLabel}\n />\n )}\n <Row>\n <Col xs={12} md={7}>\n <div className=\"d-flex align-items-center flex-column-sm mb-3 mb-md-0\">\n <h2 className=\"text-primary mb-0\">{pageTitle}</h2>\n {pageSubtitle && (\n <>\n <hr className=\"authz-action-divider mx-lg-3 my-md-0 mx-md-3\" />\n {typeof pageSubtitle === 'string'\n ? <h3 className=\"mb-0 font-weight-light text-gray-700\">{pageSubtitle}</h3>\n : <div className=\"mb-0\">{pageSubtitle}</div>}\n </>\n )}\n\n </div>\n </Col>\n <Col xs={12} md={5}>\n <Stack className=\"justify-content-end\" direction={isDesktop ? 'horizontal' : 'vertical'}>\n {\n actions.map((action, index) => {\n const content = isValidElement(action)\n ? action\n : <ActionButton {...action as Action} />;\n const key = isValidElement(action)\n ? action.key\n : (action as Action).label;\n return (\n <Fragment key={`authz-header-action-${key}`}>\n {content}\n {(index === actions.length - 1) ? null\n : (<hr className=\"authz-action-divider mx-lg-5\" />)}\n </Fragment>\n );\n })\n }\n </Stack>\n </Col>\n </Row>\n </div>\n );\n};\n\nexport default AuthZTitle;\n"]}
@@ -12,7 +12,7 @@ const PermissionTable = ({ permissionsTable, roles, title }) => {
12
12
  // Only the narrowest viewports are too small for the matrix, so the card scrolls there
13
13
  // (see `.permission-table-scroll`). Above that it is not a scroll container, which is
14
14
  // what lets the header row stick to the viewport as the page scrolls.
15
- _jsx(Card, { className: "permission-table-scroll", children: _jsxs("table", { className: "permission-table w-100", children: [_jsx("thead", { children: _jsxs("tr", { children: [_jsx("th", { className: "sticky-top bg-white px-4 py-3", children: title }), roles.map(role => (_jsx("th", { className: `text-center py-3 sticky-top bg-white ${role.disabled ? 'text-gray-200' : ''}`, children: role.disabled ? (_jsx(OverlayTrigger, { placement: "top", overlay: (_jsx(Tooltip, { id: `tooltip-${role.name}`, variant: "light", children: formatMessage(messages['authz.role.card.permission.for.role.status.disabled']) })), children: _jsx("span", { style: { cursor: 'help' }, children: role.name }) })) : (role.name) }, role.name)))] }) }), _jsx("tbody", { children: permissionsTable.map(resourceGroup => (_jsxs(React.Fragment, { children: [_jsx("tr", { className: "bg-info-100 text-primary", children: _jsx("td", { colSpan: roles.length + 1, className: "text-start py-3 px-4", children: _jsxs("div", { className: "d-flex align-items-center", children: [resourceGroup.icon && _jsx(Icon, { className: "d-inline-block mr-2", size: "xs", src: resourceGroup.icon }), _jsx("strong", { children: resourceGroup.label }), _jsx(ResourceTooltip, { resourceGroup: resourceGroup })] }) }) }), resourceGroup.permissions.map(permission => (_jsxs("tr", { className: "border-top", children: [_jsxs("td", { className: "text-start d-flex align-items-center small px-4 py-3", children: [_jsx(Icon, { className: "d-inline-block mr-2", size: "sm", src: actionsDictionary[permission.actionKey] }), permission.label] }), roles.map(role => (_jsx("td", { className: `text-center ${role.disabled ? 'text-gray-200' : ''}`, children: permission.roles[role.name]
15
+ _jsx(Card, { className: "permission-table-scroll", children: _jsxs("table", { className: "permission-table w-100", children: [_jsx("thead", { children: _jsxs("tr", { children: [_jsx("th", { className: "sticky-top bg-white px-4 py-3", children: title }), roles.map(role => (_jsx("th", { className: `text-center py-3 sticky-top bg-white ${role.disabled ? 'text-gray-200' : ''}`, children: role.disabled ? (_jsx(OverlayTrigger, { placement: "top", overlay: (_jsx(Tooltip, { id: `tooltip-${role.name}`, variant: "light", children: formatMessage(messages['authz.role.card.permission.for.role.status.disabled']) })), children: _jsx("span", { style: { cursor: 'help' }, children: role.name }) })) : (role.name) }, role.name)))] }) }), _jsx("tbody", { children: permissionsTable.map(resourceGroup => (_jsxs(React.Fragment, { children: [_jsx("tr", { className: "bg-info-100 text-primary", children: _jsx("td", { colSpan: roles.length + 1, className: "text-start py-3 px-4", children: _jsxs("div", { className: "d-flex align-items-center", children: [resourceGroup.icon && _jsx(Icon, { className: "d-inline-block mr-2", size: "xs", src: resourceGroup.icon }), _jsxs("span", { className: "small", children: [" ", _jsx("strong", { children: resourceGroup.label })] }), _jsx(ResourceTooltip, { resourceGroup: resourceGroup })] }) }) }), resourceGroup.permissions.map(permission => (_jsxs("tr", { className: "border-top", children: [_jsxs("td", { className: "text-start d-flex align-items-center small px-4 py-3", children: [_jsx(Icon, { className: "d-inline-block mr-2", size: "sm", src: actionsDictionary[permission.actionKey] }), permission.label] }), roles.map(role => (_jsx("td", { className: `text-center ${role.disabled ? 'text-gray-200' : ''}`, children: permission.roles[role.name]
16
16
  ? (_jsx(Icon, { className: `d-inline-block ${role.disabled ? 'text-gray-200' : 'text-success'}`, src: Check, "aria-label": formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {
17
17
  roleName: role.name,
18
18
  }), screenReaderText: formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {
@@ -1 +1 @@
1
- {"version":3,"file":"PermissionTable.js","sourceRoot":"","sources":["../../../src/authz-module/components/PermissionTable.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\nimport { useIntl } from '@openedx/frontend-base';\nimport { Check, Close } from '@openedx/paragon/icons';\nimport {\n Card, Icon, OverlayTrigger, Tooltip,\n} from '@openedx/paragon';\nimport { PermissionsResourceGrouped, Role } from '@src/types';\nimport { actionsDictionary } from './RoleCard/constants';\nimport ResourceTooltip from './ResourceTooltip';\nimport messages from './messages';\n\ninterface PermissionTableProps {\n roles: Role[];\n permissionsTable: PermissionsResourceGrouped[];\n title?: string;\n}\n\nconst PermissionTable = ({ permissionsTable, roles, title }: PermissionTableProps) => {\n const { formatMessage } = useIntl();\n return (\n // Only the narrowest viewports are too small for the matrix, so the card scrolls there\n // (see `.permission-table-scroll`). Above that it is not a scroll container, which is\n // what lets the header row stick to the viewport as the page scrolls.\n <Card className=\"permission-table-scroll\">\n <table className=\"permission-table w-100\">\n <thead>\n <tr>\n <th className=\"sticky-top bg-white px-4 py-3\">\n {title}\n </th>\n {roles.map(role => (\n <th\n key={role.name}\n className={`text-center py-3 sticky-top bg-white ${role.disabled ? 'text-gray-200' : ''}`}\n >\n {role.disabled ? (\n <OverlayTrigger\n placement=\"top\"\n overlay={(\n <Tooltip\n id={`tooltip-${role.name}`}\n variant=\"light\"\n >\n {formatMessage(messages['authz.role.card.permission.for.role.status.disabled'])}\n </Tooltip>\n )}\n >\n <span style={{ cursor: 'help' }}>{role.name}</span>\n </OverlayTrigger>\n ) : (\n role.name\n )}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {permissionsTable.map(resourceGroup => (\n <React.Fragment key={resourceGroup.key}>\n <tr className=\"bg-info-100 text-primary\">\n <td colSpan={roles.length + 1} className=\"text-start py-3 px-4\">\n <div className=\"d-flex align-items-center\">\n {resourceGroup.icon && <Icon className=\"d-inline-block mr-2\" size=\"xs\" src={resourceGroup.icon} />}\n <strong>{resourceGroup.label}</strong>\n <ResourceTooltip resourceGroup={resourceGroup} />\n </div>\n </td>\n </tr>\n {resourceGroup.permissions.map(permission => (\n <tr key={permission.key} className=\"border-top\">\n <td className=\"text-start d-flex align-items-center small px-4 py-3\">\n <Icon className=\"d-inline-block mr-2\" size=\"sm\" src={actionsDictionary[permission.actionKey]} />\n {permission.label}\n </td>\n {roles.map(role => (\n <td key={role.name} className={`text-center ${role.disabled ? 'text-gray-200' : ''}`}>\n {\n permission.roles[role.name]\n ? (\n <Icon\n className={`d-inline-block ${role.disabled ? 'text-gray-200' : 'text-success'}`}\n src={Check}\n aria-label={formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {\n roleName: role.name,\n })}\n screenReaderText={formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {\n roleName: role.name,\n })}\n />\n )\n : (\n <Icon\n className={`d-inline-block ${role.disabled ? 'text-gray-200' : 'text-danger'}`}\n src={Close}\n aria-label={formatMessage(messages['authz.role.card.permission.for.role.status.not.granted'], {\n roleName: role.name,\n })}\n screenReaderText={formatMessage(messages['authz.role.card.permission.for.role.status.not.granted'], {\n roleName: role.name,\n })}\n />\n )\n }\n </td>\n ))}\n </tr>\n ))}\n </React.Fragment>\n ))}\n </tbody>\n </table>\n </Card>\n );\n};\n\nexport default PermissionTable;\n"]}
1
+ {"version":3,"file":"PermissionTable.js","sourceRoot":"","sources":["../../../src/authz-module/components/PermissionTable.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\nimport { useIntl } from '@openedx/frontend-base';\nimport { Check, Close } from '@openedx/paragon/icons';\nimport {\n Card, Icon, OverlayTrigger, Tooltip,\n} from '@openedx/paragon';\nimport { PermissionsResourceGrouped, Role } from '@src/types';\nimport { actionsDictionary } from './RoleCard/constants';\nimport ResourceTooltip from './ResourceTooltip';\nimport messages from './messages';\n\ninterface PermissionTableProps {\n roles: Role[];\n permissionsTable: PermissionsResourceGrouped[];\n title?: string;\n}\n\nconst PermissionTable = ({ permissionsTable, roles, title }: PermissionTableProps) => {\n const { formatMessage } = useIntl();\n return (\n // Only the narrowest viewports are too small for the matrix, so the card scrolls there\n // (see `.permission-table-scroll`). Above that it is not a scroll container, which is\n // what lets the header row stick to the viewport as the page scrolls.\n <Card className=\"permission-table-scroll\">\n <table className=\"permission-table w-100\">\n <thead>\n <tr>\n <th className=\"sticky-top bg-white px-4 py-3\">\n {title}\n </th>\n {roles.map(role => (\n <th\n key={role.name}\n className={`text-center py-3 sticky-top bg-white ${role.disabled ? 'text-gray-200' : ''}`}\n >\n {role.disabled ? (\n <OverlayTrigger\n placement=\"top\"\n overlay={(\n <Tooltip\n id={`tooltip-${role.name}`}\n variant=\"light\"\n >\n {formatMessage(messages['authz.role.card.permission.for.role.status.disabled'])}\n </Tooltip>\n )}\n >\n <span style={{ cursor: 'help' }}>{role.name}</span>\n </OverlayTrigger>\n ) : (\n role.name\n )}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {permissionsTable.map(resourceGroup => (\n <React.Fragment key={resourceGroup.key}>\n <tr className=\"bg-info-100 text-primary\">\n <td colSpan={roles.length + 1} className=\"text-start py-3 px-4\">\n <div className=\"d-flex align-items-center\">\n {resourceGroup.icon && <Icon className=\"d-inline-block mr-2\" size=\"xs\" src={resourceGroup.icon} />}\n <span className=\"small\"> <strong>{resourceGroup.label}</strong></span>\n <ResourceTooltip resourceGroup={resourceGroup} />\n </div>\n </td>\n </tr>\n {resourceGroup.permissions.map(permission => (\n <tr key={permission.key} className=\"border-top\">\n <td className=\"text-start d-flex align-items-center small px-4 py-3\">\n <Icon className=\"d-inline-block mr-2\" size=\"sm\" src={actionsDictionary[permission.actionKey]} />\n {permission.label}\n </td>\n {roles.map(role => (\n <td key={role.name} className={`text-center ${role.disabled ? 'text-gray-200' : ''}`}>\n {\n permission.roles[role.name]\n ? (\n <Icon\n className={`d-inline-block ${role.disabled ? 'text-gray-200' : 'text-success'}`}\n src={Check}\n aria-label={formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {\n roleName: role.name,\n })}\n screenReaderText={formatMessage(messages['authz.role.card.permission.for.role.status.granted'], {\n roleName: role.name,\n })}\n />\n )\n : (\n <Icon\n className={`d-inline-block ${role.disabled ? 'text-gray-200' : 'text-danger'}`}\n src={Close}\n aria-label={formatMessage(messages['authz.role.card.permission.for.role.status.not.granted'], {\n roleName: role.name,\n })}\n screenReaderText={formatMessage(messages['authz.role.card.permission.for.role.status.not.granted'], {\n roleName: role.name,\n })}\n />\n )\n }\n </td>\n ))}\n </tr>\n ))}\n </React.Fragment>\n ))}\n </tbody>\n </table>\n </Card>\n );\n};\n\nexport default PermissionTable;\n"]}
@@ -1,3 +1,3 @@
1
1
  import { MultipleChoiceFilterProps } from './types';
2
- declare const MultipleChoiceFilter: ({ filterButtonText, filterChoices, filterValue, setFilter, isGrouped, isSearchable, onSearchChange, iconSrc, disabled, }: MultipleChoiceFilterProps) => import("react").JSX.Element;
2
+ declare const MultipleChoiceFilter: ({ filterButtonText, filterChoices, filterValue, setFilter, isGrouped, isSearchable, onSearchChange, iconSrc, disabled, size, }: MultipleChoiceFilterProps) => import("react").JSX.Element;
3
3
  export default MultipleChoiceFilter;
@@ -4,7 +4,8 @@ import { useIntl } from '@openedx/frontend-base';
4
4
  import { FilterList, Info, Search } from '@openedx/paragon/icons';
5
5
  import { useState } from 'react';
6
6
  import messages from '../messages';
7
- const MultipleChoiceFilter = ({ filterButtonText, filterChoices, filterValue, setFilter, isGrouped = false, isSearchable = false, onSearchChange, iconSrc, disabled = false, }) => {
7
+ import { validateSizeFormControl } from '../../utils';
8
+ const MultipleChoiceFilter = ({ filterButtonText, filterChoices, filterValue, setFilter, isGrouped = false, isSearchable = false, onSearchChange, iconSrc, disabled = false, size = 'sm', }) => {
8
9
  const [searchValue, setSearchValue] = useState(undefined);
9
10
  const { formatMessage } = useIntl();
10
11
  const checkedBoxes = filterValue || [];
@@ -37,10 +38,10 @@ const MultipleChoiceFilter = ({ filterButtonText, filterChoices, filterValue, se
37
38
  }, new Map());
38
39
  return Array.from(groupedFilterChoices.values());
39
40
  };
40
- return (_jsxs(Dropdown, { className: "no-caret-dropdown filters", children: [_jsx(Dropdown.Toggle, { variant: checkedBoxes.length > 0 ? 'primary' : 'outline-primary', children: _jsxs(Stack, { direction: "horizontal", gap: 2, children: [iconSrc && _jsx(Icon, { color: "primary", src: iconSrc }), filterButtonText, checkedBoxes.length > 0 && ` (${checkedBoxes.length})`, _jsx(Icon, { color: "primary", src: FilterList })] }) }), _jsxs(Dropdown.Menu, { children: [isSearchable && (_jsx(Form.Control, { className: "m-1", type: "text", trailingElement: _jsx(Icon, { src: Search }), placeholder: formatMessage(messages['authz.table.controlbar.search']), onChange: (e) => {
41
+ return (_jsxs(Dropdown, { className: "no-caret-dropdown filters", children: [_jsx(Dropdown.Toggle, { variant: checkedBoxes.length > 0 ? 'primary' : 'outline-primary', size: size, children: _jsxs(Stack, { direction: "horizontal", gap: 2, children: [iconSrc && _jsx(Icon, { color: "primary", src: iconSrc }), filterButtonText, checkedBoxes.length > 0 && ` (${checkedBoxes.length})`, _jsx(Icon, { color: "primary", src: FilterList })] }) }), _jsxs(Dropdown.Menu, { children: [isSearchable && (_jsx(Form.Control, { className: "m-1", type: "text", trailingElement: _jsx(Icon, { src: Search }), placeholder: formatMessage(messages['authz.table.controlbar.search']), onChange: (e) => {
41
42
  setSearchValue(e.target.value);
42
43
  onSearchChange === null || onSearchChange === void 0 ? void 0 : onSearchChange(e.target.value);
43
- }, value: searchValue })), _jsxs(Form.CheckboxSet, { className: "pgn__dropdown-filter-checkbox-group", name: filterButtonText, "aria-label": filterButtonText, value: checkedBoxes, children: [_jsx("span", { className: "small text-info-700 mt-2", children: formatMessage(messages['authz.table.controlbar.filters.items.showing'], { current: filterChoices.length, total: filterChoices.length }) }), !isGrouped ? filterChoices.map(({ displayName, value, description, }) => (_jsx(Form.Checkbox, { className: "m-2 w-100", checked: checkedBoxes.includes(value), value: value, onChange: () => handleClickCheckbox(value, displayName), "aria-label": displayName, disabled: checkedBoxes.includes(value) ? false : disabled, children: _jsxs("div", { className: "d-flex flex-column", children: [_jsx("span", { className: "small", children: displayName }), description && _jsx("span", { className: "small text-muted d-block", children: description })] }) }, displayName)))
44
+ }, value: searchValue, size: validateSizeFormControl(size) })), _jsxs(Form.CheckboxSet, { className: "pgn__dropdown-filter-checkbox-group", name: filterButtonText, "aria-label": filterButtonText, value: checkedBoxes, children: [_jsx("span", { className: "small text-info-700 mt-2", children: formatMessage(messages['authz.table.controlbar.filters.items.showing'], { current: filterChoices.length, total: filterChoices.length }) }), !isGrouped ? filterChoices.map(({ displayName, value, description, }) => (_jsx(Form.Checkbox, { className: "m-2 w-100", checked: checkedBoxes.includes(value), value: value, onChange: () => handleClickCheckbox(value, displayName), "aria-label": displayName, disabled: checkedBoxes.includes(value) ? false : disabled, children: _jsxs("div", { className: "d-flex flex-column", children: [_jsx("span", { className: "small", children: displayName }), description && _jsx("span", { className: "small text-muted d-block", children: description })] }) }, displayName)))
44
45
  : getGroupedChoices().map(({ groupName, icon, options }) => (_jsxs("div", { children: [_jsxs("div", { className: "pgn__dropdown-filter-group-name text-info-700 d-flex align-items-center small m-2 ml-0", children: [icon && _jsx(Icon, { color: "primary", src: icon, className: "mr-2", size: "xs" }), _jsx("span", { children: groupName })] }), options.map(({ displayName, value, description }) => (_jsx(Form.Checkbox, { className: "m-2 w-100", value: value, onChange: () => handleClickCheckbox(value, displayName), disabled: checkedBoxes.includes(value) ? false : disabled, "aria-label": displayName, children: _jsxs("div", { className: "d-flex flex-column", children: [_jsx("span", { className: "small", children: displayName }), description && _jsx("span", { className: "small text-muted d-block", children: description })] }) }, displayName)))] }, groupName))), isSearchable && (_jsxs("div", { className: "d-flex align-items-center justify-content-between p-2", children: [_jsx("span", { className: "text-muted small", children: formatMessage(messages['authz.table.controlbar.filters.more.results']) }), _jsx(Icon, { className: "text-gray-300 ml-1", src: Info, size: "xs" })] }))] })] })] }));
45
46
  };
46
47
  export default MultipleChoiceFilter;
@@ -1 +1 @@
1
- {"version":3,"file":"MultipleChoiceFilter.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/MultipleChoiceFilter.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n Dropdown, Form, Icon, Stack,\n} from '@openedx/paragon';\nimport { useIntl } from '@openedx/frontend-base';\nimport { FilterList, Info, Search } from '@openedx/paragon/icons';\nimport { useState } from 'react';\nimport messages from '@src/authz-module/components/messages';\nimport { FilterChoice, MultipleChoiceFilterProps } from './types';\n\nconst MultipleChoiceFilter = ({\n filterButtonText,\n filterChoices,\n filterValue,\n setFilter,\n isGrouped = false,\n isSearchable = false,\n onSearchChange,\n iconSrc,\n disabled = false,\n}: MultipleChoiceFilterProps) => {\n const [searchValue, setSearchValue] = useState<string | undefined>(undefined);\n const { formatMessage } = useIntl();\n\n const checkedBoxes = filterValue || [];\n const handleClickCheckbox = (value, displayName) => {\n const newValue = {\n groupName: filterButtonText?.toLocaleLowerCase() || '',\n value,\n displayName,\n };\n if (checkedBoxes.includes(value)) {\n const newCheckedBoxes = checkedBoxes.filter((val) => val !== value);\n return setFilter(newCheckedBoxes, newValue);\n }\n const newCheckedBoxes = [...checkedBoxes, value];\n return setFilter(newCheckedBoxes, newValue);\n };\n\n const getGroupedChoices = () => {\n const groupedFilterChoices = filterChoices.reduce((groups, choice) => {\n const groupName = choice.groupName || 'Ungrouped';\n const icon = choice.groupIcon || undefined;\n if (!groups.has(groupName)) {\n groups.set(groupName, { groupName, options: [], icon });\n }\n groups.get(groupName)!.options.push({\n displayName: choice.displayName,\n value: choice.value,\n description: choice.description,\n });\n return groups;\n }, new Map<string, { groupName: string; options: FilterChoice[]; icon?: any }>());\n return Array.from(groupedFilterChoices.values());\n };\n\n return (\n <Dropdown className=\"no-caret-dropdown filters\">\n <Dropdown.Toggle variant={checkedBoxes.length > 0 ? 'primary' : 'outline-primary'}>\n <Stack direction=\"horizontal\" gap={2}>\n {iconSrc && <Icon color=\"primary\" src={iconSrc} />}\n {filterButtonText}\n {checkedBoxes.length > 0 && ` (${checkedBoxes.length})`}\n <Icon color=\"primary\" src={FilterList} />\n </Stack>\n </Dropdown.Toggle>\n\n <Dropdown.Menu>\n {isSearchable && (\n <Form.Control\n className=\"m-1\"\n type=\"text\"\n trailingElement={<Icon src={Search} />}\n placeholder={formatMessage(messages['authz.table.controlbar.search'])}\n onChange={(e) => {\n setSearchValue(e.target.value);\n onSearchChange?.(e.target.value);\n }}\n value={searchValue}\n />\n )}\n <Form.CheckboxSet\n className=\"pgn__dropdown-filter-checkbox-group\"\n name={filterButtonText}\n aria-label={filterButtonText}\n value={checkedBoxes}\n >\n <span className=\"small text-info-700 mt-2\">\n {formatMessage(messages['authz.table.controlbar.filters.items.showing'], { current: filterChoices.length, total: filterChoices.length })}\n </span>\n {!isGrouped ? filterChoices.map(({\n displayName, value, description,\n }) => (\n <Form.Checkbox\n className=\"m-2 w-100\"\n key={displayName}\n checked={checkedBoxes.includes(value)}\n value={value}\n onChange={() => handleClickCheckbox(value, displayName)}\n aria-label={displayName}\n disabled={checkedBoxes.includes(value) ? false : disabled}\n >\n <div className=\"d-flex flex-column\">\n <span className=\"small\">{displayName}</span>\n { description && <span className=\"small text-muted d-block\">{description}</span> }\n </div>\n </Form.Checkbox>\n ))\n : getGroupedChoices().map(({ groupName, icon, options }) => (\n <div key={groupName}>\n <div className=\"pgn__dropdown-filter-group-name text-info-700 d-flex align-items-center small m-2 ml-0\">\n {icon && <Icon color=\"primary\" src={icon} className=\"mr-2\" size=\"xs\" />}\n <span>{groupName}</span>\n </div>\n {options.map(({ displayName, value, description }) => (\n <Form.Checkbox\n className=\"m-2 w-100\"\n key={displayName}\n value={value}\n onChange={() => handleClickCheckbox(value, displayName)}\n disabled={checkedBoxes.includes(value) ? false : disabled}\n aria-label={displayName}\n >\n <div className=\"d-flex flex-column\">\n <span className=\"small\">{displayName}</span>\n { description && <span className=\"small text-muted d-block\">{description}</span> }\n </div>\n </Form.Checkbox>\n ))}\n </div>\n ))}\n { isSearchable && (\n <div className=\"d-flex align-items-center justify-content-between p-2\">\n <span className=\"text-muted small\">{formatMessage(messages['authz.table.controlbar.filters.more.results'])}</span>\n <Icon className=\"text-gray-300 ml-1\" src={Info} size=\"xs\" />\n </div>\n )}\n </Form.CheckboxSet>\n </Dropdown.Menu>\n\n </Dropdown>\n );\n};\n\nexport default MultipleChoiceFilter;\n"]}
1
+ {"version":3,"file":"MultipleChoiceFilter.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/MultipleChoiceFilter.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n Dropdown, Form, Icon, Stack,\n} from '@openedx/paragon';\nimport { useIntl } from '@openedx/frontend-base';\nimport { FilterList, Info, Search } from '@openedx/paragon/icons';\nimport { useState } from 'react';\nimport messages from '@src/authz-module/components/messages';\nimport { FilterChoice, MultipleChoiceFilterProps } from './types';\nimport { validateSizeFormControl } from '@src/authz-module/utils';\n\nconst MultipleChoiceFilter = ({\n filterButtonText,\n filterChoices,\n filterValue,\n setFilter,\n isGrouped = false,\n isSearchable = false,\n onSearchChange,\n iconSrc,\n disabled = false,\n size = 'sm',\n}: MultipleChoiceFilterProps) => {\n const [searchValue, setSearchValue] = useState<string | undefined>(undefined);\n const { formatMessage } = useIntl();\n\n const checkedBoxes = filterValue || [];\n const handleClickCheckbox = (value, displayName) => {\n const newValue = {\n groupName: filterButtonText?.toLocaleLowerCase() || '',\n value,\n displayName,\n };\n if (checkedBoxes.includes(value)) {\n const newCheckedBoxes = checkedBoxes.filter((val) => val !== value);\n return setFilter(newCheckedBoxes, newValue);\n }\n const newCheckedBoxes = [...checkedBoxes, value];\n return setFilter(newCheckedBoxes, newValue);\n };\n\n const getGroupedChoices = () => {\n const groupedFilterChoices = filterChoices.reduce((groups, choice) => {\n const groupName = choice.groupName || 'Ungrouped';\n const icon = choice.groupIcon || undefined;\n if (!groups.has(groupName)) {\n groups.set(groupName, { groupName, options: [], icon });\n }\n groups.get(groupName)!.options.push({\n displayName: choice.displayName,\n value: choice.value,\n description: choice.description,\n });\n return groups;\n }, new Map<string, { groupName: string; options: FilterChoice[]; icon?: any }>());\n return Array.from(groupedFilterChoices.values());\n };\n\n return (\n <Dropdown className=\"no-caret-dropdown filters\">\n <Dropdown.Toggle variant={checkedBoxes.length > 0 ? 'primary' : 'outline-primary'} size={size}>\n <Stack direction=\"horizontal\" gap={2}>\n {iconSrc && <Icon color=\"primary\" src={iconSrc} />}\n {filterButtonText}\n {checkedBoxes.length > 0 && ` (${checkedBoxes.length})`}\n <Icon color=\"primary\" src={FilterList} />\n </Stack>\n </Dropdown.Toggle>\n\n <Dropdown.Menu>\n {isSearchable && (\n <Form.Control\n className=\"m-1\"\n type=\"text\"\n trailingElement={<Icon src={Search} />}\n placeholder={formatMessage(messages['authz.table.controlbar.search'])}\n onChange={(e) => {\n setSearchValue(e.target.value);\n onSearchChange?.(e.target.value);\n }}\n value={searchValue}\n size={validateSizeFormControl(size)}\n />\n )}\n <Form.CheckboxSet\n className=\"pgn__dropdown-filter-checkbox-group\"\n name={filterButtonText}\n aria-label={filterButtonText}\n value={checkedBoxes}\n >\n <span className=\"small text-info-700 mt-2\">\n {formatMessage(messages['authz.table.controlbar.filters.items.showing'], { current: filterChoices.length, total: filterChoices.length })}\n </span>\n {!isGrouped ? filterChoices.map(({\n displayName, value, description,\n }) => (\n <Form.Checkbox\n className=\"m-2 w-100\"\n key={displayName}\n checked={checkedBoxes.includes(value)}\n value={value}\n onChange={() => handleClickCheckbox(value, displayName)}\n aria-label={displayName}\n disabled={checkedBoxes.includes(value) ? false : disabled}\n >\n <div className=\"d-flex flex-column\">\n <span className=\"small\">{displayName}</span>\n { description && <span className=\"small text-muted d-block\">{description}</span> }\n </div>\n </Form.Checkbox>\n ))\n : getGroupedChoices().map(({ groupName, icon, options }) => (\n <div key={groupName}>\n <div className=\"pgn__dropdown-filter-group-name text-info-700 d-flex align-items-center small m-2 ml-0\">\n {icon && <Icon color=\"primary\" src={icon} className=\"mr-2\" size=\"xs\" />}\n <span>{groupName}</span>\n </div>\n {options.map(({ displayName, value, description }) => (\n <Form.Checkbox\n className=\"m-2 w-100\"\n key={displayName}\n value={value}\n onChange={() => handleClickCheckbox(value, displayName)}\n disabled={checkedBoxes.includes(value) ? false : disabled}\n aria-label={displayName}\n >\n <div className=\"d-flex flex-column\">\n <span className=\"small\">{displayName}</span>\n { description && <span className=\"small text-muted d-block\">{description}</span> }\n </div>\n </Form.Checkbox>\n ))}\n </div>\n ))}\n { isSearchable && (\n <div className=\"d-flex align-items-center justify-content-between p-2\">\n <span className=\"text-muted small\">{formatMessage(messages['authz.table.controlbar.filters.more.results'])}</span>\n <Icon className=\"text-gray-300 ml-1\" src={Info} size=\"xs\" />\n </div>\n )}\n </Form.CheckboxSet>\n </Dropdown.Menu>\n\n </Dropdown>\n );\n};\n\nexport default MultipleChoiceFilter;\n"]}
@@ -2,6 +2,7 @@ interface SearchFilterProps {
2
2
  filterValue: string;
3
3
  setFilter: (value: string) => void;
4
4
  placeholder: string;
5
+ size?: 'sm' | 'md' | 'lg';
5
6
  }
6
- declare const SearchFilter: ({ filterValue, setFilter, placeholder, }: SearchFilterProps) => import("react").JSX.Element;
7
+ declare const SearchFilter: ({ filterValue, setFilter, placeholder, size }: SearchFilterProps) => import("react").JSX.Element;
7
8
  export default SearchFilter;
@@ -1,7 +1,8 @@
1
1
  import { jsx as _jsx } from "react/jsx-runtime";
2
2
  import { Form, Icon, } from '@openedx/paragon';
3
3
  import { Search } from '@openedx/paragon/icons';
4
- const SearchFilter = ({ filterValue, setFilter, placeholder, }) => (_jsx(Form.Group, { className: "m-0", children: _jsx(Form.Control, { className: "mw-xs mr-0", trailingElement: _jsx(Icon, { src: Search }), value: filterValue || '', type: "text", onChange: e => {
4
+ import { validateSizeFormControl } from '../../utils';
5
+ const SearchFilter = ({ filterValue, setFilter, placeholder, size = 'sm' }) => (_jsx(Form.Group, { className: "m-0", size: validateSizeFormControl(size), children: _jsx(Form.Control, { className: "mw-xs mr-0", trailingElement: _jsx(Icon, { src: Search }), value: filterValue || '', type: "text", onChange: e => {
5
6
  setFilter(e.target.value || undefined); // Set undefined to remove the filter entirely
6
7
  }, placeholder: placeholder }) }));
7
8
  export default SearchFilter;
@@ -1 +1 @@
1
- {"version":3,"file":"SearchFilter.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/SearchFilter.tsx"],"names":[],"mappings":";AAAA,OAAO,EACL,IAAI,EACJ,IAAI,GACL,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EAAE,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAQhD,MAAM,YAAY,GAAG,CAAC,EACpB,WAAW,EAAE,SAAS,EAAE,WAAW,GACjB,EAAE,EAAE,CAAC,CACvB,KAAC,IAAI,CAAC,KAAK,IAAC,SAAS,EAAC,KAAK,YACzB,KAAC,IAAI,CAAC,OAAO,IACX,SAAS,EAAC,YAAY,EACtB,eAAe,EAAE,KAAC,IAAI,IAAC,GAAG,EAAE,MAAM,GAAI,EACtC,KAAK,EAAE,WAAW,IAAI,EAAE,EACxB,IAAI,EAAC,MAAM,EACX,QAAQ,EAAE,CAAC,CAAC,EAAE;YACZ,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,IAAI,SAAS,CAAC,CAAC,CAAC,8CAA8C;QACxF,CAAC,EACD,WAAW,EAAE,WAAW,GACxB,GACS,CACd,CAAC;AAEF,eAAe,YAAY,CAAC","sourcesContent":["import {\n Form,\n Icon,\n} from '@openedx/paragon';\nimport { Search } from '@openedx/paragon/icons';\n\ninterface SearchFilterProps {\n filterValue: string;\n setFilter: (value: string) => void;\n placeholder: string;\n}\n\nconst SearchFilter = ({\n filterValue, setFilter, placeholder,\n}: SearchFilterProps) => (\n <Form.Group className=\"m-0\">\n <Form.Control\n className=\"mw-xs mr-0\"\n trailingElement={<Icon src={Search} />}\n value={filterValue || ''}\n type=\"text\"\n onChange={e => {\n setFilter(e.target.value || undefined); // Set undefined to remove the filter entirely\n }}\n placeholder={placeholder}\n />\n </Form.Group>\n);\n\nexport default SearchFilter;\n"]}
1
+ {"version":3,"file":"SearchFilter.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/SearchFilter.tsx"],"names":[],"mappings":";AAAA,OAAO,EACL,IAAI,EACJ,IAAI,GACL,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EAAE,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAChD,OAAO,EAAE,uBAAuB,EAAE,MAAM,yBAAyB,CAAC;AASlE,MAAM,YAAY,GAAG,CAAC,EACpB,WAAW,EAAE,SAAS,EAAE,WAAW,EAAE,IAAI,GAAG,IAAI,EAC9B,EAAE,EAAE,CAAC,CACvB,KAAC,IAAI,CAAC,KAAK,IAAC,SAAS,EAAC,KAAK,EAAC,IAAI,EAAE,uBAAuB,CAAC,IAAI,CAAC,YAC7D,KAAC,IAAI,CAAC,OAAO,IACX,SAAS,EAAC,YAAY,EACtB,eAAe,EAAE,KAAC,IAAI,IAAC,GAAG,EAAE,MAAM,GAAI,EACtC,KAAK,EAAE,WAAW,IAAI,EAAE,EACxB,IAAI,EAAC,MAAM,EACX,QAAQ,EAAE,CAAC,CAAC,EAAE;YACZ,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,IAAI,SAAS,CAAC,CAAC,CAAC,8CAA8C;QACxF,CAAC,EACD,WAAW,EAAE,WAAW,GACxB,GACS,CACd,CAAC;AAEF,eAAe,YAAY,CAAC","sourcesContent":["import {\n Form,\n Icon,\n} from '@openedx/paragon';\nimport { Search } from '@openedx/paragon/icons';\nimport { validateSizeFormControl } from '@src/authz-module/utils';\n\ninterface SearchFilterProps {\n filterValue: string;\n setFilter: (value: string) => void;\n placeholder: string;\n size?: 'sm' | 'md' | 'lg';\n}\n\nconst SearchFilter = ({\n filterValue, setFilter, placeholder, size = 'sm'\n}: SearchFilterProps) => (\n <Form.Group className=\"m-0\" size={validateSizeFormControl(size)}>\n <Form.Control\n className=\"mw-xs mr-0\"\n trailingElement={<Icon src={Search} />}\n value={filterValue || ''}\n type=\"text\"\n onChange={e => {\n setFilter(e.target.value || undefined); // Set undefined to remove the filter entirely\n }}\n placeholder={placeholder}\n />\n </Form.Group>\n);\n\nexport default SearchFilter;\n"]}
@@ -15,4 +15,5 @@ export interface MultipleChoiceFilterProps {
15
15
  onSearchChange?: (value: string) => void;
16
16
  iconSrc?: React.ComponentType | undefined;
17
17
  disabled?: boolean;
18
+ size?: 'sm' | 'md' | 'lg' | 'inline';
18
19
  }
@@ -1 +1 @@
1
- {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/types.ts"],"names":[],"mappings":"","sourcesContent":["export interface FilterChoice {\n groupName?: string;\n groupIcon?: React.ComponentType;\n displayName: string;\n value: string;\n description?: string;\n}\n\nexport interface MultipleChoiceFilterProps {\n filterButtonText: string;\n filterChoices: FilterChoice[];\n filterValue: string[] | undefined;\n setFilter: (value: string[], newItem: FilterChoice) => void;\n isGrouped?: boolean;\n isSearchable?: boolean;\n onSearchChange?: (value: string) => void;\n iconSrc?: React.ComponentType | undefined;\n disabled?: boolean;\n}\n"]}
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../../src/authz-module/components/TableControlBar/types.ts"],"names":[],"mappings":"","sourcesContent":["export interface FilterChoice {\n groupName?: string;\n groupIcon?: React.ComponentType;\n displayName: string;\n value: string;\n description?: string;\n}\n\nexport interface MultipleChoiceFilterProps {\n filterButtonText: string;\n filterChoices: FilterChoice[];\n filterValue: string[] | undefined;\n setFilter: (value: string[], newItem: FilterChoice) => void;\n isGrouped?: boolean;\n isSearchable?: boolean;\n onSearchChange?: (value: string) => void;\n iconSrc?: React.ComponentType | undefined;\n disabled?: boolean;\n size?: 'sm' | 'md' | 'lg' | 'inline';\n}\n"]}
@@ -3,8 +3,20 @@
3
3
  .authz-module {
4
4
  --height-action-divider: 30px;
5
5
 
6
- .pgn__data-table-wrapper {
7
- padding: 1rem;
6
+ // Paragon scrolls the layout wrapper ≤1400px, which clips the table's box-shadow;
7
+ // the inner .pgn__data-table-container already handles horizontal scroll.
8
+ .pgn__data-table-layout-wrapper {
9
+ overflow-x: visible;
10
+
11
+ // A flex item won't shrink below its content by default, so without this the main
12
+ // column grows to the table's width and the inner container never gets to scroll.
13
+ .pgn__data-table-layout-main {
14
+ min-width: 0;
15
+ }
16
+ }
17
+
18
+ .title-border-bottom {
19
+ border-bottom: var(--pgn-size-nav-tabs-border-width) solid var(--pgn-color-nav-tabs-base-border-base);
8
20
  }
9
21
 
10
22
  .filters .dropdown-toggle::after {
@@ -57,9 +69,23 @@
57
69
  }
58
70
 
59
71
  .permission-table {
72
+ border-collapse: separate;
73
+ border-spacing: 0;
74
+
60
75
  td {
61
76
  line-height: 24px;
62
77
  }
78
+
79
+ thead th::after {
80
+ content: '';
81
+ position: absolute;
82
+ top: 100%;
83
+ left: 0;
84
+ right: 0;
85
+ height: 6px;
86
+ background: linear-gradient(rgba(0, 0, 0, 0.15), transparent);
87
+ pointer-events: none;
88
+ }
63
89
  }
64
90
 
65
91
  // Paragon's `.overflow-auto` lives in the `paragon` cascade layer, where its `!important`
@@ -1,7 +1,7 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
2
  import { useMemo, useState } from 'react';
3
3
  import { useIntl } from '@openedx/frontend-base';
4
- import { Alert, Button, ButtonGroup, Container, Hyperlink, } from '@openedx/paragon';
4
+ import { Alert, Button, ButtonGroup, Card, Hyperlink, } from '@openedx/paragon';
5
5
  import { coursePermissions, courseResourceTypes, courseRolesWithPermissions, } from './course/constants';
6
6
  import { libraryRolesWithPermissions, libraryPermissions, libraryResourceTypes, } from './library/constants';
7
7
  import AnchorButton from '../components/AnchorButton';
@@ -29,7 +29,7 @@ const RolesPermissions = () => {
29
29
  });
30
30
  return permissionsByResource;
31
31
  }, [intl]);
32
- return (_jsxs(_Fragment, { children: [_jsx(Container, { className: "pb-5", children: _jsxs(ButtonGroup, { size: "lg", className: "mb-2", children: [_jsx(Button, { onClick: () => setActive('courses'), variant: `${active === 'courses' ? 'primary' : 'outline-primary'}`, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab']) }), _jsx(Button, { onClick: () => setActive('libraries'), variant: `${active === 'libraries' ? 'primary' : 'outline-primary'}`, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab']) })] }) }), active === 'courses' && (_jsxs("div", { className: "position-relative", children: [_jsx(PermissionTable, { permissionsTable: coursePermissionsByResource, roles: courseRolesWithPermissions, title: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab.title']) }), _jsx(Alert, { variant: "info", className: "mt-5", children: _jsxs("div", { className: "row align-items-center", children: [_jsxs("div", { className: "col-12 col-md-7", children: [_jsx("p", { className: "text-primary font-weight-bold h4", children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.title']) }), _jsxs("span", { children: [_jsx("span", { className: "font-weight-bold", children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.note']) }), intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.description'])] })] }), _jsx("div", { className: "col-12 col-md-5 mt-3 mt-md-0", children: _jsx(Hyperlink, { className: "d-block text-right h5 font-weight-normal", destination: "https://docs.openedx.org/en/latest/educators/references/course_development/course_team_roles.html", target: "_blank", showLaunchIcon: false, isInline: true, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.link']) }) })] }) })] })), active === 'libraries' && (_jsx(PermissionTable, { permissionsTable: libraryPermissionsByResource, roles: libraryRolesWithPermissions, title: intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab.title']) })), _jsx(AnchorButton, {})] }));
32
+ return (_jsxs(_Fragment, { children: [_jsxs(Card, { className: "bg-light-200", children: [_jsx("div", { className: "px-3 py-4", children: _jsxs(ButtonGroup, { size: "md", children: [_jsx(Button, { onClick: () => setActive('courses'), variant: `${active === 'courses' ? 'primary' : 'outline-primary'}`, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab']) }), _jsx(Button, { onClick: () => setActive('libraries'), variant: `${active === 'libraries' ? 'primary' : 'outline-primary'}`, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab']) })] }) }), active === 'courses' && (_jsx("div", { className: "position-relative", children: _jsx(PermissionTable, { permissionsTable: coursePermissionsByResource, roles: courseRolesWithPermissions, title: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab.title']) }) })), active === 'libraries' && (_jsx(PermissionTable, { permissionsTable: libraryPermissionsByResource, roles: libraryRolesWithPermissions, title: intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab.title']) }))] }), active === 'courses' && (_jsx(Alert, { variant: "info", className: "mt-5", children: _jsxs("div", { className: "row align-items-center", children: [_jsxs("div", { className: "col-12 col-md-7", children: [_jsx("p", { className: "text-primary font-weight-bold h4", children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.title']) }), _jsxs("span", { children: [_jsx("span", { className: "font-weight-bold", children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.note']) }), intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.description'])] })] }), _jsx("div", { className: "col-12 col-md-5 mt-3 mt-md-0", children: _jsx(Hyperlink, { className: "d-block text-right h5 font-weight-normal", destination: "https://docs.openedx.org/en/latest/educators/references/course_development/course_team_roles.html", target: "_blank", showLaunchIcon: false, isInline: true, children: intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.link']) }) })] }) })), _jsx(AnchorButton, {})] }));
33
33
  };
34
34
  export default RolesPermissions;
35
35
  //# sourceMappingURL=RolesPermissions.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"RolesPermissions.js","sourceRoot":"","sources":["../../../src/authz-module/roles-permissions/RolesPermissions.tsx"],"names":[],"mappings":"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","sourcesContent":["import { useMemo, useState } from 'react';\nimport { useIntl } from '@openedx/frontend-base';\nimport {\n Alert,\n Button,\n ButtonGroup,\n Container, Hyperlink,\n} from '@openedx/paragon';\n\nimport {\n coursePermissions,\n courseResourceTypes,\n courseRolesWithPermissions,\n} from './course/constants';\nimport {\n libraryRolesWithPermissions,\n libraryPermissions,\n libraryResourceTypes,\n} from './library/constants';\nimport AnchorButton from '@src/authz-module/components/AnchorButton';\nimport PermissionTable from '@src/authz-module/components/PermissionTable';\n\nimport { buildPermissionMatrixByResource } from './utils';\n\nimport messages from './messages';\n\nconst RolesPermissions = () => {\n const intl = useIntl();\n const [active, setActive] = useState('courses');\n\n const libraryPermissionsByResource = useMemo(() => {\n const permissionsByResource = buildPermissionMatrixByResource({\n roles: libraryRolesWithPermissions,\n permissions: libraryPermissions,\n resources: libraryResourceTypes,\n intl,\n });\n\n return permissionsByResource;\n }, [intl]);\n\n const coursePermissionsByResource = useMemo(() => {\n const permissionsByResource = buildPermissionMatrixByResource({\n roles: courseRolesWithPermissions,\n permissions: coursePermissions,\n resources: courseResourceTypes,\n intl,\n });\n\n return permissionsByResource;\n }, [intl]);\n\n return (\n <>\n <Container className=\"pb-5\">\n <ButtonGroup size=\"lg\" className=\"mb-2\">\n <Button\n onClick={() => setActive('courses')}\n variant={`${active === 'courses' ? 'primary' : 'outline-primary'}`}\n >\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab']) }\n </Button>\n <Button\n onClick={() => setActive('libraries')}\n variant={`${active === 'libraries' ? 'primary' : 'outline-primary'}`}\n >\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab']) }\n </Button>\n </ButtonGroup>\n </Container>\n {/* Courses */}\n { active === 'courses' && (\n <div className=\"position-relative\">\n <PermissionTable\n permissionsTable={coursePermissionsByResource}\n roles={courseRolesWithPermissions}\n title={intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab.title'])}\n />\n <Alert\n variant=\"info\"\n className=\"mt-5\"\n >\n <div className=\"row align-items-center\">\n <div className=\"col-12 col-md-7\">\n <p className=\"text-primary font-weight-bold h4\">{intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.title'])}</p>\n <span>\n <span className=\"font-weight-bold\">{intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.note'])}</span>\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.description'])}\n </span>\n </div>\n <div className=\"col-12 col-md-5 mt-3 mt-md-0\">\n <Hyperlink className=\"d-block text-right h5 font-weight-normal\" destination=\"https://docs.openedx.org/en/latest/educators/references/course_development/course_team_roles.html\" target=\"_blank\" showLaunchIcon={false} isInline>\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.link'])}\n </Hyperlink>\n </div>\n </div>\n </Alert>\n </div>\n )}\n {/* Libraries */}\n { active === 'libraries' && (\n <PermissionTable\n permissionsTable={libraryPermissionsByResource}\n roles={libraryRolesWithPermissions}\n title={intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab.title'])}\n />\n )}\n <AnchorButton />\n </>\n );\n};\n\nexport default RolesPermissions;\n"]}
1
+ {"version":3,"file":"RolesPermissions.js","sourceRoot":"","sources":["../../../src/authz-module/roles-permissions/RolesPermissions.tsx"],"names":[],"mappings":"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","sourcesContent":["import { useMemo, useState } from 'react';\nimport { useIntl } from '@openedx/frontend-base';\nimport {\n Alert,\n Button,\n ButtonGroup,\n Card,\n Hyperlink,\n} from '@openedx/paragon';\n\nimport {\n coursePermissions,\n courseResourceTypes,\n courseRolesWithPermissions,\n} from './course/constants';\nimport {\n libraryRolesWithPermissions,\n libraryPermissions,\n libraryResourceTypes,\n} from './library/constants';\nimport AnchorButton from '@src/authz-module/components/AnchorButton';\nimport PermissionTable from '@src/authz-module/components/PermissionTable';\n\nimport { buildPermissionMatrixByResource } from './utils';\n\nimport messages from './messages';\n\nconst RolesPermissions = () => {\n const intl = useIntl();\n const [active, setActive] = useState('courses');\n\n const libraryPermissionsByResource = useMemo(() => {\n const permissionsByResource = buildPermissionMatrixByResource({\n roles: libraryRolesWithPermissions,\n permissions: libraryPermissions,\n resources: libraryResourceTypes,\n intl,\n });\n\n return permissionsByResource;\n }, [intl]);\n\n const coursePermissionsByResource = useMemo(() => {\n const permissionsByResource = buildPermissionMatrixByResource({\n roles: courseRolesWithPermissions,\n permissions: coursePermissions,\n resources: courseResourceTypes,\n intl,\n });\n\n return permissionsByResource;\n }, [intl]);\n\n return (\n <>\n <Card className=\"bg-light-200\">\n <div className=\"px-3 py-4\">\n <ButtonGroup size=\"md\">\n <Button\n onClick={() => setActive('courses')}\n variant={`${active === 'courses' ? 'primary' : 'outline-primary'}`}\n >\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab'])}\n </Button>\n <Button\n onClick={() => setActive('libraries')}\n variant={`${active === 'libraries' ? 'primary' : 'outline-primary'}`}\n >\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab'])}\n </Button>\n </ButtonGroup>\n </div>\n {/* Courses */}\n {active === 'courses' && (\n <div className=\"position-relative\">\n <PermissionTable\n permissionsTable={coursePermissionsByResource}\n roles={courseRolesWithPermissions}\n title={intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.tab.title'])}\n />\n </div>\n )}\n {/* Libraries */}\n {active === 'libraries' && (\n <PermissionTable\n permissionsTable={libraryPermissionsByResource}\n roles={libraryRolesWithPermissions}\n title={intl.formatMessage(messages['authz.tabs.permissionsRoles.libraries.tab.title'])}\n />\n )}\n </Card>\n {active === 'courses' && (\n <Alert\n variant=\"info\"\n className=\"mt-5\"\n >\n <div className=\"row align-items-center\">\n <div className=\"col-12 col-md-7\">\n <p className=\"text-primary font-weight-bold h4\">{intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.title'])}</p>\n <span>\n <span className=\"font-weight-bold\">{intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.note'])}</span>\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.description'])}\n </span>\n </div>\n <div className=\"col-12 col-md-5 mt-3 mt-md-0\">\n <Hyperlink className=\"d-block text-right h5 font-weight-normal\" destination=\"https://docs.openedx.org/en/latest/educators/references/course_development/course_team_roles.html\" target=\"_blank\" showLaunchIcon={false} isInline>\n {intl.formatMessage(messages['authz.tabs.permissionsRoles.courses.alert.link'])}\n </Hyperlink>\n </div>\n </div>\n </Alert>\n )}\n <AnchorButton />\n </>\n );\n};\n\nexport default RolesPermissions;\n"]}
@@ -27,3 +27,4 @@ export declare const getScopeManageActionPermission: (scope: string) => {
27
27
  action: string;
28
28
  scope: string;
29
29
  };
30
+ export declare const validateSizeFormControl: (size: any) => any;
@@ -42,4 +42,6 @@ export const getScopeManageActionPermission = (scope) => {
42
42
  scope,
43
43
  };
44
44
  };
45
+ // "md" is mapped to undefined because Paragon's Form.Control has no "md" size.
46
+ export const validateSizeFormControl = (size) => size === 'md' ? undefined : size;
45
47
  //# sourceMappingURL=utils.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"utils.js","sourceRoot":"","sources":["../../src/authz-module/utils.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AACxC,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AACpD,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AACxD,OAAO,EAAE,aAAa,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACjE,OAAO,EAAE,0BAA0B,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AAE9F;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,MAAM,aAAa,GAAG,CAAC,QAAgB,EAAE,WAAmB,EAAE,cAAwB,EAAE,EAAE;IAC/F,IAAI,cAAc,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC;QACtC,MAAM,cAAc,GAAG,GAAG,EAAE,CAAC,CAC3B,gBAAM,SAAS,EAAC,oCAAoC,aAClD,KAAC,IAAI,IAAC,GAAG,EAAE,UAAU,EAAE,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,MAAM,GAAG,EACnD,WAAW,IACP,CACR,CAAC;QACF,cAAc,CAAC,WAAW,GAAG,kBAAkB,QAAQ,EAAE,CAAC;QAC1D,cAAc,CAAC,QAAQ,GAAG,GAAG,EAAE,CAAC,kBAAkB,QAAQ,EAAE,CAAC;QAC7D,OAAO,cAAc,CAAC;IACxB,CAAC;IACD,OAAO,WAAW,CAAC;AACrB,CAAC,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,MAAM,oBAAoB,GAAG,CAAC,KAAa,EAAE,EAAE,CAAC,CACrD,mBAAmB,CAAC,KAAK,CAAC,KAAK,aAAa,CAAC,OAAO,CAAC,CAAC,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,cAAc,CAAC,MAAM,CACtG,CAAC;AAEF,6FAA6F;AAC7F,MAAM,CAAC,MAAM,oBAAoB,GAAG,CAAC,KAAa,EAAE,EAAE,CAAC,CACrD,mBAAmB,CAAC,KAAK,CAAC,KAAK,aAAa,CAAC,OAAO;IAClD,CAAC,CAAC,2BAA2B,CAAC,mBAAmB;IACjD,CAAC,CAAC,0BAA0B,CAAC,kBAAkB,CAClD,CAAC;AAEF,MAAM,CAAC,MAAM,8BAA8B,GAAG,CAAC,KAAa,EAAE,EAAE;IAC9D,MAAM,MAAM,GAAG,oBAAoB,CAAC,KAAK,CAAC,CAAC;IAC3C,OAAO;QACL,MAAM;QACN,KAAK;KACN,CAAC;AACJ,CAAC,CAAC","sourcesContent":["import { Icon } from '@openedx/paragon';\nimport { FilterList } from '@openedx/paragon/icons';\nimport { RESOURCE_ICONS } from './components/constants';\nimport { CONTEXT_TYPES, getScopeContextType } from './constants';\nimport { CONTENT_COURSE_PERMISSIONS, CONTENT_LIBRARY_PERMISSIONS } from './roles-permissions';\n\n/**\n * Returns a header value for a DataTable column that shows a filter icon\n * when the column has an active filter.\n *\n * When a filter is active, returns a **component function** with a custom\n * toString() override. This is necessary because Paragon's TableRow builds\n * cell keys via: `${cell.column.Header}${row.id}`\n *\n * - A JSX element stringifies to \"[object Object]\", causing duplicate keys.\n * - A function with a custom toString() produces a unique string per column.\n *\n * react-table's render('Header') calls the function as a component, so the\n * JSX is still rendered correctly in the table header.\n */\nexport const getCellHeader = (columnId: string, columnTitle: string, filtersApplied: string[]) => {\n if (filtersApplied.includes(columnId)) {\n const FilteredHeader = () => (\n <span className=\"d-flex flex-row align-items-center\">\n <Icon src={FilterList} size=\"sm\" className=\"mr-2\" />\n {columnTitle}\n </span>\n );\n FilteredHeader.displayName = `FilteredHeader_${columnId}`;\n FilteredHeader.toString = () => `FilteredHeader_${columnId}`;\n return FilteredHeader;\n }\n return columnTitle;\n};\n\n/**\n * Picks the course or library icon for a scope from the scope key itself.\n */\nexport const getScopeResourceIcon = (scope: string) => (\n getScopeContextType(scope) === CONTEXT_TYPES.LIBRARY ? RESOURCE_ICONS.LIBRARY : RESOURCE_ICONS.COURSE\n);\n\n/** Unrecognised scopes fall back to the course permission, as `getScopeContextType` does. */\nexport const getScopeManageAction = (scope: string) => (\n getScopeContextType(scope) === CONTEXT_TYPES.LIBRARY\n ? CONTENT_LIBRARY_PERMISSIONS.MANAGE_LIBRARY_TEAM\n : CONTENT_COURSE_PERMISSIONS.MANAGE_COURSE_TEAM\n);\n\nexport const getScopeManageActionPermission = (scope: string) => {\n const action = getScopeManageAction(scope);\n return {\n action,\n scope,\n };\n};\n"]}
1
+ {"version":3,"file":"utils.js","sourceRoot":"","sources":["../../src/authz-module/utils.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AACxC,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AACpD,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAC;AACxD,OAAO,EAAE,aAAa,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACjE,OAAO,EAAE,0BAA0B,EAAE,2BAA2B,EAAE,MAAM,qBAAqB,CAAC;AAE9F;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,MAAM,aAAa,GAAG,CAAC,QAAgB,EAAE,WAAmB,EAAE,cAAwB,EAAE,EAAE;IAC/F,IAAI,cAAc,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC;QACtC,MAAM,cAAc,GAAG,GAAG,EAAE,CAAC,CAC3B,gBAAM,SAAS,EAAC,oCAAoC,aAClD,KAAC,IAAI,IAAC,GAAG,EAAE,UAAU,EAAE,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,MAAM,GAAG,EACnD,WAAW,IACP,CACR,CAAC;QACF,cAAc,CAAC,WAAW,GAAG,kBAAkB,QAAQ,EAAE,CAAC;QAC1D,cAAc,CAAC,QAAQ,GAAG,GAAG,EAAE,CAAC,kBAAkB,QAAQ,EAAE,CAAC;QAC7D,OAAO,cAAc,CAAC;IACxB,CAAC;IACD,OAAO,WAAW,CAAC;AACrB,CAAC,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,MAAM,oBAAoB,GAAG,CAAC,KAAa,EAAE,EAAE,CAAC,CACrD,mBAAmB,CAAC,KAAK,CAAC,KAAK,aAAa,CAAC,OAAO,CAAC,CAAC,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC,cAAc,CAAC,MAAM,CACtG,CAAC;AAEF,6FAA6F;AAC7F,MAAM,CAAC,MAAM,oBAAoB,GAAG,CAAC,KAAa,EAAE,EAAE,CAAC,CACrD,mBAAmB,CAAC,KAAK,CAAC,KAAK,aAAa,CAAC,OAAO;IAClD,CAAC,CAAC,2BAA2B,CAAC,mBAAmB;IACjD,CAAC,CAAC,0BAA0B,CAAC,kBAAkB,CAClD,CAAC;AAEF,MAAM,CAAC,MAAM,8BAA8B,GAAG,CAAC,KAAa,EAAE,EAAE;IAC9D,MAAM,MAAM,GAAG,oBAAoB,CAAC,KAAK,CAAC,CAAC;IAC3C,OAAO;QACL,MAAM;QACN,KAAK;KACN,CAAC;AACJ,CAAC,CAAC;AAEF,+EAA+E;AAC/E,MAAM,CAAC,MAAM,uBAAuB,GAAG,CAAC,IAAI,EAAE,EAAE,CAC9C,IAAI,KAAK,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC","sourcesContent":["import { Icon } from '@openedx/paragon';\nimport { FilterList } from '@openedx/paragon/icons';\nimport { RESOURCE_ICONS } from './components/constants';\nimport { CONTEXT_TYPES, getScopeContextType } from './constants';\nimport { CONTENT_COURSE_PERMISSIONS, CONTENT_LIBRARY_PERMISSIONS } from './roles-permissions';\n\n/**\n * Returns a header value for a DataTable column that shows a filter icon\n * when the column has an active filter.\n *\n * When a filter is active, returns a **component function** with a custom\n * toString() override. This is necessary because Paragon's TableRow builds\n * cell keys via: `${cell.column.Header}${row.id}`\n *\n * - A JSX element stringifies to \"[object Object]\", causing duplicate keys.\n * - A function with a custom toString() produces a unique string per column.\n *\n * react-table's render('Header') calls the function as a component, so the\n * JSX is still rendered correctly in the table header.\n */\nexport const getCellHeader = (columnId: string, columnTitle: string, filtersApplied: string[]) => {\n if (filtersApplied.includes(columnId)) {\n const FilteredHeader = () => (\n <span className=\"d-flex flex-row align-items-center\">\n <Icon src={FilterList} size=\"sm\" className=\"mr-2\" />\n {columnTitle}\n </span>\n );\n FilteredHeader.displayName = `FilteredHeader_${columnId}`;\n FilteredHeader.toString = () => `FilteredHeader_${columnId}`;\n return FilteredHeader;\n }\n return columnTitle;\n};\n\n/**\n * Picks the course or library icon for a scope from the scope key itself.\n */\nexport const getScopeResourceIcon = (scope: string) => (\n getScopeContextType(scope) === CONTEXT_TYPES.LIBRARY ? RESOURCE_ICONS.LIBRARY : RESOURCE_ICONS.COURSE\n);\n\n/** Unrecognised scopes fall back to the course permission, as `getScopeContextType` does. */\nexport const getScopeManageAction = (scope: string) => (\n getScopeContextType(scope) === CONTEXT_TYPES.LIBRARY\n ? CONTENT_LIBRARY_PERMISSIONS.MANAGE_LIBRARY_TEAM\n : CONTENT_COURSE_PERMISSIONS.MANAGE_COURSE_TEAM\n);\n\nexport const getScopeManageActionPermission = (scope: string) => {\n const action = getScopeManageAction(scope);\n return {\n action,\n scope,\n };\n};\n\n// \"md\" is mapped to undefined because Paragon's Form.Control has no \"md\" size.\nexport const validateSizeFormControl = (size) =>\n size === 'md' ? undefined : size;\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@openedx/frontend-app-admin-console",
3
- "version": "1.0.0-alpha.7",
3
+ "version": "1.0.0-alpha.9",
4
4
  "description": "Frontend Admin Console",
5
5
  "packageManager": "npm@11.12.1",
6
6
  "repository": {