Skip to content

Commit

Permalink
Merge pull request #712 from Justfemi/feat-roles-and-components-kimiko
Browse files Browse the repository at this point in the history
Feat (roles and permission) for team-kimiko
  • Loading branch information
Prudent Bird authored Jul 29, 2024
2 parents eab07a7 + b771439 commit c15aa1a
Show file tree
Hide file tree
Showing 2 changed files with 248 additions and 3 deletions.
Original file line number Diff line number Diff line change
@@ -1,5 +1,185 @@
const page = () => {
return <div>page</div>;
"use client";

import { useState } from "react";

import CustomButton from "~/components/common/common-button/common-button";
import RoleCreationModal from "~/components/common/modals/role-creation";

type Role = {
id: number;
name: string;
description: string;
};

type Permission = {
name: string;
enabled: boolean;
};

const rolesData: Role[] = [
{ id: 1, name: "Guest", description: "Read-only access" },
{ id: 2, name: "User", description: "Read, write, update" },
{ id: 3, name: "Manager", description: "Read, write, approve" },
{ id: 4, name: "Project Lead", description: "Manage, coordinate, oversee" },
{ id: 5, name: "Administrator", description: "Full access, control" },
];

const permissionsData: { [key: number]: Permission[] } = {
1: [
{ name: "Can view transactions", enabled: true },
{ name: "Can view refunds", enabled: false },
{ name: "Can log refunds", enabled: true },
],
2: [
{ name: "Can view users", enabled: true },
{ name: "Can create users", enabled: false },
{ name: "Can edit users", enabled: true },
{ name: "Can blacklist/whitelist users", enabled: true },
],
3: [
{ name: "Can view users", enabled: true },
{ name: "Can create users", enabled: true },
{ name: "Can edit users", enabled: false },
{ name: "Can blacklist/whitelist users", enabled: true },
],
4: [
{ name: "Can view transactions", enabled: true },
{ name: "Can view refunds", enabled: true },
{ name: "Can log refunds", enabled: true },
{ name: "Can view users", enabled: true },
{ name: "Can create users", enabled: true },
{ name: "Can edit users", enabled: true },
{ name: "Can blacklist/whitelist users", enabled: true },
],
5: [
{ name: "Can view transactions", enabled: true },
{ name: "Can view refunds", enabled: true },
{ name: "Can log refunds", enabled: true },
{ name: "Can view users", enabled: true },
{ name: "Can create users", enabled: true },
{ name: "Can edit users", enabled: true },
{ name: "Can blacklist/whitelist users", enabled: true },
],
};

const RolesAndPermission = () => {
const [selectedRoleId, setSelectedRoleId] = useState<number | undefined>();
const [permissions, setPermissions] = useState<Permission[]>([]);
const [isModalOpen, setIsModalOpen] = useState(false);

const handleRoleClick = (roleId: number) => {
setSelectedRoleId(roleId);
setPermissions([...permissionsData[roleId]]);
};

const handleToggle = (index: number) => {
setPermissions((previous) => {
const newPermissions = [...previous];
newPermissions[index].enabled = !newPermissions[index].enabled;
permissionsData[selectedRoleId!] = newPermissions;
return newPermissions;
});
};

const handleModalOpen = () => {
setIsModalOpen(true);
};

const handleModalClose = () => {
setIsModalOpen(false);
};

return (
<div className="min-h-screen p-8">
<div className="flex">
<div className="w-1/4 pr-6">
<h2 className="mb-10 text-xl font-medium">Roles</h2>
<ul>
{rolesData.map((role) => (
<li
key={role.id}
className={`mb-6 cursor-pointer border-b border-[#CBD5E1] p-2 ${
selectedRoleId === role.id
? "rounded-md bg-orange-500 text-white"
: "bg-white text-[#0a0a0a] hover:bg-[#F1F5F9]"
}`}
onClick={() => handleRoleClick(role.id)}
>
<div className="text-base font-medium">{role.name}</div>
<div
className={`text-xs font-normal ${selectedRoleId === role.id ? "text-white" : "text-[#525252]"}`}
>
{role.description}
</div>
</li>
))}
</ul>
</div>
<div className="w-3/4">
<div className="flex justify-end">
<CustomButton
variant="primary"
className="mb-6"
onClick={handleModalOpen}
>
+ Create roles
</CustomButton>
</div>
<div className="border-l border-[#CBD5E1] pl-6">
<div className="border-b border-[#CBD5E1] pb-4">
<h2 className="mb-2 text-xl font-semibold text-[#0A0A0A]">
Permissions
</h2>
<p className="text-xs font-normal text-[#525252]">
See the list of permissions for this role
</p>
</div>
{selectedRoleId === undefined ? (
<div className="item-center flex flex-col justify-center py-56">
<p className="text-center text-sm font-normal text-[#525252]">
No list to show
</p>
<p className="text-center text-sm font-normal text-[#525252]">
Click on a role to view permissions
</p>
</div>
) : (
<div className="mt-6">
<h3 className="mb-4 font-[#0a0a0a] text-base font-medium">
Transactions Permission
</h3>
{permissions.map((permission, index) => (
<div
key={permission.name}
className="mb-6 flex items-center justify-between"
>
<span className="text-sm font-normal text-[#525252]">
{permission.name}
</span>
<label className="relative inline-flex cursor-pointer items-center">
<input
type="checkbox"
className="peer sr-only"
checked={permission.enabled}
onChange={() => handleToggle(index)}
/>
<div className="peer h-6 w-11 rounded-full bg-gray-200 after:absolute after:left-[2px] after:top-[2px] after:h-5 after:w-5 after:rounded-full after:border after:border-gray-300 after:bg-white after:transition-all after:content-[''] peer-checked:bg-orange-600 peer-checked:after:translate-x-full peer-checked:after:border-white peer-focus:ring-4 peer-focus:ring-orange-300 dark:border-gray-600 dark:bg-gray-700 dark:peer-focus:ring-orange-800"></div>
</label>
</div>
))}
<div className="mt-16 flex justify-end">
<button className="rounded border border-[#E2E8F0] bg-[#F1F5F9] px-4 py-2 text-sm font-medium text-[#0F172A] hover:bg-[#c1c9d2]">
Save Preferences
</button>
</div>
</div>
)}
</div>
</div>
</div>
<RoleCreationModal show={isModalOpen} onClose={handleModalClose} />
</div>
);
};

export default page;
export default RolesAndPermission;
65 changes: 65 additions & 0 deletions src/components/common/modals/role-creation/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
"use client";

import CustomButton from "~/components/common/common-button/common-button";
import {
Dialog,
DialogContent,
DialogDescription,
DialogHeader,
DialogTitle,
} from "~/components/ui/dialog";

interface ModalProperties {
show: boolean;
onClose: () => void;
}

const RoleCreationModal: React.FC<ModalProperties> = ({ show, onClose }) => {
return (
<>
<Dialog open={show} onOpenChange={onClose}>
<DialogContent>
<DialogHeader>
<DialogTitle>
<h2 className="mb-2 text-left text-lg font-semibold text-neutral-dark-2">
Create Role
</h2>
</DialogTitle>
<DialogDescription>
<p className="text-left text-sm font-normal text-[#475569]">
Define customized responsibilities for collaborative success.
</p>
<div className="mb-7 mt-6">
<label className="mb-2 block text-left text-base font-bold text-neutral-dark-2">
Name of role
</label>
<input
type="text"
placeholder="e.g: IT Staff"
className="w-full rounded-md border border-border px-3 py-2 shadow-sm outline-none focus:border-primary focus:ring-ring md:w-56"
/>
</div>
<div>
<label className="mb-2 block text-left text-base font-bold text-neutral-dark-2">
Role Descriotion
</label>
<textarea
placeholder="describe role"
className="min-h-20 w-full resize-none rounded-md border border-border px-3 py-2 shadow-sm outline-none focus:border-primary focus:ring-ring"
/>
</div>
<div className="mt-8 flex items-center justify-end gap-4">
<CustomButton variant="subtle" onClick={onClose}>
Cancel
</CustomButton>
<CustomButton variant="primary">Create Role</CustomButton>
</div>
</DialogDescription>
</DialogHeader>
</DialogContent>
</Dialog>
</>
);
};

export default RoleCreationModal;

0 comments on commit c15aa1a

Please sign in to comment.