update style

This commit is contained in:
Vladyslav Matsiiako
2024-03-28 18:17:59 -07:00
parent e46256f45b
commit 31ad6b0c86
6 changed files with 128 additions and 142 deletions
@@ -308,11 +308,11 @@ export const IdentityTab = withProjectPermission(
onOpenChange={(state) => handlePopUpToggle("updateRole", state)} onOpenChange={(state) => handlePopUpToggle("updateRole", state)}
> >
<ModalContent <ModalContent
className="max-w-4xl" className="max-w-3xl"
title={`Manage Access for ${(popUp.updateRole.data as IdentityMembership)?.identity?.name title={`Manage Access for ${(popUp.updateRole.data as IdentityMembership)?.identity?.name
}`} }`}
subTitle={` subTitle={`
Configure role-based access control by Infisical users a mix of one built-in role, multiple custom roles, and multiple specific privileges. A user will gain access to alll actions within the roles assigned to them, not just the actions those roles share in common. You must choose at least one permanent role. Configure role-based access control by assigning machine identities a mix of roles and specific privileges. An identity will gain access to all actions within the roles assigned to it, not just the actions those roles share in common. You must choose at least one permanent role.
`} `}
> >
<IdentityRoleForm <IdentityRoleForm
@@ -1,8 +1,8 @@
import { Controller, useFieldArray, useForm } from "react-hook-form"; import { Controller, useFieldArray, useForm } from "react-hook-form";
import { faCaretDown, faClock, faClose } from "@fortawesome/free-solid-svg-icons"; import { faCaretDown, faClock, faPlus, faTrash } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { zodResolver } from "@hookform/resolvers/zod"; import { zodResolver } from "@hookform/resolvers/zod";
import { formatDistance } from "date-fns"; import { format } from "date-fns";
import ms from "ms"; import ms from "ms";
import { twMerge } from "tailwind-merge"; import { twMerge } from "tailwind-merge";
import { z } from "zod"; import { z } from "zod";
@@ -21,8 +21,7 @@ import {
Select, Select,
SelectItem, SelectItem,
Spinner, Spinner,
Tag, Tag
Tooltip
} from "@app/components/v2"; } from "@app/components/v2";
import { import {
ProjectPermissionActions, ProjectPermissionActions,
@@ -183,29 +182,24 @@ export const IdentityRbacSection = ({ identityProjectMember, onOpenUpgradeModal
/> />
<Popover> <Popover>
<PopoverTrigger disabled={isMemberEditDisabled}> <PopoverTrigger disabled={isMemberEditDisabled}>
<Tooltip
asChild
content={isExpired ? "Timed access expired" : "Grant timed access"}
>
<Button <Button
variant="outline_bg" variant="outline_bg"
leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined} leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined}
rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />} rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />}
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
className={twMerge( className={twMerge(
"border-none bg-mineshaft-600 py-2 capitalize", "border-none bg-mineshaft-600 hover:bg-mineshaft-500 py-2.5 capitalize text-xs",
isTemporary && "text-primary", isTemporary && "text-primary",
isExpired && "text-red-600" isExpired && "text-red-600"
)} )}
> >
{!temporaryAccess?.isTemporary {!temporaryAccess?.isTemporary
? "Permanent" ? "Permanent"
: formatDistance( : `Expires at ${format(
new Date(temporaryAccess.temporaryAccessEndTime || ""), new Date(temporaryAccess.temporaryAccessEndTime || ""),
new Date() "yyyy-MM-dd HH:mm:ss"
)} )}`}
</Button> </Button>
</Tooltip>
</PopoverTrigger> </PopoverTrigger>
<PopoverContent <PopoverContent
arrowClassName="fill-gray-600" arrowClassName="fill-gray-600"
@@ -283,10 +277,9 @@ export const IdentityRbacSection = ({ identityProjectMember, onOpenUpgradeModal
</div> </div>
</PopoverContent> </PopoverContent>
</Popover> </Popover>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Remove"}>
<IconButton <IconButton
variant="outline_bg" variant="outline_bg"
className="border-none bg-mineshaft-600 py-3" className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-3"
ariaLabel="delete-role" ariaLabel="delete-role"
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
onClick={() => { onClick={() => {
@@ -295,9 +288,8 @@ export const IdentityRbacSection = ({ identityProjectMember, onOpenUpgradeModal
} }
}} }}
> >
<FontAwesomeIcon icon={faClose} /> <FontAwesomeIcon icon={faTrash} />
</IconButton> </IconButton>
</Tooltip>
</div> </div>
); );
})} })}
@@ -311,6 +303,7 @@ export const IdentityRbacSection = ({ identityProjectMember, onOpenUpgradeModal
<Button <Button
variant="outline_bg" variant="outline_bg"
isDisabled={!isAllowed} isDisabled={!isAllowed}
leftIcon={<FontAwesomeIcon icon={faPlus} />}
onClick={() => onClick={() =>
selectedRoleList.append({ selectedRoleList.append({
slug: ProjectMembershipRole.Member, slug: ProjectMembershipRole.Member,
@@ -1,8 +1,8 @@
import { Controller, useForm } from "react-hook-form"; import { Controller, useForm } from "react-hook-form";
import { faCancel, faCaretDown, faClock, faClose, faSave } from "@fortawesome/free-solid-svg-icons"; import { faArrowRotateLeft, faCaretDown, faCheck, faClock, faPlus, faTrash } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { zodResolver } from "@hookform/resolvers/zod"; import { zodResolver } from "@hookform/resolvers/zod";
import { formatDistance } from "date-fns"; import { format } from "date-fns";
import ms from "ms"; import ms from "ms";
import { twMerge } from "tailwind-merge"; import { twMerge } from "tailwind-merge";
import { z } from "zod"; import { z } from "zod";
@@ -176,7 +176,7 @@ const SpecificPrivilegeSecretForm = ({
const getAccessLabel = () => { const getAccessLabel = () => {
if (isExpired) return "Access expired"; if (isExpired) return "Access expired";
if (!temporaryAccessField?.isTemporary) return "Permanent"; if (!temporaryAccessField?.isTemporary) return "Permanent";
return formatDistance(new Date(temporaryAccessField.temporaryAccessEndTime || ""), new Date()); return `Until ${format(new Date(temporaryAccessField.temporaryAccessEndTime || ""), "yyyy-MM-dd HH:mm:ss")}`;
}; };
return ( return (
@@ -191,9 +191,8 @@ const SpecificPrivilegeSecretForm = ({
<Select <Select
{...field} {...field}
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
className="bg-mineshaft-600" className="bg-mineshaft-600 hover:bg-mineshaft-500"
onValueChange={(e) => onChange(e)} onValueChange={(e) => onChange(e)}
// className="w-full border border-mineshaft-500 bg-mineshaft-700 text-mineshaft-100"
> >
{currentWorkspace?.environments?.map(({ slug, id }) => ( {currentWorkspace?.environments?.map(({ slug, id }) => (
<SelectItem value={slug} key={id}> <SelectItem value={slug} key={id}>
@@ -292,7 +291,7 @@ const SpecificPrivilegeSecretForm = ({
leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined} leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined}
rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />} rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />}
className={twMerge( className={twMerge(
"border-none py-1.5 capitalize", "border-none py-2.5 capitalize text-xs hover:bg-mineshaft-500",
isTemporary && "text-primary", isTemporary && "text-primary",
isExpired && "text-red-600" isExpired && "text-red-600"
)} )}
@@ -379,42 +378,42 @@ const SpecificPrivilegeSecretForm = ({
</Popover> </Popover>
{privilegeForm.formState.isDirty ? ( {privilegeForm.formState.isDirty ? (
<> <>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Save"}> <Tooltip content="Cancel" className="mr-4">
<IconButton
isDisabled={isMemberEditDisabled}
className="border-none py-2.5"
ariaLabel="save-privilege"
type="submit"
>
{privilegeForm.formState.isSubmitting ? (
<Spinner size="xs" className="m-0 h-3 w-3 text-slate-500" />
) : (
<FontAwesomeIcon icon={faSave} />
)}
</IconButton>
</Tooltip>
<Tooltip content="Cancel">
<IconButton <IconButton
variant="outline_bg" variant="outline_bg"
className="border-none bg-mineshaft-600 py-2.5" className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-2.5"
ariaLabel="delete-privilege" ariaLabel="delete-privilege"
isDisabled={privilegeForm.formState.isSubmitting} isDisabled={privilegeForm.formState.isSubmitting}
onClick={() => privilegeForm.reset()} onClick={() => privilegeForm.reset()}
> >
<FontAwesomeIcon icon={faCancel} /> <FontAwesomeIcon icon={faArrowRotateLeft} className="py-0.5" />
</IconButton>
</Tooltip>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Save"} className="mr-4">
<IconButton
isDisabled={isMemberEditDisabled}
className="border-none py-3"
ariaLabel="save-privilege"
type="submit"
>
{privilegeForm.formState.isSubmitting ? (
<Spinner size="xs" className="m-0 text-slate-500 w-3 h-3" />
) : (
<FontAwesomeIcon icon={faCheck} className="px-0.5"/>
)}
</IconButton> </IconButton>
</Tooltip> </Tooltip>
</> </>
) : ( ) : (
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Delete"}> <Tooltip content={isMemberEditDisabled ? "Access restricted" : "Delete"} className="mr-4">
<IconButton <IconButton
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
variant="outline_bg" variant="outline_bg"
className="border-none bg-mineshaft-600 py-2.5" className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-3"
ariaLabel="delete-privilege" ariaLabel="delete-privilege"
onClick={() => handlePopUpOpen("deletePrivilege")} onClick={() => handlePopUpOpen("deletePrivilege")}
> >
<FontAwesomeIcon icon={faClose} /> <FontAwesomeIcon icon={faTrash} />
</IconButton> </IconButton>
</Tooltip> </Tooltip>
)} )}
@@ -476,12 +475,12 @@ export const SpecificPrivilegeSection = ({ identityId }: Props) => {
}; };
return ( return (
<div className="mt-6 border-t border-t-gray-700 pt-6"> <div className="mt-6 border-t border-t-mineshaft-600 pt-6">
<div className="flex items-center space-x-2 text-lg font-medium"> <div className="flex items-center space-x-2 text-lg font-medium">
Additional Privileges Additional Privileges
{isLoading && <Spinner size="xs" />} {isLoading && <Spinner size="xs" />}
</div> </div>
<p className="text-sm text-mineshaft-400"> <p className="text-sm text-mineshaft-400 mt-0.5">
Select individual privileges to associate with the identity. Select individual privileges to associate with the identity.
</p> </p>
<div> <div>
@@ -502,6 +501,7 @@ export const SpecificPrivilegeSection = ({ identityId }: Props) => {
<Button <Button
variant="outline_bg" variant="outline_bg"
className="mt-4" className="mt-4"
leftIcon={<FontAwesomeIcon icon={faPlus} />}
onClick={handleCreatePrivilege} onClick={handleCreatePrivilege}
isLoading={createIdentityPrivilege.isLoading} isLoading={createIdentityPrivilege.isLoading}
isDisabled={!isAllowed} isDisabled={!isAllowed}
@@ -472,7 +472,7 @@ export const MemberListTab = () => {
className="max-w-4xl" className="max-w-4xl"
title={`Manage Access for ${(popUp.updateRole.data as TWorkspaceUser)?.user?.email}`} title={`Manage Access for ${(popUp.updateRole.data as TWorkspaceUser)?.user?.email}`}
subTitle={` subTitle={`
Configure role-based access control by Infisical users a mix of one built-in role, multiple custom roles, and multiple specific privileges. A user will gain access to alll actions within the roles assigned to them, not just the actions those roles share in common. You must choose at least one permanent role. Configure role-based access control by assigning Infisical users a mix of roles and specific privileges. A user will gain access to all actions within the roles assigned to them, not just the actions those roles share in common. You must choose at least one permanent role.
`} `}
> >
<MemberRoleForm <MemberRoleForm
@@ -1,8 +1,8 @@
import { Controller, useFieldArray, useForm } from "react-hook-form"; import { Controller, useFieldArray, useForm } from "react-hook-form";
import { faCaretDown, faClock, faClose } from "@fortawesome/free-solid-svg-icons"; import { faCaretDown, faClock, faPlus, faTrash } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { zodResolver } from "@hookform/resolvers/zod"; import { zodResolver } from "@hookform/resolvers/zod";
import { formatDistance } from "date-fns"; import { format } from "date-fns";
import ms from "ms"; import ms from "ms";
import { twMerge } from "tailwind-merge"; import { twMerge } from "tailwind-merge";
import { z } from "zod"; import { z } from "zod";
@@ -21,8 +21,7 @@ import {
Select, Select,
SelectItem, SelectItem,
Spinner, Spinner,
Tag, Tag
Tooltip
} from "@app/components/v2"; } from "@app/components/v2";
import { import {
ProjectPermissionActions, ProjectPermissionActions,
@@ -171,7 +170,7 @@ export const MemberRbacSection = ({ projectMember, onOpenUpgradeModal }: Props)
{...field} {...field}
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
onValueChange={(e) => onChange(e)} onValueChange={(e) => onChange(e)}
className="w-full bg-mineshaft-600" className="w-full bg-mineshaft-600 hover:bg-mineshaft-500 duration-200"
> >
{projectRoles?.map(({ name, slug, id: projectRoleId }) => ( {projectRoles?.map(({ name, slug, id: projectRoleId }) => (
<SelectItem value={slug} key={projectRoleId}> <SelectItem value={slug} key={projectRoleId}>
@@ -183,29 +182,24 @@ export const MemberRbacSection = ({ projectMember, onOpenUpgradeModal }: Props)
/> />
<Popover> <Popover>
<PopoverTrigger disabled={isMemberEditDisabled}> <PopoverTrigger disabled={isMemberEditDisabled}>
<Tooltip
asChild
content={isExpired ? "Timed access expired" : "Grant timed access"}
>
<Button <Button
variant="outline_bg" variant="outline_bg"
leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined} leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined}
rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />} rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />}
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
className={twMerge( className={twMerge(
"border-none bg-mineshaft-600 py-2 capitalize", "border-none bg-mineshaft-600 hover:bg-mineshaft-500 py-2.5 capitalize text-xs",
isTemporary && "text-primary", isTemporary && "text-primary",
isExpired && "text-red-600" isExpired && "text-red-600"
)} )}
> >
{!temporaryAccess?.isTemporary {!temporaryAccess?.isTemporary
? "Permanent" ? "Permanent"
: formatDistance( : `Until ${format(
new Date(temporaryAccess.temporaryAccessEndTime || ""), new Date(temporaryAccess.temporaryAccessEndTime || ""),
new Date() "yyyy-MM-dd HH:mm:ss"
)} )}`}
</Button> </Button>
</Tooltip>
</PopoverTrigger> </PopoverTrigger>
<PopoverContent <PopoverContent
arrowClassName="fill-gray-600" arrowClassName="fill-gray-600"
@@ -283,10 +277,9 @@ export const MemberRbacSection = ({ projectMember, onOpenUpgradeModal }: Props)
</div> </div>
</PopoverContent> </PopoverContent>
</Popover> </Popover>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Remove"}>
<IconButton <IconButton
variant="outline_bg" variant="outline_bg"
className="border-none bg-mineshaft-600 py-3" className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-3"
ariaLabel="delete-role" ariaLabel="delete-role"
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
onClick={() => { onClick={() => {
@@ -295,9 +288,8 @@ export const MemberRbacSection = ({ projectMember, onOpenUpgradeModal }: Props)
} }
}} }}
> >
<FontAwesomeIcon icon={faClose} /> <FontAwesomeIcon icon={faTrash} />
</IconButton> </IconButton>
</Tooltip>
</div> </div>
); );
})} })}
@@ -308,6 +300,7 @@ export const MemberRbacSection = ({ projectMember, onOpenUpgradeModal }: Props)
<Button <Button
variant="outline_bg" variant="outline_bg"
isDisabled={!isAllowed} isDisabled={!isAllowed}
leftIcon={<FontAwesomeIcon icon={faPlus} />}
onClick={() => onClick={() =>
selectedRoleList.append({ selectedRoleList.append({
slug: ProjectMembershipRole.Member, slug: ProjectMembershipRole.Member,
@@ -1,8 +1,8 @@
import { Controller, useForm } from "react-hook-form"; import { Controller, useForm } from "react-hook-form";
import { faCancel, faCaretDown, faClock, faClose, faSave } from "@fortawesome/free-solid-svg-icons"; import { faArrowRotateLeft, faCaretDown, faCheck, faClock, faPlus, faTrash } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { zodResolver } from "@hookform/resolvers/zod"; import { zodResolver } from "@hookform/resolvers/zod";
import { formatDistance } from "date-fns"; import { format } from "date-fns";
import ms from "ms"; import ms from "ms";
import { twMerge } from "tailwind-merge"; import { twMerge } from "tailwind-merge";
import { z } from "zod"; import { z } from "zod";
@@ -164,7 +164,7 @@ const SpecificPrivilegeSecretForm = ({ privilege }: { privilege: TProjectUserPri
const getAccessLabel = () => { const getAccessLabel = () => {
if (isExpired) return "Access expired"; if (isExpired) return "Access expired";
if (!temporaryAccessField?.isTemporary) return "Permanent"; if (!temporaryAccessField?.isTemporary) return "Permanent";
return formatDistance(new Date(temporaryAccessField.temporaryAccessEndTime || ""), new Date()); return `Until ${format(new Date(temporaryAccessField.temporaryAccessEndTime || ""), "yyyy-MM-dd HH:mm:ss")}`;
}; };
return ( return (
@@ -179,9 +179,8 @@ const SpecificPrivilegeSecretForm = ({ privilege }: { privilege: TProjectUserPri
<Select <Select
{...field} {...field}
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
className="bg-mineshaft-600" className="bg-mineshaft-600 hover:bg-mineshaft-500"
onValueChange={(e) => onChange(e)} onValueChange={(e) => onChange(e)}
// className="w-full border border-mineshaft-500 bg-mineshaft-700 text-mineshaft-100"
> >
{currentWorkspace?.environments?.map(({ slug, id }) => ( {currentWorkspace?.environments?.map(({ slug, id }) => (
<SelectItem value={slug} key={id}> <SelectItem value={slug} key={id}>
@@ -280,7 +279,7 @@ const SpecificPrivilegeSecretForm = ({ privilege }: { privilege: TProjectUserPri
leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined} leftIcon={isTemporary ? <FontAwesomeIcon icon={faClock} /> : undefined}
rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />} rightIcon={<FontAwesomeIcon icon={faCaretDown} className="ml-2" />}
className={twMerge( className={twMerge(
"border-none py-1.5 capitalize", "border-none py-2.5 capitalize text-xs hover:bg-mineshaft-500",
isTemporary && "text-primary", isTemporary && "text-primary",
isExpired && "text-red-600" isExpired && "text-red-600"
)} )}
@@ -367,42 +366,42 @@ const SpecificPrivilegeSecretForm = ({ privilege }: { privilege: TProjectUserPri
</Popover> </Popover>
{privilegeForm.formState.isDirty ? ( {privilegeForm.formState.isDirty ? (
<> <>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Save"}> <Tooltip content="Cancel" className="mr-4">
<IconButton
variant="outline_bg"
className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-2.5"
ariaLabel="delete-privilege"
isDisabled={privilegeForm.formState.isSubmitting}
onClick={() => privilegeForm.reset()}
>
<FontAwesomeIcon icon={faArrowRotateLeft} className="py-0.5" />
</IconButton>
</Tooltip>
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Save"} className="mr-4">
<IconButton <IconButton
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
className="border-none py-2.5" className="border-none py-3"
ariaLabel="save-privilege" ariaLabel="save-privilege"
type="submit" type="submit"
> >
{privilegeForm.formState.isSubmitting ? ( {privilegeForm.formState.isSubmitting ? (
<Spinner size="xs" className="m-0 text-slate-500 w-3 h-3" /> <Spinner size="xs" className="m-0 text-slate-500 w-3 h-3" />
) : ( ) : (
<FontAwesomeIcon icon={faSave} /> <FontAwesomeIcon icon={faCheck} className="px-0.5"/>
)} )}
</IconButton> </IconButton>
</Tooltip> </Tooltip>
<Tooltip content="Cancel">
<IconButton
variant="outline_bg"
className="border-none bg-mineshaft-600 py-2.5"
ariaLabel="delete-privilege"
isDisabled={privilegeForm.formState.isSubmitting}
onClick={() => privilegeForm.reset()}
>
<FontAwesomeIcon icon={faCancel} />
</IconButton>
</Tooltip>
</> </>
) : ( ) : (
<Tooltip content={isMemberEditDisabled ? "Access restricted" : "Delete"}> <Tooltip content={isMemberEditDisabled ? "Access restricted" : "Delete"} className="mr-4">
<IconButton <IconButton
isDisabled={isMemberEditDisabled} isDisabled={isMemberEditDisabled}
variant="outline_bg" variant="outline_bg"
className="border-none bg-mineshaft-600 py-2.5" className="border border-mineshaft-500 bg-mineshaft-600 hover:bg-red/20 hover:border-red/70 py-3"
ariaLabel="delete-privilege" ariaLabel="delete-privilege"
onClick={() => handlePopUpOpen("deletePrivilege")} onClick={() => handlePopUpOpen("deletePrivilege")}
> >
<FontAwesomeIcon icon={faClose} /> <FontAwesomeIcon icon={faTrash} />
</IconButton> </IconButton>
</Tooltip> </Tooltip>
)} )}
@@ -459,13 +458,13 @@ export const SpecificPrivilegeSection = ({ membershipId }: Props) => {
}; };
return ( return (
<div className="mt-6 border-t border-t-gray-700 pt-6"> <div className="mt-6 border-t border-t-mineshaft-600 pt-6">
<div className="flex items-center space-x-2 text-lg font-medium"> <div className="flex items-center space-x-2 text-lg font-medium">
Additional Privileges Additional Privileges
{isLoading && <Spinner size="xs" />} {isLoading && <Spinner size="xs" />}
</div> </div>
<p className="text-sm text-mineshaft-400"> <p className="text-sm text-mineshaft-400 mt-0.5">
Select individual privileges to associate with the user Select individual privileges to associate with the user.
</p> </p>
<div> <div>
{userPrivileges {userPrivileges
@@ -484,6 +483,7 @@ export const SpecificPrivilegeSection = ({ membershipId }: Props) => {
<Button <Button
variant="outline_bg" variant="outline_bg"
className="mt-4" className="mt-4"
leftIcon={<FontAwesomeIcon icon={faPlus} />}
onClick={handleCreatePrivilege} onClick={handleCreatePrivilege}
isLoading={createUserPrivilege.isLoading} isLoading={createUserPrivilege.isLoading}
isDisabled={!isAllowed} isDisabled={!isAllowed}