auto commit
This commit is contained in:
parent
19f82aca2b
commit
304318af4e
@ -126,22 +126,27 @@ const AccountsPage = () => {
|
|||||||
|
|
||||||
// Table columns
|
// Table columns
|
||||||
const columns: ColumnDef<User>[] = [
|
const columns: ColumnDef<User>[] = [
|
||||||
{
|
// {
|
||||||
accessorKey: "username",
|
// accessorKey: "username",
|
||||||
header: "아이디",
|
// header: "아이디",
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "name",
|
accessorKey: "name",
|
||||||
header: "이름",
|
header: "이름",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
accessorKey: "email",
|
accessorKey: "Department.name",
|
||||||
header: "이메일",
|
header: "부서",
|
||||||
},
|
cell: ({ row }) => row.original.Department?.name || "-",
|
||||||
{
|
|
||||||
accessorKey: "phone",
|
|
||||||
header: "전화번호",
|
|
||||||
},
|
},
|
||||||
|
// {
|
||||||
|
// accessorKey: "email",
|
||||||
|
// header: "이메일",
|
||||||
|
// },
|
||||||
|
// {
|
||||||
|
// accessorKey: "phone",
|
||||||
|
// header: "전화번호",
|
||||||
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "role",
|
accessorKey: "role",
|
||||||
header: "역할",
|
header: "역할",
|
||||||
@ -164,6 +169,16 @@ const AccountsPage = () => {
|
|||||||
return (roles ?? []).map((role) => role.name).join(", ");
|
return (roles ?? []).map((role) => role.name).join(", ");
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
// {
|
||||||
|
// accessorKey: "Company.name",
|
||||||
|
// header: "회사",
|
||||||
|
// cell: ({ row }) => row.original.Company?.name || "-",
|
||||||
|
// },
|
||||||
|
// {
|
||||||
|
// accessorKey: "Branch.name",
|
||||||
|
// header: "지점",
|
||||||
|
// cell: ({ row }) => row.original.Branch?.name || "-",
|
||||||
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "isActive",
|
accessorKey: "isActive",
|
||||||
header: "활성화",
|
header: "활성화",
|
||||||
@ -176,21 +191,6 @@ const AccountsPage = () => {
|
|||||||
/>
|
/>
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
{
|
|
||||||
accessorKey: "Company.name",
|
|
||||||
header: "회사",
|
|
||||||
cell: ({ row }) => row.original.Company?.name || "-",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
accessorKey: "Branch.name",
|
|
||||||
header: "지점",
|
|
||||||
cell: ({ row }) => row.original.Branch?.name || "-",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
accessorKey: "Department.name",
|
|
||||||
header: "부서",
|
|
||||||
cell: ({ row }) => row.original.Department?.name || "-",
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
id: "actions",
|
id: "actions",
|
||||||
header: "액션",
|
header: "액션",
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
// src/app/(admin)/users/roles/components/RoleForm.tsx
|
// src/app/(admin)/users/roles/components/RoleForm.tsx
|
||||||
import React from "react";
|
import React, { useEffect, useState } from "react";
|
||||||
import { useForm } from "react-hook-form";
|
import { useForm } from "react-hook-form";
|
||||||
import { zodResolver } from "@hookform/resolvers/zod";
|
import { zodResolver } from "@hookform/resolvers/zod";
|
||||||
import * as z from "zod";
|
import * as z from "zod";
|
||||||
@ -17,18 +17,7 @@ import { Textarea } from "@/components/ui/textarea";
|
|||||||
import { Checkbox } from "@/components/ui/checkbox";
|
import { Checkbox } from "@/components/ui/checkbox";
|
||||||
import { Button } from "@/components/ui/button";
|
import { Button } from "@/components/ui/button";
|
||||||
import { Card, CardContent } from "@/components/ui/card";
|
import { Card, CardContent } from "@/components/ui/card";
|
||||||
|
import { Role } from "@/types/user";
|
||||||
interface Permission {
|
|
||||||
[key: string]: string[];
|
|
||||||
}
|
|
||||||
|
|
||||||
interface Role {
|
|
||||||
id: string;
|
|
||||||
name: string;
|
|
||||||
description: string;
|
|
||||||
permissions: Permission;
|
|
||||||
isActive: boolean;
|
|
||||||
}
|
|
||||||
|
|
||||||
const formSchema = z.object({
|
const formSchema = z.object({
|
||||||
name: z
|
name: z
|
||||||
@ -66,38 +55,55 @@ export const RoleForm = ({
|
|||||||
onSubmit,
|
onSubmit,
|
||||||
onCancel,
|
onCancel,
|
||||||
}: RoleFormProps) => {
|
}: RoleFormProps) => {
|
||||||
const form = useForm<z.infer<typeof formSchema>>({
|
const [mounted, setMounted] = useState(false);
|
||||||
resolver: zodResolver(formSchema),
|
|
||||||
defaultValues: {
|
// 초기값 설정을 별도 상수로 분리
|
||||||
name: initialData?.name || "",
|
const defaultPermissions = {
|
||||||
description: initialData?.description || "",
|
|
||||||
permissions: initialData?.permissions || {
|
|
||||||
company: [],
|
company: [],
|
||||||
user: [],
|
user: [],
|
||||||
energy: [],
|
energy: [],
|
||||||
equipment: [],
|
equipment: [],
|
||||||
report: [],
|
report: [],
|
||||||
},
|
};
|
||||||
|
|
||||||
|
const form = useForm<z.infer<typeof formSchema>>({
|
||||||
|
resolver: zodResolver(formSchema),
|
||||||
|
defaultValues: {
|
||||||
|
name: initialData?.name || "",
|
||||||
|
description: initialData?.description || "",
|
||||||
|
permissions: initialData?.permissions || defaultPermissions,
|
||||||
isActive: initialData?.isActive ?? true,
|
isActive: initialData?.isActive ?? true,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
// handlePermissionChange 함수 수정
|
useEffect(() => {
|
||||||
|
setMounted(true);
|
||||||
|
|
||||||
|
// initialData가 있을 경우, 폼 값을 초기화
|
||||||
|
if (initialData) {
|
||||||
|
Object.entries(initialData.permissions).forEach(
|
||||||
|
([category, permissions]) => {
|
||||||
|
form.setValue(`permissions.${category}`, permissions, {
|
||||||
|
shouldValidate: true,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}, [initialData, form]);
|
||||||
|
|
||||||
|
// permissions 값을 watch로 관찰
|
||||||
|
const permissions = form.watch("permissions");
|
||||||
|
|
||||||
const handlePermissionChange = (
|
const handlePermissionChange = (
|
||||||
category: string,
|
category: string,
|
||||||
type: string,
|
type: string,
|
||||||
checked: boolean
|
checked: boolean
|
||||||
) => {
|
) => {
|
||||||
const currentPermissions = form.getValues().permissions[category] || [];
|
const currentPermissions = permissions[category] || [];
|
||||||
let newPermissions;
|
const newPermissions = checked
|
||||||
|
? [...currentPermissions, type]
|
||||||
|
: currentPermissions.filter((p) => p !== type);
|
||||||
|
|
||||||
if (checked) {
|
|
||||||
newPermissions = [...currentPermissions, type];
|
|
||||||
} else {
|
|
||||||
newPermissions = currentPermissions.filter((p) => p !== type);
|
|
||||||
}
|
|
||||||
|
|
||||||
// form.setValue 대신 setValue를 사용하고 shouldValidate를 true로 설정
|
|
||||||
form.setValue(`permissions.${category}`, newPermissions, {
|
form.setValue(`permissions.${category}`, newPermissions, {
|
||||||
shouldValidate: true,
|
shouldValidate: true,
|
||||||
shouldDirty: true,
|
shouldDirty: true,
|
||||||
@ -105,6 +111,38 @@ export const RoleForm = ({
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const renderPermissionCheckbox = (
|
||||||
|
category: string,
|
||||||
|
type: string,
|
||||||
|
typeName: string
|
||||||
|
) => {
|
||||||
|
if (!mounted && !initialData) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
const isChecked = permissions[category]?.includes(type);
|
||||||
|
const defaultChecked = initialData?.permissions[category]?.includes(type);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div key={`${category}-${type}`} className="flex items-center space-x-2">
|
||||||
|
<Checkbox
|
||||||
|
id={`${category}-${type}`}
|
||||||
|
checked={isChecked}
|
||||||
|
defaultChecked={defaultChecked}
|
||||||
|
onCheckedChange={(checked) =>
|
||||||
|
handlePermissionChange(category, type, checked as boolean)
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
<label
|
||||||
|
htmlFor={`${category}-${type}`}
|
||||||
|
className="text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70"
|
||||||
|
>
|
||||||
|
{typeName}
|
||||||
|
</label>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Form {...form}>
|
<Form {...form}>
|
||||||
<form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6">
|
<form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6">
|
||||||
@ -148,33 +186,8 @@ export const RoleForm = ({
|
|||||||
<CardContent className="pt-4">
|
<CardContent className="pt-4">
|
||||||
<div className="font-medium mb-2">{categoryName}</div>
|
<div className="font-medium mb-2">{categoryName}</div>
|
||||||
<div className="grid grid-cols-2 md:grid-cols-4 gap-4">
|
<div className="grid grid-cols-2 md:grid-cols-4 gap-4">
|
||||||
{Object.entries(PERMISSION_TYPES).map(
|
{Object.entries(PERMISSION_TYPES).map(([type, typeName]) =>
|
||||||
([type, typeName]) => (
|
renderPermissionCheckbox(category, type, typeName)
|
||||||
<div
|
|
||||||
key={`${category}-${type}`}
|
|
||||||
className="flex items-center space-x-2"
|
|
||||||
>
|
|
||||||
<Checkbox
|
|
||||||
id={`${category}-${type}`}
|
|
||||||
checked={form
|
|
||||||
.watch(`permissions.${category}`, [])
|
|
||||||
.includes(type)}
|
|
||||||
onCheckedChange={(checked) =>
|
|
||||||
handlePermissionChange(
|
|
||||||
category,
|
|
||||||
type,
|
|
||||||
checked as boolean
|
|
||||||
)
|
|
||||||
}
|
|
||||||
/>
|
|
||||||
<label
|
|
||||||
htmlFor={`${category}-${type}`}
|
|
||||||
className="text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70"
|
|
||||||
>
|
|
||||||
{typeName}
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
)
|
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</CardContent>
|
</CardContent>
|
||||||
@ -205,12 +218,21 @@ export const RoleForm = ({
|
|||||||
/>
|
/>
|
||||||
|
|
||||||
<div className="flex justify-end space-x-2">
|
<div className="flex justify-end space-x-2">
|
||||||
<Button type="button" variant="outline" onClick={onCancel}>
|
<Button
|
||||||
|
type="button"
|
||||||
|
variant="outline"
|
||||||
|
onClick={onCancel}
|
||||||
|
className="w-24"
|
||||||
|
>
|
||||||
취소
|
취소
|
||||||
</Button>
|
</Button>
|
||||||
<Button type="submit">{initialData ? "수정" : "생성"}</Button>
|
<Button type="submit" className="w-24">
|
||||||
|
{initialData ? "수정" : "생성"}
|
||||||
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
</Form>
|
</Form>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export default RoleForm;
|
||||||
|
@ -19,18 +19,7 @@ import { RoleForm } from "./components/RoleForm";
|
|||||||
import { api } from "@/lib/api";
|
import { api } from "@/lib/api";
|
||||||
import { AxiosError } from "axios";
|
import { AxiosError } from "axios";
|
||||||
import { useAuthStore } from "@/stores/auth";
|
import { useAuthStore } from "@/stores/auth";
|
||||||
|
import { Role } from "@/types/user";
|
||||||
interface Permission {
|
|
||||||
[key: string]: string[];
|
|
||||||
}
|
|
||||||
|
|
||||||
interface Role {
|
|
||||||
id: string;
|
|
||||||
name: string;
|
|
||||||
description: string;
|
|
||||||
permissions: Permission;
|
|
||||||
isActive: boolean;
|
|
||||||
}
|
|
||||||
|
|
||||||
const RolesPage = () => {
|
const RolesPage = () => {
|
||||||
const { token, user } = useAuthStore();
|
const { token, user } = useAuthStore();
|
||||||
@ -234,7 +223,7 @@ const RolesPage = () => {
|
|||||||
</div>
|
</div>
|
||||||
{/* 중첩된 Dialog를 제거하고 하나의 Dialog만 사용 */}
|
{/* 중첩된 Dialog를 제거하고 하나의 Dialog만 사용 */}
|
||||||
<Dialog open={isOpen} onOpenChange={setIsOpen}>
|
<Dialog open={isOpen} onOpenChange={setIsOpen}>
|
||||||
<DialogContent className="max-w-2xl">
|
<DialogContent className="max-w-3xl max-h-[80vh] overflow-y-auto">
|
||||||
<DialogHeader>
|
<DialogHeader>
|
||||||
<DialogTitle>
|
<DialogTitle>
|
||||||
{editingRole ? "권한 그룹 수정" : "새 권한 그룹"}
|
{editingRole ? "권한 그룹 수정" : "새 권한 그룹"}
|
||||||
|
@ -191,7 +191,14 @@ export function EquipmentForm({
|
|||||||
// 사양 정보 상태 추가
|
// 사양 정보 상태 추가
|
||||||
const [specifications, setSpecifications] = React.useState<
|
const [specifications, setSpecifications] = React.useState<
|
||||||
Record<string, string>
|
Record<string, string>
|
||||||
>(initialData?.specifications || defaultSpecifications);
|
>(
|
||||||
|
Object.fromEntries(
|
||||||
|
Object.entries(initialData?.specifications || {}).map(([k, v]) => [
|
||||||
|
k,
|
||||||
|
String(v),
|
||||||
|
])
|
||||||
|
) || defaultSpecifications
|
||||||
|
);
|
||||||
|
|
||||||
// 사양 정보 필드 추가/제거 핸들러 수정
|
// 사양 정보 필드 추가/제거 핸들러 수정
|
||||||
const handleSpecificationChange = (key: string, value: string) => {
|
const handleSpecificationChange = (key: string, value: string) => {
|
||||||
|
@ -100,10 +100,10 @@ const InventoryPage = () => {
|
|||||||
accessorKey: "model",
|
accessorKey: "model",
|
||||||
header: "모델명",
|
header: "모델명",
|
||||||
},
|
},
|
||||||
{
|
// {
|
||||||
accessorKey: "manufacturer",
|
// accessorKey: "manufacturer",
|
||||||
header: "제조사",
|
// header: "제조사",
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "type",
|
accessorKey: "type",
|
||||||
header: "유형",
|
header: "유형",
|
||||||
@ -119,12 +119,12 @@ const InventoryPage = () => {
|
|||||||
return typeMap[row.original.type] || row.original.type;
|
return typeMap[row.original.type] || row.original.type;
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
// {
|
||||||
accessorKey: "installationDate",
|
// accessorKey: "installationDate",
|
||||||
header: "설치일",
|
// header: "설치일",
|
||||||
cell: ({ row }) =>
|
// cell: ({ row }) =>
|
||||||
new Date(row.original.installationDate).toLocaleDateString(),
|
// new Date(row.original.installationDate).toLocaleDateString(),
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "lastMaintenance",
|
accessorKey: "lastMaintenance",
|
||||||
header: "최근 정비일",
|
header: "최근 정비일",
|
||||||
|
@ -60,6 +60,15 @@ const MaintenancePage = () => {
|
|||||||
|
|
||||||
// Table columns
|
// Table columns
|
||||||
const columns: ColumnDef<MaintenanceLog>[] = [
|
const columns: ColumnDef<MaintenanceLog>[] = [
|
||||||
|
{
|
||||||
|
accessorKey: "equipment.name",
|
||||||
|
header: "설비명",
|
||||||
|
cell: ({ row }) => row.original.Equipment?.name || "-",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
accessorKey: "description",
|
||||||
|
header: "정비 내용",
|
||||||
|
},
|
||||||
{
|
{
|
||||||
accessorKey: "type",
|
accessorKey: "type",
|
||||||
header: "정비 유형",
|
header: "정비 유형",
|
||||||
@ -100,15 +109,6 @@ const MaintenancePage = () => {
|
|||||||
? new Date(row.original.completionDate).toLocaleDateString()
|
? new Date(row.original.completionDate).toLocaleDateString()
|
||||||
: "-",
|
: "-",
|
||||||
},
|
},
|
||||||
{
|
|
||||||
accessorKey: "equipment.name",
|
|
||||||
header: "설비명",
|
|
||||||
cell: ({ row }) => row.original.Equipment?.name || "-",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
accessorKey: "description",
|
|
||||||
header: "정비 내용",
|
|
||||||
},
|
|
||||||
// {
|
// {
|
||||||
// accessorKey: "isActive",
|
// accessorKey: "isActive",
|
||||||
// header: "활성 상태",
|
// header: "활성 상태",
|
||||||
|
@ -144,10 +144,10 @@ const PartsPage = () => {
|
|||||||
</Badge>
|
</Badge>
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
{
|
// {
|
||||||
accessorKey: "manufacturer",
|
// accessorKey: "manufacturer",
|
||||||
header: "제조사",
|
// header: "제조사",
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
accessorKey: "stockQuantity",
|
accessorKey: "stockQuantity",
|
||||||
header: "재고수량",
|
header: "재고수량",
|
||||||
@ -276,9 +276,16 @@ const PartsPage = () => {
|
|||||||
initialData={editingPart || undefined}
|
initialData={editingPart || undefined}
|
||||||
onSubmit={(data) => {
|
onSubmit={(data) => {
|
||||||
if (editingPart) {
|
if (editingPart) {
|
||||||
updateMutation.mutate({ id: editingPart.id, ...data });
|
updateMutation.mutate({
|
||||||
|
id: editingPart.id,
|
||||||
|
...data,
|
||||||
|
specifications: JSON.stringify(data.specifications || {}),
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
createMutation.mutate(data);
|
createMutation.mutate({
|
||||||
|
...data,
|
||||||
|
specifications: JSON.stringify(data.specifications || {}),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
onCancel={() => {
|
onCancel={() => {
|
||||||
|
@ -7,7 +7,7 @@ import { useForm, useFieldArray } from "react-hook-form";
|
|||||||
import * as z from "zod";
|
import * as z from "zod";
|
||||||
import { Button } from "@/components/ui/button";
|
import { Button } from "@/components/ui/button";
|
||||||
import { Badge } from "@/components/ui/badge";
|
import { Badge } from "@/components/ui/badge";
|
||||||
import { Award, Plus, X } from "lucide-react";
|
import { Award, X } from "lucide-react";
|
||||||
import {
|
import {
|
||||||
Form,
|
Form,
|
||||||
FormControl,
|
FormControl,
|
||||||
@ -64,7 +64,7 @@ const formSchema = z.object({
|
|||||||
|
|
||||||
interface PersonnelFormProps {
|
interface PersonnelFormProps {
|
||||||
initialData?: Personnel;
|
initialData?: Personnel;
|
||||||
onSubmit: (data: any) => void;
|
onSubmit: (data: z.infer<typeof formSchema>) => void;
|
||||||
onCancel: () => void;
|
onCancel: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -113,11 +113,7 @@ export function PersonnelForm({
|
|||||||
});
|
});
|
||||||
|
|
||||||
// useFieldArray 설정
|
// useFieldArray 설정
|
||||||
const {
|
useFieldArray({
|
||||||
fields: certFields,
|
|
||||||
append: appendCert,
|
|
||||||
remove: removeCert,
|
|
||||||
} = useFieldArray({
|
|
||||||
control: form.control,
|
control: form.control,
|
||||||
name: "certifications",
|
name: "certifications",
|
||||||
});
|
});
|
||||||
@ -200,7 +196,7 @@ export function PersonnelForm({
|
|||||||
<SelectValue placeholder="부서를 선택하세요" />
|
<SelectValue placeholder="부서를 선택하세요" />
|
||||||
</SelectTrigger>
|
</SelectTrigger>
|
||||||
<SelectContent>
|
<SelectContent>
|
||||||
{department?.map((dept: any) => (
|
{department?.map((dept: { id: string; name: string }) => (
|
||||||
<SelectItem key={dept.id} value={dept.name}>
|
<SelectItem key={dept.id} value={dept.name}>
|
||||||
{dept.name}
|
{dept.name}
|
||||||
</SelectItem>
|
</SelectItem>
|
||||||
|
@ -16,7 +16,7 @@ import {
|
|||||||
DialogDescription,
|
DialogDescription,
|
||||||
} from "@/components/ui/dialog";
|
} from "@/components/ui/dialog";
|
||||||
import { useToast } from "@/hooks/use-toast";
|
import { useToast } from "@/hooks/use-toast";
|
||||||
import { Plus, Edit, Trash2, Wrench, Search } from "lucide-react";
|
import { Plus, Edit, Trash2, Search } from "lucide-react";
|
||||||
import { ColumnDef } from "@tanstack/react-table";
|
import { ColumnDef } from "@tanstack/react-table";
|
||||||
import { useAuthStore } from "@/stores/auth";
|
import { useAuthStore } from "@/stores/auth";
|
||||||
import { AxiosError } from "axios";
|
import { AxiosError } from "axios";
|
||||||
@ -157,7 +157,7 @@ const PersonnelPage = () => {
|
|||||||
header: "자격증",
|
header: "자격증",
|
||||||
cell: ({ row }) => (
|
cell: ({ row }) => (
|
||||||
<div className="flex flex-wrap gap-1">
|
<div className="flex flex-wrap gap-1">
|
||||||
{row.original.certifications?.map((cert: any, index: number) => (
|
{row.original.certifications?.map((cert: { name: string }, index: number) => (
|
||||||
<Badge key={index} variant="secondary">
|
<Badge key={index} variant="secondary">
|
||||||
{cert.name}
|
{cert.name}
|
||||||
</Badge>
|
</Badge>
|
||||||
@ -308,9 +308,26 @@ const PersonnelPage = () => {
|
|||||||
initialData={editingPersonnel || undefined}
|
initialData={editingPersonnel || undefined}
|
||||||
onSubmit={(data) => {
|
onSubmit={(data) => {
|
||||||
if (editingPersonnel) {
|
if (editingPersonnel) {
|
||||||
updateMutation.mutate({ id: editingPersonnel.id, ...data });
|
updateMutation.mutate({
|
||||||
|
id: editingPersonnel.id,
|
||||||
|
...data,
|
||||||
|
certifications: data.certifications?.map(cert => ({
|
||||||
|
name: cert.name,
|
||||||
|
date: cert.issueDate,
|
||||||
|
expiry: cert.expiryDate || "",
|
||||||
|
expiryDate: cert.expiryDate || "",
|
||||||
|
})),
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
createMutation.mutate(data);
|
createMutation.mutate({
|
||||||
|
...data,
|
||||||
|
certifications: data.certifications?.map(cert => ({
|
||||||
|
name: cert.name,
|
||||||
|
date: cert.issueDate,
|
||||||
|
expiry: cert.expiryDate || "",
|
||||||
|
expiryDate: cert.expiryDate || "",
|
||||||
|
})),
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
onCancel={() => {
|
onCancel={() => {
|
||||||
|
@ -8,6 +8,7 @@ export interface Equipment {
|
|||||||
manufacturer: string;
|
manufacturer: string;
|
||||||
type: "HVAC" | "Boiler" | "Compressor" | "Motor" | "Pump" | "Other";
|
type: "HVAC" | "Boiler" | "Compressor" | "Motor" | "Pump" | "Other";
|
||||||
specifications: Record<string, string | number | boolean>;
|
specifications: Record<string, string | number | boolean>;
|
||||||
|
defaultSpecifications: Record<string, string | number | boolean>;
|
||||||
installationDate: string;
|
installationDate: string;
|
||||||
lastMaintenance: string | null;
|
lastMaintenance: string | null;
|
||||||
isActive: boolean;
|
isActive: boolean;
|
||||||
|
@ -34,5 +34,11 @@ export interface User {
|
|||||||
export interface Role {
|
export interface Role {
|
||||||
id: string;
|
id: string;
|
||||||
name: string;
|
name: string;
|
||||||
description?: string;
|
description: string;
|
||||||
|
permissions: Permission;
|
||||||
|
isActive: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface Permission {
|
||||||
|
[key: string]: string[];
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user