mirror of
https://github.com/grafana/grafana.git
synced 2024-11-24 09:50:29 -06:00
RBAC: Remove builtin role code (#53767)
* remove rbacBuiltInRoleAssignmentEnabled from frontendsettings * RBAC: Remove RBACBuiltInRoleAssignmentEnabled * RBAC: Remove code for builtin role * RolePicker: Remove unused prop * RolePicker: Rename builtinRole to basicRole * RolePicker: Rename onBuiltinRoleChange to onBasicRoleChange * RolePicker: Rename properties
This commit is contained in:
parent
8145caf554
commit
4ff4aaab23
@ -182,7 +182,6 @@ export interface GrafanaConfig {
|
||||
verifyEmailEnabled: boolean;
|
||||
oauth: OAuthSettings;
|
||||
rbacEnabled: boolean;
|
||||
rbacBuiltInRoleAssignmentEnabled: boolean;
|
||||
disableUserSignUp: boolean;
|
||||
loginHint: string;
|
||||
passwordHint: string;
|
||||
|
@ -62,7 +62,6 @@ export class GrafanaBootConfig implements GrafanaConfig {
|
||||
verifyEmailEnabled = false;
|
||||
oauth: OAuthSettings = {};
|
||||
rbacEnabled = true;
|
||||
rbacBuiltInRoleAssignmentEnabled = false;
|
||||
disableUserSignUp = false;
|
||||
loginHint = '';
|
||||
passwordHint = '';
|
||||
|
@ -112,7 +112,6 @@ func (hs *HTTPServer) getFrontendSettingsMap(c *models.ReqContext) (map[string]i
|
||||
"sigV4AuthEnabled": setting.SigV4AuthEnabled,
|
||||
"azureAuthEnabled": setting.AzureAuthEnabled,
|
||||
"rbacEnabled": hs.Cfg.RBACEnabled,
|
||||
"rbacBuiltInRoleAssignmentEnabled": hs.Cfg.RBACBuiltInRoleAssignmentEnabled,
|
||||
"exploreEnabled": setting.ExploreEnabled,
|
||||
"helpEnabled": setting.HelpEnabled,
|
||||
"profileEnabled": setting.ProfileEnabled,
|
||||
|
@ -272,16 +272,9 @@ func IsDisabled(cfg *setting.Cfg) bool {
|
||||
}
|
||||
|
||||
// GetOrgRoles returns legacy org roles for a user
|
||||
func GetOrgRoles(cfg *setting.Cfg, user *user.SignedInUser) []string {
|
||||
func GetOrgRoles(user *user.SignedInUser) []string {
|
||||
roles := []string{string(user.OrgRole)}
|
||||
|
||||
// With built-in role simplifying, inheritance is performed upon role registration.
|
||||
if cfg.RBACBuiltInRoleAssignmentEnabled {
|
||||
for _, br := range user.OrgRole.Children() {
|
||||
roles = append(roles, string(br))
|
||||
}
|
||||
}
|
||||
|
||||
if user.IsGrafanaAdmin {
|
||||
roles = append(roles, RoleGrafanaAdmin)
|
||||
}
|
||||
|
@ -112,7 +112,7 @@ func (ac *OSSAccessControlService) GetUserPermissions(ctx context.Context, user
|
||||
dbPermissions, err := ac.store.GetUserPermissions(ctx, accesscontrol.GetUserPermissionsQuery{
|
||||
OrgID: user.OrgID,
|
||||
UserID: user.UserID,
|
||||
Roles: accesscontrol.GetOrgRoles(ac.cfg, user),
|
||||
Roles: accesscontrol.GetOrgRoles(user),
|
||||
TeamIDs: user.Teams,
|
||||
Actions: actionsToFetch,
|
||||
})
|
||||
@ -136,7 +136,7 @@ func (ac *OSSAccessControlService) GetUserPermissions(ctx context.Context, user
|
||||
func (ac *OSSAccessControlService) getFixedPermissions(ctx context.Context, user *user.SignedInUser) []accesscontrol.Permission {
|
||||
permissions := make([]accesscontrol.Permission, 0)
|
||||
|
||||
for _, builtin := range accesscontrol.GetOrgRoles(ac.cfg, user) {
|
||||
for _, builtin := range accesscontrol.GetOrgRoles(user) {
|
||||
if basicRole, ok := ac.roles[builtin]; ok {
|
||||
permissions = append(permissions, basicRole.Permissions...)
|
||||
}
|
||||
|
@ -451,9 +451,6 @@ type Cfg struct {
|
||||
// Access Control
|
||||
RBACEnabled bool
|
||||
RBACPermissionCache bool
|
||||
// Undocumented option as a backup in case removing builtin-role assignment
|
||||
// fails
|
||||
RBACBuiltInRoleAssignmentEnabled bool
|
||||
}
|
||||
|
||||
type CommandLineArgs struct {
|
||||
@ -1356,7 +1353,6 @@ func readAccessControlSettings(iniFile *ini.File, cfg *Cfg) {
|
||||
rbac := iniFile.Section("rbac")
|
||||
cfg.RBACEnabled = rbac.Key("enabled").MustBool(true)
|
||||
cfg.RBACPermissionCache = rbac.Key("permission_cache").MustBool(true)
|
||||
cfg.RBACBuiltInRoleAssignmentEnabled = rbac.Key("builtin_role_assignment_enabled").MustBool(false)
|
||||
}
|
||||
|
||||
func readUserSettings(iniFile *ini.File, cfg *Cfg) error {
|
||||
|
@ -8,44 +8,43 @@ import { RolePickerMenu } from './RolePickerMenu';
|
||||
import { MENU_MAX_HEIGHT, ROLE_PICKER_WIDTH } from './constants';
|
||||
|
||||
export interface Props {
|
||||
builtInRole?: OrgRole;
|
||||
basicRole?: OrgRole;
|
||||
appliedRoles: Role[];
|
||||
roleOptions: Role[];
|
||||
builtInRoles?: Record<string, Role[]>;
|
||||
isLoading?: boolean;
|
||||
disabled?: boolean;
|
||||
builtinRolesDisabled?: boolean;
|
||||
showBuiltInRole?: boolean;
|
||||
basicRoleDisabled?: boolean;
|
||||
showBasicRole?: boolean;
|
||||
onRolesChange: (newRoles: Role[]) => void;
|
||||
onBuiltinRoleChange?: (newRole: OrgRole) => void;
|
||||
onBasicRoleChange?: (newRole: OrgRole) => void;
|
||||
canUpdateRoles?: boolean;
|
||||
apply?: boolean;
|
||||
}
|
||||
|
||||
export const RolePicker = ({
|
||||
builtInRole,
|
||||
basicRole,
|
||||
appliedRoles,
|
||||
roleOptions,
|
||||
disabled,
|
||||
isLoading,
|
||||
builtinRolesDisabled,
|
||||
showBuiltInRole,
|
||||
basicRoleDisabled,
|
||||
showBasicRole,
|
||||
onRolesChange,
|
||||
onBuiltinRoleChange,
|
||||
onBasicRoleChange,
|
||||
canUpdateRoles = true,
|
||||
apply = false,
|
||||
}: Props): JSX.Element | null => {
|
||||
const [isOpen, setOpen] = useState(false);
|
||||
const [selectedRoles, setSelectedRoles] = useState<Role[]>(appliedRoles);
|
||||
const [selectedBuiltInRole, setSelectedBuiltInRole] = useState<OrgRole | undefined>(builtInRole);
|
||||
const [selectedBuiltInRole, setSelectedBuiltInRole] = useState<OrgRole | undefined>(basicRole);
|
||||
const [query, setQuery] = useState('');
|
||||
const [offset, setOffset] = useState({ vertical: 0, horizontal: 0 });
|
||||
const ref = useRef<HTMLDivElement>(null);
|
||||
|
||||
useEffect(() => {
|
||||
setSelectedBuiltInRole(builtInRole);
|
||||
setSelectedBuiltInRole(basicRole);
|
||||
setSelectedRoles(appliedRoles);
|
||||
}, [appliedRoles, builtInRole]);
|
||||
}, [appliedRoles, basicRole]);
|
||||
|
||||
useEffect(() => {
|
||||
const dimensions = ref?.current?.getBoundingClientRect();
|
||||
@ -85,8 +84,8 @@ export const RolePicker = ({
|
||||
setOpen(false);
|
||||
setQuery('');
|
||||
setSelectedRoles(appliedRoles);
|
||||
setSelectedBuiltInRole(builtInRole);
|
||||
}, [appliedRoles, builtInRole]);
|
||||
setSelectedBuiltInRole(basicRole);
|
||||
}, [appliedRoles, basicRole]);
|
||||
|
||||
// Only call onClose if menu is open. Prevent unnecessary calls for multiple pickers on the page.
|
||||
const onClickOutside = () => isOpen && onClose();
|
||||
@ -103,13 +102,13 @@ export const RolePicker = ({
|
||||
setSelectedRoles(roles);
|
||||
};
|
||||
|
||||
const onBuiltInRoleSelect = (role: OrgRole) => {
|
||||
const onBasicRoleSelect = (role: OrgRole) => {
|
||||
setSelectedBuiltInRole(role);
|
||||
};
|
||||
|
||||
const onUpdate = (newRoles: Role[], newBuiltInRole?: OrgRole) => {
|
||||
if (onBuiltinRoleChange && newBuiltInRole && newBuiltInRole !== builtInRole) {
|
||||
onBuiltinRoleChange(newBuiltInRole);
|
||||
if (onBasicRoleChange && newBuiltInRole && newBuiltInRole !== basicRole) {
|
||||
onBasicRoleChange(newBuiltInRole);
|
||||
}
|
||||
if (canUpdateRoles) {
|
||||
onRolesChange(newRoles);
|
||||
@ -141,7 +140,7 @@ export const RolePicker = ({
|
||||
<div data-testid="role-picker" style={{ position: 'relative', width: ROLE_PICKER_WIDTH }} ref={ref}>
|
||||
<ClickOutsideWrapper onClick={onClickOutside}>
|
||||
<RolePickerInput
|
||||
builtInRole={selectedBuiltInRole}
|
||||
basicRole={selectedBuiltInRole}
|
||||
appliedRoles={selectedRoles}
|
||||
query={query}
|
||||
onQueryChange={onInputChange}
|
||||
@ -149,20 +148,20 @@ export const RolePicker = ({
|
||||
onClose={onClose}
|
||||
isFocused={isOpen}
|
||||
disabled={disabled}
|
||||
showBuiltInRole={showBuiltInRole}
|
||||
showBasicRole={showBasicRole}
|
||||
/>
|
||||
{isOpen && (
|
||||
<RolePickerMenu
|
||||
options={getOptions()}
|
||||
builtInRole={selectedBuiltInRole}
|
||||
basicRole={selectedBuiltInRole}
|
||||
appliedRoles={appliedRoles}
|
||||
onBuiltInRoleSelect={onBuiltInRoleSelect}
|
||||
onBasicRoleSelect={onBasicRoleSelect}
|
||||
onSelect={onSelect}
|
||||
onUpdate={onUpdate}
|
||||
showGroups={query.length === 0 || query.trim() === ''}
|
||||
builtinRolesDisabled={builtinRolesDisabled}
|
||||
showBuiltInRole={showBuiltInRole}
|
||||
updateDisabled={builtinRolesDisabled && !canUpdateRoles}
|
||||
basicRoleDisabled={basicRoleDisabled}
|
||||
showBasicRole={showBasicRole}
|
||||
updateDisabled={basicRoleDisabled && !canUpdateRoles}
|
||||
apply={apply}
|
||||
offset={offset}
|
||||
/>
|
||||
|
@ -13,9 +13,9 @@ const stopPropagation = (event: React.MouseEvent<HTMLDivElement>) => event.stopP
|
||||
|
||||
interface InputProps extends HTMLProps<HTMLInputElement> {
|
||||
appliedRoles: Role[];
|
||||
builtInRole?: string;
|
||||
basicRole?: string;
|
||||
query: string;
|
||||
showBuiltInRole?: boolean;
|
||||
showBasicRole?: boolean;
|
||||
isFocused?: boolean;
|
||||
disabled?: boolean;
|
||||
onQueryChange: (query?: string) => void;
|
||||
@ -25,11 +25,11 @@ interface InputProps extends HTMLProps<HTMLInputElement> {
|
||||
|
||||
export const RolePickerInput = ({
|
||||
appliedRoles,
|
||||
builtInRole,
|
||||
basicRole,
|
||||
disabled,
|
||||
isFocused,
|
||||
query,
|
||||
showBuiltInRole,
|
||||
showBasicRole,
|
||||
onOpen,
|
||||
onClose,
|
||||
onQueryChange,
|
||||
@ -53,12 +53,12 @@ export const RolePickerInput = ({
|
||||
|
||||
return !isFocused ? (
|
||||
<div className={cx(styles.wrapper, styles.selectedRoles)} onMouseDown={onOpen}>
|
||||
{showBuiltInRole && <ValueContainer>{builtInRole}</ValueContainer>}
|
||||
<RolesLabel appliedRoles={appliedRoles} numberOfRoles={numberOfRoles} showBuiltInRole={showBuiltInRole} />
|
||||
{showBasicRole && <ValueContainer>{basicRole}</ValueContainer>}
|
||||
<RolesLabel appliedRoles={appliedRoles} numberOfRoles={numberOfRoles} showBuiltInRole={showBasicRole} />
|
||||
</div>
|
||||
) : (
|
||||
<div className={styles.wrapper}>
|
||||
{showBuiltInRole && <ValueContainer>{builtInRole}</ValueContainer>}
|
||||
{showBasicRole && <ValueContainer>{basicRole}</ValueContainer>}
|
||||
{appliedRoles.map((role) => (
|
||||
<ValueContainer key={role.uid}>{role.displayName}</ValueContainer>
|
||||
))}
|
||||
|
@ -19,8 +19,8 @@ import { OrgRole, Role } from 'app/types';
|
||||
|
||||
import { MENU_MAX_HEIGHT } from './constants';
|
||||
|
||||
const BuiltinRoles = Object.values(OrgRole);
|
||||
const BuiltinRoleOption: Array<SelectableValue<OrgRole>> = BuiltinRoles.map((r) => ({
|
||||
const BasicRoles = Object.values(OrgRole);
|
||||
const BasicRoleOption: Array<SelectableValue<OrgRole>> = BasicRoles.map((r) => ({
|
||||
label: r,
|
||||
value: r,
|
||||
}));
|
||||
@ -31,14 +31,14 @@ const fixedRoleGroupNames: Record<string, string> = {
|
||||
};
|
||||
|
||||
interface RolePickerMenuProps {
|
||||
builtInRole?: OrgRole;
|
||||
basicRole?: OrgRole;
|
||||
options: Role[];
|
||||
appliedRoles: Role[];
|
||||
showGroups?: boolean;
|
||||
builtinRolesDisabled?: boolean;
|
||||
showBuiltInRole?: boolean;
|
||||
basicRoleDisabled?: boolean;
|
||||
showBasicRole?: boolean;
|
||||
onSelect: (roles: Role[]) => void;
|
||||
onBuiltInRoleSelect?: (role: OrgRole) => void;
|
||||
onBasicRoleSelect?: (role: OrgRole) => void;
|
||||
onUpdate: (newRoles: Role[], newBuiltInRole?: OrgRole) => void;
|
||||
updateDisabled?: boolean;
|
||||
apply?: boolean;
|
||||
@ -46,21 +46,21 @@ interface RolePickerMenuProps {
|
||||
}
|
||||
|
||||
export const RolePickerMenu = ({
|
||||
builtInRole,
|
||||
basicRole,
|
||||
options,
|
||||
appliedRoles,
|
||||
showGroups,
|
||||
builtinRolesDisabled,
|
||||
showBuiltInRole,
|
||||
basicRoleDisabled,
|
||||
showBasicRole,
|
||||
onSelect,
|
||||
onBuiltInRoleSelect,
|
||||
onBasicRoleSelect,
|
||||
onUpdate,
|
||||
updateDisabled,
|
||||
offset,
|
||||
apply,
|
||||
}: RolePickerMenuProps): JSX.Element => {
|
||||
const [selectedOptions, setSelectedOptions] = useState<Role[]>(appliedRoles);
|
||||
const [selectedBuiltInRole, setSelectedBuiltInRole] = useState<OrgRole | undefined>(builtInRole);
|
||||
const [selectedBuiltInRole, setSelectedBuiltInRole] = useState<OrgRole | undefined>(basicRole);
|
||||
const [showSubMenu, setShowSubMenu] = useState(false);
|
||||
const [openedMenuGroup, setOpenedMenuGroup] = useState('');
|
||||
const [subMenuOptions, setSubMenuOptions] = useState<Role[]>([]);
|
||||
@ -75,10 +75,10 @@ export const RolePickerMenu = ({
|
||||
}, [selectedOptions, onSelect]);
|
||||
|
||||
useEffect(() => {
|
||||
if (onBuiltInRoleSelect && selectedBuiltInRole) {
|
||||
onBuiltInRoleSelect(selectedBuiltInRole);
|
||||
if (onBasicRoleSelect && selectedBuiltInRole) {
|
||||
onBasicRoleSelect(selectedBuiltInRole);
|
||||
}
|
||||
}, [selectedBuiltInRole, onBuiltInRoleSelect]);
|
||||
}, [selectedBuiltInRole, onBasicRoleSelect]);
|
||||
|
||||
const customRoles = options.filter(filterCustomRoles).sort(sortRolesByName);
|
||||
const fixedRoles = options.filter(filterFixedRoles).sort(sortRolesByName);
|
||||
@ -188,16 +188,16 @@ export const RolePickerMenu = ({
|
||||
>
|
||||
<div className={customStyles.menu} aria-label="Role picker menu">
|
||||
<CustomScrollbar autoHide={false} autoHeightMax={`${MENU_MAX_HEIGHT}px`} hideHorizontalTrack hideVerticalTrack>
|
||||
{showBuiltInRole && (
|
||||
{showBasicRole && (
|
||||
<div className={customStyles.menuSection}>
|
||||
<div className={customStyles.groupHeader}>Basic roles</div>
|
||||
<RadioButtonGroup
|
||||
className={customStyles.builtInRoleSelector}
|
||||
options={BuiltinRoleOption}
|
||||
className={customStyles.basicRoleSelector}
|
||||
options={BasicRoleOption}
|
||||
value={selectedBuiltInRole}
|
||||
onChange={onSelectedBuiltinRoleChange}
|
||||
fullWidth={true}
|
||||
disabled={builtinRolesDisabled}
|
||||
disabled={basicRoleDisabled}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
@ -621,7 +621,7 @@ export const getStyles = (theme: GrafanaTheme2) => {
|
||||
menuOptionInfoSign: css`
|
||||
color: ${theme.colors.text.disabled};
|
||||
`,
|
||||
builtInRoleSelector: css`
|
||||
basicRoleSelector: css`
|
||||
margin: ${theme.spacing(1, 1.25, 1, 1)};
|
||||
`,
|
||||
subMenuPortal: css`
|
||||
|
@ -13,10 +13,9 @@ export interface Props {
|
||||
orgId?: number;
|
||||
roleOptions: Role[];
|
||||
disabled?: boolean;
|
||||
builtinRolesDisabled?: boolean;
|
||||
}
|
||||
|
||||
export const TeamRolePicker: FC<Props> = ({ teamId, orgId, roleOptions, disabled, builtinRolesDisabled }) => {
|
||||
export const TeamRolePicker: FC<Props> = ({ teamId, orgId, roleOptions, disabled }) => {
|
||||
const [{ loading, value: appliedRoles = [] }, getTeamRoles] = useAsyncFn(async () => {
|
||||
try {
|
||||
return await fetchTeamRoles(teamId, orgId);
|
||||
@ -47,7 +46,6 @@ export const TeamRolePicker: FC<Props> = ({ teamId, orgId, roleOptions, disabled
|
||||
appliedRoles={appliedRoles}
|
||||
isLoading={loading}
|
||||
disabled={disabled}
|
||||
builtinRolesDisabled={builtinRolesDisabled}
|
||||
canUpdateRoles={canUpdateRoles}
|
||||
/>
|
||||
);
|
||||
|
@ -8,28 +8,26 @@ import { RolePicker } from './RolePicker';
|
||||
import { fetchUserRoles, updateUserRoles } from './api';
|
||||
|
||||
export interface Props {
|
||||
builtInRole: OrgRole;
|
||||
basicRole: OrgRole;
|
||||
userId: number;
|
||||
orgId?: number;
|
||||
onBuiltinRoleChange: (newRole: OrgRole) => void;
|
||||
onBasicRoleChange: (newRole: OrgRole) => void;
|
||||
roleOptions: Role[];
|
||||
builtInRoles?: { [key: string]: Role[] };
|
||||
disabled?: boolean;
|
||||
builtinRolesDisabled?: boolean;
|
||||
basicRoleDisabled?: boolean;
|
||||
apply?: boolean;
|
||||
onApplyRoles?: (newRoles: Role[], userId: number, orgId: number | undefined) => void;
|
||||
pendingRoles?: Role[];
|
||||
}
|
||||
|
||||
export const UserRolePicker: FC<Props> = ({
|
||||
builtInRole,
|
||||
basicRole,
|
||||
userId,
|
||||
orgId,
|
||||
onBuiltinRoleChange,
|
||||
onBasicRoleChange,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
disabled,
|
||||
builtinRolesDisabled,
|
||||
basicRoleDisabled,
|
||||
apply = false,
|
||||
onApplyRoles,
|
||||
pendingRoles,
|
||||
@ -74,15 +72,14 @@ export const UserRolePicker: FC<Props> = ({
|
||||
return (
|
||||
<RolePicker
|
||||
appliedRoles={appliedRoles}
|
||||
builtInRole={builtInRole}
|
||||
basicRole={basicRole}
|
||||
onRolesChange={onRolesChange}
|
||||
onBuiltinRoleChange={onBuiltinRoleChange}
|
||||
onBasicRoleChange={onBasicRoleChange}
|
||||
roleOptions={roleOptions}
|
||||
builtInRoles={builtInRoles}
|
||||
isLoading={loading}
|
||||
disabled={disabled}
|
||||
builtinRolesDisabled={builtinRolesDisabled}
|
||||
showBuiltInRole
|
||||
basicRoleDisabled={basicRoleDisabled}
|
||||
showBasicRole
|
||||
apply={apply}
|
||||
canUpdateRoles={canUpdateRoles}
|
||||
/>
|
||||
|
@ -13,14 +13,6 @@ export const fetchRoleOptions = async (orgId?: number, query?: string): Promise<
|
||||
return roles;
|
||||
};
|
||||
|
||||
export const fetchBuiltinRoles = (orgId?: number): Promise<{ [key: string]: Role[] }> => {
|
||||
let builtinRolesUrl = '/api/access-control/builtin-roles';
|
||||
if (orgId) {
|
||||
builtinRolesUrl += `?targetOrgId=${orgId}`;
|
||||
}
|
||||
return getBackendSrv().get(builtinRolesUrl);
|
||||
};
|
||||
|
||||
export const fetchUserRoles = async (userId: number, orgId?: number): Promise<Role[]> => {
|
||||
let userRolesUrl = `/api/access-control/users/${userId}/roles`;
|
||||
if (orgId) {
|
||||
|
@ -112,10 +112,6 @@ export class ContextSrv {
|
||||
return config.rbacEnabled;
|
||||
}
|
||||
|
||||
accessControlBuiltInRoleAssignmentEnabled(): boolean {
|
||||
return config.rbacBuiltInRoleAssignmentEnabled;
|
||||
}
|
||||
|
||||
licensedAccessControlEnabled(): boolean {
|
||||
return featureEnabled('accesscontrol') && config.rbacEnabled;
|
||||
}
|
||||
|
@ -144,7 +144,6 @@ class UnThemedOrgRow extends PureComponent<OrgRowProps> {
|
||||
currentRole: this.props.org.role,
|
||||
isChangingRole: false,
|
||||
roleOptions: [],
|
||||
builtInRoles: {},
|
||||
};
|
||||
|
||||
componentDidMount() {
|
||||
@ -179,7 +178,7 @@ class UnThemedOrgRow extends PureComponent<OrgRowProps> {
|
||||
this.setState({ isChangingRole: false });
|
||||
};
|
||||
|
||||
onBuiltinRoleChange = (newRole: OrgRole) => {
|
||||
onBasicRoleChange = (newRole: OrgRole) => {
|
||||
this.props.onOrgRoleChange(this.props.org.orgId, newRole);
|
||||
};
|
||||
|
||||
@ -205,11 +204,10 @@ class UnThemedOrgRow extends PureComponent<OrgRowProps> {
|
||||
<UserRolePicker
|
||||
userId={user?.id || 0}
|
||||
orgId={org.orgId}
|
||||
builtInRole={org.role}
|
||||
basicRole={org.role}
|
||||
roleOptions={this.state.roleOptions}
|
||||
builtInRoles={this.state.builtInRoles}
|
||||
onBuiltinRoleChange={this.onBuiltinRoleChange}
|
||||
builtinRolesDisabled={rolePickerDisabled}
|
||||
onBasicRoleChange={this.onBasicRoleChange}
|
||||
basicRoleDisabled={rolePickerDisabled}
|
||||
/>
|
||||
</div>
|
||||
{isExternalUser && <ExternalUserTooltip />}
|
||||
@ -377,9 +375,9 @@ export class AddToOrgModal extends PureComponent<AddToOrgModalProps, AddToOrgMod
|
||||
<UserRolePicker
|
||||
userId={user?.id || 0}
|
||||
orgId={selectedOrg?.id}
|
||||
builtInRole={role}
|
||||
onBuiltinRoleChange={this.onOrgRoleChange}
|
||||
builtinRolesDisabled={false}
|
||||
basicRole={role}
|
||||
onBasicRoleChange={this.onOrgRoleChange}
|
||||
basicRoleDisabled={false}
|
||||
roleOptions={roleOptions}
|
||||
apply={true}
|
||||
onApplyRoles={this.onRoleUpdate}
|
||||
|
@ -4,7 +4,7 @@ import { getBackendSrv, locationService } from '@grafana/runtime';
|
||||
import { Form, Button, Input, Field, FieldSet } from '@grafana/ui';
|
||||
import { Page } from 'app/core/components/Page/Page';
|
||||
import { UserRolePicker } from 'app/core/components/RolePicker/UserRolePicker';
|
||||
import { fetchBuiltinRoles, fetchRoleOptions, updateUserRoles } from 'app/core/components/RolePicker/api';
|
||||
import { fetchRoleOptions, updateUserRoles } from 'app/core/components/RolePicker/api';
|
||||
import { contextSrv } from 'app/core/core';
|
||||
import { AccessControlAction, OrgRole, Role, ServiceAccountCreateApiResponse, ServiceAccountDTO } from 'app/types';
|
||||
|
||||
@ -23,7 +23,6 @@ const updateServiceAccount = async (id: number, sa: ServiceAccountDTO) =>
|
||||
|
||||
export const ServiceAccountCreatePage = ({}: Props): JSX.Element => {
|
||||
const [roleOptions, setRoleOptions] = useState<Role[]>([]);
|
||||
const [builtinRoles, setBuiltinRoles] = useState<{ [key: string]: Role[] }>({});
|
||||
const [pendingRoles, setPendingRoles] = useState<Role[]>([]);
|
||||
|
||||
const currentOrgId = contextSrv.user.orgId;
|
||||
@ -46,14 +45,6 @@ export const ServiceAccountCreatePage = ({}: Props): JSX.Element => {
|
||||
let options = await fetchRoleOptions(currentOrgId);
|
||||
setRoleOptions(options);
|
||||
}
|
||||
|
||||
if (
|
||||
contextSrv.accessControlBuiltInRoleAssignmentEnabled() &&
|
||||
contextSrv.hasPermission(AccessControlAction.ActionBuiltinRolesList)
|
||||
) {
|
||||
const builtInRoles = await fetchBuiltinRoles(currentOrgId);
|
||||
setBuiltinRoles(builtInRoles);
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('Error loading options', e);
|
||||
}
|
||||
@ -131,9 +122,8 @@ export const ServiceAccountCreatePage = ({}: Props): JSX.Element => {
|
||||
apply
|
||||
userId={serviceAccount.id || 0}
|
||||
orgId={serviceAccount.orgId}
|
||||
builtInRole={serviceAccount.role}
|
||||
builtInRoles={builtinRoles}
|
||||
onBuiltinRoleChange={onRoleChange}
|
||||
basicRole={serviceAccount.role}
|
||||
onBasicRoleChange={onRoleChange}
|
||||
roleOptions={roleOptions}
|
||||
onApplyRoles={onPendingRolesUpdate}
|
||||
pendingRoles={pendingRoles}
|
||||
|
@ -26,7 +26,6 @@ const setup = (propOverrides: Partial<Props>) => {
|
||||
const props: Props = {
|
||||
serviceAccount: {} as ServiceAccountDTO,
|
||||
tokens: [],
|
||||
builtInRoles: {},
|
||||
isLoading: false,
|
||||
roleOptions: [],
|
||||
match: {
|
||||
|
@ -28,7 +28,6 @@ interface OwnProps extends GrafanaRouteComponentProps<{ id: string }> {
|
||||
tokens: ApiKey[];
|
||||
isLoading: boolean;
|
||||
roleOptions: Role[];
|
||||
builtInRoles: Record<string, Role[]>;
|
||||
}
|
||||
|
||||
function mapStateToProps(state: StoreState) {
|
||||
@ -37,7 +36,6 @@ function mapStateToProps(state: StoreState) {
|
||||
tokens: state.serviceAccountProfile.tokens,
|
||||
isLoading: state.serviceAccountProfile.isLoading,
|
||||
roleOptions: state.serviceAccounts.roleOptions,
|
||||
builtInRoles: state.serviceAccounts.builtInRoles,
|
||||
timezone: getTimeZone(state.user),
|
||||
};
|
||||
}
|
||||
@ -62,7 +60,6 @@ export const ServiceAccountPageUnconnected = ({
|
||||
timezone,
|
||||
isLoading,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
createServiceAccountToken,
|
||||
deleteServiceAccount,
|
||||
deleteServiceAccountToken,
|
||||
@ -187,7 +184,6 @@ export const ServiceAccountPageUnconnected = ({
|
||||
serviceAccount={serviceAccount}
|
||||
timeZone={timezone}
|
||||
roleOptions={roleOptions}
|
||||
builtInRoles={builtInRoles}
|
||||
onChange={onProfileChange}
|
||||
/>
|
||||
)}
|
||||
|
@ -26,7 +26,6 @@ const setup = (propOverrides: Partial<Props>) => {
|
||||
const getApiKeysMigrationInfoMock = jest.fn();
|
||||
const closeApiKeysMigrationInfoMock = jest.fn();
|
||||
const props: Props = {
|
||||
builtInRoles: {},
|
||||
isLoading: false,
|
||||
page: 0,
|
||||
perPage: 10,
|
||||
|
@ -55,7 +55,6 @@ export const ServiceAccountsListPageUnconnected = ({
|
||||
serviceAccounts,
|
||||
isLoading,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
query,
|
||||
serviceAccountStateFilter,
|
||||
apiKeysMigrated,
|
||||
@ -268,7 +267,6 @@ export const ServiceAccountsListPageUnconnected = ({
|
||||
<ServiceAccountListItem
|
||||
serviceAccount={serviceAccount}
|
||||
key={serviceAccount.id}
|
||||
builtInRoles={builtInRoles}
|
||||
roleOptions={roleOptions}
|
||||
onRoleChange={onRoleChange}
|
||||
onRemoveButtonClick={onRemoveButtonClick}
|
||||
|
@ -13,17 +13,10 @@ interface Props {
|
||||
serviceAccount: ServiceAccountDTO;
|
||||
timeZone: TimeZone;
|
||||
roleOptions: Role[];
|
||||
builtInRoles: Record<string, Role[]>;
|
||||
onChange: (serviceAccount: ServiceAccountDTO) => void;
|
||||
}
|
||||
|
||||
export function ServiceAccountProfile({
|
||||
serviceAccount,
|
||||
timeZone,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
onChange,
|
||||
}: Props): JSX.Element {
|
||||
export function ServiceAccountProfile({ serviceAccount, timeZone, roleOptions, onChange }: Props): JSX.Element {
|
||||
const styles = useStyles2(getStyles);
|
||||
const ableToWrite = contextSrv.hasPermission(AccessControlAction.ServiceAccountsWrite);
|
||||
|
||||
@ -51,7 +44,6 @@ export function ServiceAccountProfile({
|
||||
label="Roles"
|
||||
serviceAccount={serviceAccount}
|
||||
onRoleChange={onRoleChange}
|
||||
builtInRoles={builtInRoles}
|
||||
roleOptions={roleOptions}
|
||||
/>
|
||||
<ServiceAccountProfileRow
|
||||
|
@ -11,16 +11,9 @@ interface Props {
|
||||
serviceAccount: ServiceAccountDTO;
|
||||
onRoleChange: (role: OrgRole) => void;
|
||||
roleOptions: Role[];
|
||||
builtInRoles: Record<string, Role[]>;
|
||||
}
|
||||
|
||||
export const ServiceAccountRoleRow = ({
|
||||
label,
|
||||
serviceAccount,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
onRoleChange,
|
||||
}: Props): JSX.Element => {
|
||||
export const ServiceAccountRoleRow = ({ label, serviceAccount, roleOptions, onRoleChange }: Props): JSX.Element => {
|
||||
const inputId = `${label}-input`;
|
||||
const canUpdateRole = contextSrv.hasPermissionInMetadata(AccessControlAction.ServiceAccountsWrite, serviceAccount);
|
||||
|
||||
@ -34,11 +27,10 @@ export const ServiceAccountRoleRow = ({
|
||||
<UserRolePicker
|
||||
userId={serviceAccount.id}
|
||||
orgId={serviceAccount.orgId}
|
||||
builtInRole={serviceAccount.role}
|
||||
onBuiltinRoleChange={onRoleChange}
|
||||
basicRole={serviceAccount.role}
|
||||
onBasicRoleChange={onRoleChange}
|
||||
roleOptions={roleOptions}
|
||||
builtInRoles={builtInRoles}
|
||||
builtinRolesDisabled={!canUpdateRole}
|
||||
basicRoleDisabled={!canUpdateRole}
|
||||
disabled={serviceAccount.isDisabled}
|
||||
/>
|
||||
</td>
|
||||
|
@ -12,7 +12,6 @@ type ServiceAccountListItemProps = {
|
||||
serviceAccount: ServiceAccountDTO;
|
||||
onRoleChange: (role: OrgRole, serviceAccount: ServiceAccountDTO) => void;
|
||||
roleOptions: Role[];
|
||||
builtInRoles: Record<string, Role[]>;
|
||||
onRemoveButtonClick: (serviceAccount: ServiceAccountDTO) => void;
|
||||
onDisable: (serviceAccount: ServiceAccountDTO) => void;
|
||||
onEnable: (serviceAccount: ServiceAccountDTO) => void;
|
||||
@ -28,7 +27,6 @@ const ServiceAccountListItem = memo(
|
||||
serviceAccount,
|
||||
onRoleChange,
|
||||
roleOptions,
|
||||
builtInRoles,
|
||||
onRemoveButtonClick,
|
||||
onDisable,
|
||||
onEnable,
|
||||
@ -78,11 +76,10 @@ const ServiceAccountListItem = memo(
|
||||
<UserRolePicker
|
||||
userId={serviceAccount.id}
|
||||
orgId={serviceAccount.orgId}
|
||||
builtInRole={serviceAccount.role}
|
||||
onBuiltinRoleChange={(newRole) => onRoleChange(newRole, serviceAccount)}
|
||||
basicRole={serviceAccount.role}
|
||||
onBasicRoleChange={(newRole) => onRoleChange(newRole, serviceAccount)}
|
||||
roleOptions={roleOptions}
|
||||
builtInRoles={builtInRoles}
|
||||
builtinRolesDisabled={!canUpdateRole}
|
||||
basicRoleDisabled={!canUpdateRole}
|
||||
disabled={serviceAccount.isDisabled}
|
||||
/>
|
||||
)}
|
||||
|
@ -1,7 +1,7 @@
|
||||
import { debounce } from 'lodash';
|
||||
|
||||
import { getBackendSrv } from '@grafana/runtime';
|
||||
import { fetchBuiltinRoles, fetchRoleOptions } from 'app/core/components/RolePicker/api';
|
||||
import { fetchRoleOptions } from 'app/core/components/RolePicker/api';
|
||||
import { contextSrv } from 'app/core/services/context_srv';
|
||||
import store from 'app/core/store';
|
||||
import { AccessControlAction, ServiceAccountDTO, ServiceAccountStateFilter, ThunkResult } from 'app/types';
|
||||
@ -11,7 +11,6 @@ import { API_KEYS_MIGRATION_INFO_STORAGE_KEY } from '../constants';
|
||||
|
||||
import {
|
||||
acOptionsLoaded,
|
||||
builtInRolesLoaded,
|
||||
pageChanged,
|
||||
queryChanged,
|
||||
serviceAccountsFetchBegin,
|
||||
@ -31,14 +30,6 @@ export function fetchACOptions(): ThunkResult<void> {
|
||||
const options = await fetchRoleOptions();
|
||||
dispatch(acOptionsLoaded(options));
|
||||
}
|
||||
if (
|
||||
contextSrv.accessControlBuiltInRoleAssignmentEnabled() &&
|
||||
contextSrv.licensedAccessControlEnabled() &&
|
||||
contextSrv.hasPermission(AccessControlAction.ActionBuiltinRolesList)
|
||||
) {
|
||||
const builtInRoles = await fetchBuiltinRoles();
|
||||
dispatch(builtInRolesLoaded(builtInRoles));
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
}
|
||||
|
@ -43,7 +43,6 @@ export const { serviceAccountLoaded, serviceAccountTokensLoaded, serviceAccountF
|
||||
export const initialStateList: ServiceAccountsState = {
|
||||
serviceAccounts: [] as ServiceAccountDTO[],
|
||||
isLoading: true,
|
||||
builtInRoles: {},
|
||||
roleOptions: [],
|
||||
query: '',
|
||||
page: 0,
|
||||
@ -88,9 +87,6 @@ const serviceAccountsSlice = createSlice({
|
||||
acOptionsLoaded: (state, action: PayloadAction<Role[]>): ServiceAccountsState => {
|
||||
return { ...state, roleOptions: action.payload };
|
||||
},
|
||||
builtInRolesLoaded: (state, action: PayloadAction<Record<string, Role[]>>): ServiceAccountsState => {
|
||||
return { ...state, builtInRoles: action.payload };
|
||||
},
|
||||
apiKeysMigrationStatusLoaded: (state, action): ServiceAccountsState => {
|
||||
return { ...state, apiKeysMigrated: action.payload };
|
||||
},
|
||||
@ -121,7 +117,6 @@ export const {
|
||||
serviceAccountsFetchEnd,
|
||||
serviceAccountsFetched,
|
||||
acOptionsLoaded,
|
||||
builtInRolesLoaded,
|
||||
apiKeysMigrationStatusLoaded,
|
||||
showApiKeysMigrationInfoLoaded,
|
||||
pageChanged,
|
||||
|
@ -3,7 +3,7 @@ import React, { FC, useEffect, useState } from 'react';
|
||||
import { OrgRole } from '@grafana/data';
|
||||
import { Button, ConfirmModal } from '@grafana/ui';
|
||||
import { UserRolePicker } from 'app/core/components/RolePicker/UserRolePicker';
|
||||
import { fetchBuiltinRoles, fetchRoleOptions } from 'app/core/components/RolePicker/api';
|
||||
import { fetchRoleOptions } from 'app/core/components/RolePicker/api';
|
||||
import { contextSrv } from 'app/core/core';
|
||||
import { AccessControlAction, OrgUser, Role } from 'app/types';
|
||||
|
||||
@ -20,7 +20,6 @@ const UsersTable: FC<Props> = (props) => {
|
||||
const { users, orgId, onRoleChange, onRemoveUser } = props;
|
||||
const [userToRemove, setUserToRemove] = useState<OrgUser | null>(null);
|
||||
const [roleOptions, setRoleOptions] = useState<Role[]>([]);
|
||||
const [builtinRoles, setBuiltinRoles] = useState<{ [key: string]: Role[] }>({});
|
||||
|
||||
useEffect(() => {
|
||||
async function fetchOptions() {
|
||||
@ -29,14 +28,6 @@ const UsersTable: FC<Props> = (props) => {
|
||||
let options = await fetchRoleOptions(orgId);
|
||||
setRoleOptions(options);
|
||||
}
|
||||
|
||||
if (
|
||||
contextSrv.accessControlBuiltInRoleAssignmentEnabled() &&
|
||||
contextSrv.hasPermission(AccessControlAction.ActionBuiltinRolesList)
|
||||
) {
|
||||
const builtInRoles = await fetchBuiltinRoles(orgId);
|
||||
setBuiltinRoles(builtInRoles);
|
||||
}
|
||||
} catch (e) {
|
||||
console.error('Error loading options');
|
||||
}
|
||||
@ -92,12 +83,9 @@ const UsersTable: FC<Props> = (props) => {
|
||||
userId={user.userId}
|
||||
orgId={orgId}
|
||||
roleOptions={roleOptions}
|
||||
builtInRoles={builtinRoles}
|
||||
builtInRole={user.role}
|
||||
onBuiltinRoleChange={(newRole) => onRoleChange(newRole, user)}
|
||||
builtinRolesDisabled={
|
||||
!contextSrv.hasPermissionInMetadata(AccessControlAction.OrgUsersWrite, user)
|
||||
}
|
||||
basicRole={user.role}
|
||||
onBasicRoleChange={(newRole) => onRoleChange(newRole, user)}
|
||||
basicRoleDisabled={!contextSrv.hasPermissionInMetadata(AccessControlAction.OrgUsersWrite, user)}
|
||||
/>
|
||||
) : (
|
||||
<OrgRolePicker
|
||||
|
@ -63,7 +63,6 @@ export enum AccessControlAction {
|
||||
ActionTeamsPermissionsWrite = 'teams.permissions:write',
|
||||
|
||||
ActionRolesList = 'roles:read',
|
||||
ActionBuiltinRolesList = 'roles.builtin:list',
|
||||
ActionTeamsRolesList = 'teams.roles:read',
|
||||
ActionTeamsRolesAdd = 'teams.roles:add',
|
||||
ActionTeamsRolesRemove = 'teams.roles:remove',
|
||||
|
@ -65,7 +65,6 @@ export interface ServiceAccountsState {
|
||||
serviceAccounts: ServiceAccountDTO[];
|
||||
isLoading: boolean;
|
||||
roleOptions: Role[];
|
||||
builtInRoles: Record<string, Role[]>;
|
||||
apiKeysMigrated: boolean;
|
||||
showApiKeysMigrationInfo: boolean;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user