summaryrefslogtreecommitdiff
path: root/lib/pcr/table/edit-pcr-sheet.tsx
diff options
context:
space:
mode:
Diffstat (limited to 'lib/pcr/table/edit-pcr-sheet.tsx')
-rw-r--r--lib/pcr/table/edit-pcr-sheet.tsx237
1 files changed, 237 insertions, 0 deletions
diff --git a/lib/pcr/table/edit-pcr-sheet.tsx b/lib/pcr/table/edit-pcr-sheet.tsx
new file mode 100644
index 00000000..df625515
--- /dev/null
+++ b/lib/pcr/table/edit-pcr-sheet.tsx
@@ -0,0 +1,237 @@
+"use client"
+
+import * as React from "react"
+import { useForm } from "react-hook-form"
+import { zodResolver } from "@hookform/resolvers/zod"
+import * as z from "zod"
+import { Button } from "@/components/ui/button"
+import {
+ Sheet,
+ SheetContent,
+ SheetDescription,
+ SheetFooter,
+ SheetHeader,
+ SheetTitle,
+} from "@/components/ui/sheet"
+import {
+ Form,
+ FormControl,
+ FormField,
+ FormItem,
+ FormLabel,
+ FormMessage,
+} from "@/components/ui/form"
+import { Textarea } from "@/components/ui/textarea"
+import {
+ Select,
+ SelectContent,
+ SelectItem,
+ SelectTrigger,
+ SelectValue,
+} from "@/components/ui/select"
+import { toast } from "sonner"
+import { PcrPoData } from "@/lib/pcr/types"
+import { updatePcrRejectionReasonAction } from "@/lib/pcr/actions"
+
+const pcrEditSchema = z.object({
+ rejectionReasonType: z.string().optional(),
+ customRejectionReason: z.string().optional(),
+})
+
+const REJECTION_REASON_OPTIONS = [
+ { value: "제작완료", label: "제작완료" },
+ { value: "납품 준비 중", label: "납품 준비 중" },
+ { value: "제작을 위한 원소재 준비 완료", label: "제작을 위한 원소재 준비 완료" },
+ { value: "협력사 거래중지로 인한 승인 불가", label: "협력사 거래중지로 인한 승인 불가" },
+ { value: "기타", label: "기타" },
+]
+
+type PcrEditFormData = z.infer<typeof pcrEditSchema>
+
+interface EditPcrSheetProps {
+ open: boolean
+ onOpenChange: (open: boolean) => void
+ pcrData: PcrPoData | null
+ onSuccess: () => void
+}
+
+export function EditPcrSheet({
+ open,
+ onOpenChange,
+ pcrData,
+ onSuccess,
+}: EditPcrSheetProps) {
+ const [isSubmitting, setIsSubmitting] = React.useState(false)
+
+ const form = useForm<PcrEditFormData>({
+ resolver: zodResolver(pcrEditSchema),
+ defaultValues: {
+ rejectionReason: "",
+ },
+ })
+
+ // PCR 데이터가 변경될 때 폼 초기화
+ React.useEffect(() => {
+ if (pcrData) {
+ const rejectionReason = pcrData.rejectionReason || ""
+
+ // 기존 rejectionReason을 파싱해서 미리 정의된 옵션인지 확인
+ const predefinedOption = REJECTION_REASON_OPTIONS.find(option =>
+ option.value === rejectionReason
+ )
+
+ if (predefinedOption) {
+ form.reset({
+ rejectionReasonType: rejectionReason,
+ customRejectionReason: "",
+ })
+ } else {
+ form.reset({
+ rejectionReasonType: "기타",
+ customRejectionReason: rejectionReason,
+ })
+ }
+ }
+ }, [pcrData, form])
+
+ const onSubmit = async (data: PcrEditFormData) => {
+ if (!pcrData) {
+ toast.error("PCR 데이터가 없습니다")
+ return
+ }
+
+ setIsSubmitting(true)
+ try {
+ // rejectionReason 조합
+ let rejectionReason = ""
+ if (data.rejectionReasonType === "기타") {
+ rejectionReason = data.customRejectionReason || ""
+ } else {
+ rejectionReason = data.rejectionReasonType || ""
+ }
+
+ const result = await updatePcrRejectionReasonAction({
+ id: pcrData.id,
+ rejectionReason: rejectionReason,
+ })
+
+ if (result.success) {
+ toast.success("PCR이 성공적으로 수정되었습니다")
+ onOpenChange(false)
+ onSuccess()
+ } else {
+ toast.error(result.error || "PCR 수정에 실패했습니다")
+ }
+ } catch (error) {
+ console.error("PCR 수정 오류:", error)
+ toast.error("PCR 수정 중 오류가 발생했습니다")
+ } finally {
+ setIsSubmitting(false)
+ }
+ }
+
+ if (!pcrData) return null
+
+ return (
+ <Sheet open={open} onOpenChange={onOpenChange}>
+ <SheetContent className="w-[400px] sm:w-[540px]">
+ <SheetHeader>
+ <SheetTitle>PCR 수정</SheetTitle>
+ <SheetDescription>
+ PO/계약번호: {pcrData.poContractNumber}
+ </SheetDescription>
+ </SheetHeader>
+
+ <Form {...form}>
+ <form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6">
+ {/* 읽기 전용 정보 표시 */}
+ <div className="space-y-4">
+ <div className="grid grid-cols-2 gap-4">
+ <div>
+ <label className="text-sm font-medium">프로젝트</label>
+ <p className="text-sm text-muted-foreground">{pcrData.project || "-"}</p>
+ </div>
+ <div>
+ <label className="text-sm font-medium">변경구분</label>
+ <p className="text-sm text-muted-foreground">{pcrData.changeType}</p>
+ </div>
+ </div>
+
+ <div>
+ <label className="text-sm font-medium">PCR 사유</label>
+ <p className="text-sm text-muted-foreground">{pcrData.pcrReason || "-"}</p>
+ </div>
+
+ <div>
+ <label className="text-sm font-medium">상세 사유</label>
+ <p className="text-sm text-muted-foreground">{pcrData.detailsReason || "-"}</p>
+ </div>
+ </div>
+
+ {/* 편집 가능한 필드 */}
+ <FormField
+ control={form.control}
+ name="rejectionReasonType"
+ render={({ field }) => (
+ <FormItem>
+ <FormLabel>거절 사유 *</FormLabel>
+ <Select onValueChange={field.onChange} value={field.value}>
+ <FormControl>
+ <SelectTrigger>
+ <SelectValue placeholder="거절 사유를 선택하세요" />
+ </SelectTrigger>
+ </FormControl>
+ <SelectContent>
+ {REJECTION_REASON_OPTIONS.map((option) => (
+ <SelectItem key={option.value} value={option.value}>
+ {option.label}
+ </SelectItem>
+ ))}
+ </SelectContent>
+ </Select>
+ <FormMessage />
+ </FormItem>
+ )}
+ />
+
+ {/* 기타 선택 시 텍스트 입력 필드 */}
+ {form.watch("rejectionReasonType") === "기타" && (
+ <FormField
+ control={form.control}
+ name="customRejectionReason"
+ render={({ field }) => (
+ <FormItem>
+ <FormLabel>기타 거절 사유</FormLabel>
+ <FormControl>
+ <Textarea
+ placeholder="거절 사유를 입력하세요"
+ className="resize-none"
+ rows={3}
+ {...field}
+ />
+ </FormControl>
+ <FormMessage />
+ </FormItem>
+ )}
+ />
+ )}
+
+ <SheetFooter>
+ <Button
+ type="button"
+ variant="outline"
+ onClick={() => onOpenChange(false)}
+ disabled={isSubmitting}
+ >
+ 취소
+ </Button>
+ <Button type="submit" disabled={isSubmitting}>
+ {isSubmitting ? "수정 중..." : "수정"}
+ </Button>
+ </SheetFooter>
+ </form>
+ </Form>
+ </SheetContent>
+ </Sheet>
+ )
+}