summaryrefslogtreecommitdiff
path: root/lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx
diff options
context:
space:
mode:
Diffstat (limited to 'lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx')
-rw-r--r--lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx610
1 files changed, 610 insertions, 0 deletions
diff --git a/lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx b/lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx
new file mode 100644
index 00000000..ce7c8baf
--- /dev/null
+++ b/lib/general-contracts_old/detail/general-contract-subcontract-checklist.tsx
@@ -0,0 +1,610 @@
+'use client'
+
+import React, { useState } from 'react'
+import { Card, CardContent } from '@/components/ui/card'
+import { Accordion, AccordionContent, AccordionItem, AccordionTrigger } from '@/components/ui/accordion'
+import { Checkbox } from '@/components/ui/checkbox'
+import { Label } from '@/components/ui/label'
+import { Badge } from '@/components/ui/badge'
+import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select'
+import { Textarea } from '@/components/ui/textarea'
+import { Alert, AlertDescription } from '@/components/ui/alert'
+import { Button } from '@/components/ui/button'
+import { updateSubcontractChecklist } from '../service'
+import { toast } from 'sonner'
+import { AlertTriangle, CheckCircle, XCircle, HelpCircle, Save } from 'lucide-react'
+
+interface SubcontractChecklistData {
+ // 1. 계약서면발급
+ contractDocumentIssuance: {
+ workOrderBeforeStart: boolean
+ entrustmentDetails: boolean
+ deliveryDetails: boolean
+ inspectionMethod: boolean
+ subcontractPayment: boolean
+ materialProvision: boolean
+ priceAdjustment: boolean
+ }
+ // 2. 부당하도급대금결정행위
+ unfairSubcontractPricing: {
+ priceReductionWithBasis: boolean
+ noNegotiationAfterLowestBid: boolean
+ noDeceptionInPricing: boolean
+ noUniformPriceReduction: boolean
+ noDiscriminatoryTreatment: boolean
+ }
+ // 점검결과
+ inspectionResult: 'compliant' | 'violation' | 'suspected_violation'
+ // 귀책부서 (위반/위반의심 시 필수)
+ responsibleDepartment?: string
+ // 원인 (위반/위반의심 시 필수)
+ cause?: string
+ causeOther?: string
+ // 대책 (위반/위반의심 시 필수)
+ countermeasure?: string
+ countermeasureOther?: string
+}
+
+interface SubcontractChecklistProps {
+ contractId: number
+ onDataChange: (data: SubcontractChecklistData) => void
+ readOnly?: boolean
+ initialData?: SubcontractChecklistData
+}
+
+export function SubcontractChecklist({ contractId, onDataChange, readOnly = false, initialData }: SubcontractChecklistProps) {
+ // 기본 데이터 구조
+ const defaultData: SubcontractChecklistData = {
+ contractDocumentIssuance: {
+ workOrderBeforeStart: false,
+ entrustmentDetails: false,
+ deliveryDetails: false,
+ inspectionMethod: false,
+ subcontractPayment: false,
+ materialProvision: false,
+ priceAdjustment: false,
+ },
+ unfairSubcontractPricing: {
+ priceReductionWithBasis: false,
+ noNegotiationAfterLowestBid: false,
+ noDeceptionInPricing: false,
+ noUniformPriceReduction: false,
+ noDiscriminatoryTreatment: false,
+ },
+ inspectionResult: 'compliant',
+ }
+
+ // initialData와 기본값을 깊이 병합
+ const mergedInitialData = React.useMemo(() => {
+ if (!initialData) return defaultData
+
+ return {
+ contractDocumentIssuance: {
+ ...defaultData.contractDocumentIssuance,
+ ...(initialData.contractDocumentIssuance || {}),
+ },
+ unfairSubcontractPricing: {
+ ...defaultData.unfairSubcontractPricing,
+ ...(initialData.unfairSubcontractPricing || {}),
+ },
+ inspectionResult: initialData.inspectionResult || defaultData.inspectionResult,
+ responsibleDepartment: initialData.responsibleDepartment,
+ cause: initialData.cause,
+ causeOther: initialData.causeOther,
+ countermeasure: initialData.countermeasure,
+ countermeasureOther: initialData.countermeasureOther,
+ }
+ }, [initialData])
+
+ const [isEnabled, setIsEnabled] = useState(true)
+ const [data, setData] = useState<SubcontractChecklistData>(mergedInitialData)
+
+ // 점검결과 자동 계산 함수
+ const calculateInspectionResult = (
+ contractDocumentIssuance: SubcontractChecklistData['contractDocumentIssuance'],
+ unfairSubcontractPricing: SubcontractChecklistData['unfairSubcontractPricing']
+ ): 'compliant' | 'violation' | 'suspected_violation' => {
+ // 1. 계약서면발급의 모든 항목이 체크되어야 함
+ const allContractItemsChecked = Object.values(contractDocumentIssuance).every(checked => checked)
+
+ // 2. 부당하도급대금결정행위에서 'X' 항목 체크 확인
+ const hasUnfairPricingViolation = Object.values(unfairSubcontractPricing).some(checked => !checked)
+
+ if (!allContractItemsChecked) {
+ return 'violation'
+ } else if (hasUnfairPricingViolation) {
+ return 'suspected_violation'
+ }
+
+ return 'compliant'
+ }
+
+ const handleContractDocumentChange = (field: keyof SubcontractChecklistData['contractDocumentIssuance'], checked: boolean) => {
+ setData(prev => {
+ const newContractDocumentIssuance = {
+ ...prev.contractDocumentIssuance,
+ [field]: checked
+ }
+ const newInspectionResult = calculateInspectionResult(newContractDocumentIssuance, prev.unfairSubcontractPricing)
+
+ return {
+ ...prev,
+ contractDocumentIssuance: newContractDocumentIssuance,
+ inspectionResult: newInspectionResult
+ }
+ })
+ }
+
+ const handleUnfairPricingChange = (field: keyof SubcontractChecklistData['unfairSubcontractPricing'], checked: boolean) => {
+ setData(prev => {
+ const newUnfairSubcontractPricing = {
+ ...prev.unfairSubcontractPricing,
+ [field]: checked
+ }
+ const newInspectionResult = calculateInspectionResult(prev.contractDocumentIssuance, newUnfairSubcontractPricing)
+
+ return {
+ ...prev,
+ unfairSubcontractPricing: newUnfairSubcontractPricing,
+ inspectionResult: newInspectionResult
+ }
+ })
+ }
+
+ const handleFieldChange = (field: keyof SubcontractChecklistData, value: string) => {
+ setData(prev => ({ ...prev, [field]: value }))
+ }
+
+ // 데이터 변경 시 부모 컴포넌트에 전달 (저장 시에만)
+ const handleSave = async () => {
+ try {
+ // validation 체크
+ const errors = []
+
+ // 위반 또는 위반의심인 경우 필수 필드 체크
+ if (data.inspectionResult === 'violation' || data.inspectionResult === 'suspected_violation') {
+ if (!data.responsibleDepartment) errors.push('귀책부서')
+ if (!data.cause) errors.push('원인')
+ if (!data.countermeasure) errors.push('대책')
+
+ // 기타 선택 시 추가 입력 필드 체크
+ if (data.cause === '기타' && !data.causeOther) errors.push('원인 기타 입력')
+ if (data.countermeasure === '기타' && !data.countermeasureOther) errors.push('대책 기타 입력')
+ }
+
+ if (errors.length > 0) {
+ toast.error(`다음 항목을 입력해주세요: ${errors.join(', ')}`)
+ return
+ }
+
+ await updateSubcontractChecklist(contractId, data)
+ onDataChange(data)
+ toast.success('하도급법 체크리스트가 저장되었습니다.')
+ } catch (error) {
+ console.error('Error saving subcontract checklist:', error)
+ toast.error('하도급법 체크리스트 저장 중 오류가 발생했습니다.')
+ }
+ }
+
+ const getInspectionResultInfo = () => {
+ switch (data.inspectionResult) {
+ case 'compliant':
+ return {
+ icon: <CheckCircle className="h-5 w-5 text-green-600" />,
+ label: '준수',
+ color: 'bg-green-100 text-green-800',
+ description: '1. 계약서면발급의 모든 항목에 체크, 2. 부당하도급에서 X항목에 체크한 상태'
+ }
+ case 'violation':
+ return {
+ icon: <XCircle className="h-5 w-5 text-red-600" />,
+ label: '위반',
+ color: 'bg-red-100 text-red-800',
+ description: '1. 계약서면발급의 모든 항목 중 1개 이상 미체크 한 경우'
+ }
+ case 'suspected_violation':
+ return {
+ icon: <AlertTriangle className="h-5 w-5 text-yellow-600" />,
+ label: '위반의심',
+ color: 'bg-yellow-100 text-yellow-800',
+ description: '2. 부당하도급에서 O항목에 체크한 경우'
+ }
+ default:
+ // 기본값으로 준수 상태 반환
+ return {
+ icon: <CheckCircle className="h-5 w-5 text-green-600" />,
+ label: '준수',
+ color: 'bg-green-100 text-green-800',
+ description: '점검 결과가 유효하지 않습니다.'
+ }
+ }
+ }
+
+ const resultInfo = getInspectionResultInfo()
+ const isViolationOrSuspected = data.inspectionResult === 'violation' || data.inspectionResult === 'suspected_violation'
+
+ const causeOptions = [
+ { value: '서면미교부_현업부서 하도급법 이해 부족', label: '서면미교부_현업부서 하도급법 이해 부족' },
+ { value: '서면미교부_기존계약 만료前 계약연장에 대한 사전조치 소홀', label: '서면미교부_기존계약 만료前 계약연장에 대한 사전조치 소홀' },
+ { value: '서면미교부_긴급작업時 先작업합의서 체결 절차 未인지', label: '서면미교부_긴급작업時 先작업합의서 체결 절차 未인지' },
+ { value: '부당가격인하_예산부족 等 원가절감 필요성 대두', label: '부당가격인하_예산부족 等 원가절감 필요성 대두' },
+ { value: '부당가격인하_하도급법 이해부족 및 금액 협의과정에 대한 근거 미흡', label: '부당가격인하_하도급법 이해부족 및 금액 협의과정에 대한 근거 미흡' },
+ { value: '기타', label: '기타' }
+ ]
+
+ const countermeasureOptions = [
+ { value: '서면미교부_준법지원을 통한 현업부서 계몽활동 실시', label: '서면미교부_준법지원을 통한 현업부서 계몽활동 실시' },
+ { value: '서면미교부_계약만료일정 별도 관리 및 사전점검', label: '서면미교부_계약만료일정 별도 관리 및 사전점검' },
+ { value: '서면미교부_작업착수前 先작업합의서 체결토록 현업에 가이드', label: '서면미교부_작업착수前 先작업합의서 체결토록 현업에 가이드' },
+ { value: '부당가격인하_최종 협의된 견적서 접수/보관 必', label: '부당가격인하_최종 협의된 견적서 접수/보관 必' },
+ { value: '부당가격인하_합의서 체결시 \'자율적 의사결정\' 等 문구 삽입', label: '부당가격인하_합의서 체결시 \'자율적 의사결정\' 等 문구 삽입' },
+ { value: '부당가격인하_수의계약時 금액 협의과정에 대한 근거 확보 (회의록, 메일, 당초/변경 견적서 等)', label: '부당가격인하_수의계약時 금액 협의과정에 대한 근거 확보 (회의록, 메일, 당초/변경 견적서 等)' },
+ { value: '기타', label: '기타' }
+ ]
+
+ return (
+ <Accordion type="single" collapsible className="w-full">
+ <AccordionItem value="checklist">
+ <AccordionTrigger className="hover:no-underline">
+ <div className="flex items-center gap-3 w-full">
+ <HelpCircle className="h-5 w-5" />
+ <span className="font-medium">하도급법 자율점검 체크리스트</span>
+ <Badge className={resultInfo.color}>
+ {resultInfo.label}
+ </Badge>
+ </div>
+ </AccordionTrigger>
+ <AccordionContent>
+ <Card>
+ <CardContent className="space-y-6 pt-6">
+ {/* 체크박스 */}
+ <div className="flex items-center gap-2">
+ <Checkbox
+ checked={isEnabled}
+ onCheckedChange={(checked) => setIsEnabled(checked as boolean)}
+ disabled={readOnly}
+ />
+ <span className="text-sm font-medium">하도급법 자율점검 체크리스트 활성화</span>
+ </div>
+
+ {/* 점검결과 표시 */}
+ <div className="flex items-center gap-4 p-4 bg-gray-50 rounded-lg">
+ <div className="flex items-center gap-2">
+ {resultInfo.icon}
+ <Badge className={resultInfo.color}>
+ {resultInfo.label}
+ </Badge>
+ </div>
+ <div className="text-sm text-gray-600">
+ {resultInfo.description}
+ </div>
+ </div>
+
+ <Accordion type="multiple" defaultValue={["contract-document", "unfair-pricing"]} className="w-full">
+ {/* 1. 계약서면발급 */}
+ <AccordionItem value="contract-document">
+ <AccordionTrigger className="text-lg font-semibold">
+ 1. 계약서면발급
+ </AccordionTrigger>
+ <AccordionContent>
+ <div className="space-y-4 p-4">
+ <Alert>
+ <AlertDescription>
+ 본 계약에 해당하는 항목을 아래 안내사항에 따라 &apos;O&apos;인 경우 체크하세요.
+ </AlertDescription>
+ </Alert>
+
+ <div className="space-y-4">
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="workOrderBeforeStart"
+ checked={data.contractDocumentIssuance.workOrderBeforeStart}
+ onCheckedChange={(checked) => handleContractDocumentChange('workOrderBeforeStart', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="workOrderBeforeStart" className="text-sm font-medium">
+ (1) 작업 착수前 계약 서면을 발급하지 못하는 경우 작업지시서(선작업합의서)를 발급했는가?
+ </Label>
+ <p className="text-xs text-gray-500">
+ ※ 단가, 물량 등을 정하지 못하는 경우 정하는 기일을 기재
+ </p>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="entrustmentDetails"
+ checked={data.contractDocumentIssuance.entrustmentDetails}
+ onCheckedChange={(checked) => handleContractDocumentChange('entrustmentDetails', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="entrustmentDetails" className="text-sm font-medium">
+ (2) 위탁일자와 위탁내용(품명, 수량 등)을 명기하였는가?
+ </Label>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="deliveryDetails"
+ checked={data.contractDocumentIssuance.deliveryDetails}
+ onCheckedChange={(checked) => handleContractDocumentChange('deliveryDetails', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="deliveryDetails" className="text-sm font-medium">
+ (3) 납품, 인도 또는 제공하는 시기 및 장소(납기 및 납품장소)를 명기하였는가?
+ </Label>
+ <p className="text-xs text-gray-500">
+ 예: 삼성의 검사완료(승인) 후 목적물 인도 등
+ </p>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="inspectionMethod"
+ checked={data.contractDocumentIssuance.inspectionMethod}
+ onCheckedChange={(checked) => handleContractDocumentChange('inspectionMethod', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="inspectionMethod" className="text-sm font-medium">
+ (4) 검사의 방법 및 시기를 명기하였는가?
+ </Label>
+ <p className="text-xs text-gray-500">
+ 예: 작업완료 후 삼성담당자 입회하에 검사를 실시하고 10일 이내 검사결과 통보
+ </p>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="subcontractPayment"
+ checked={data.contractDocumentIssuance.subcontractPayment}
+ onCheckedChange={(checked) => handleContractDocumentChange('subcontractPayment', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="subcontractPayment" className="text-sm font-medium">
+ (5) 하도급대금과 그 지급방법(현금, 어음 등) 및 지급기일을 명기하였는가?
+ </Label>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="materialProvision"
+ checked={data.contractDocumentIssuance.materialProvision}
+ onCheckedChange={(checked) => handleContractDocumentChange('materialProvision', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="materialProvision" className="text-sm font-medium">
+ (6) 원재료 등 제공 시 품명/수량/제공일/대가/대가 지급방법 및 기일을 명기하였는가?
+ </Label>
+ <p className="text-xs text-gray-500">
+ 해당사항 없을 시에도 기재로 간주
+ </p>
+ </div>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="priceAdjustment"
+ checked={data.contractDocumentIssuance.priceAdjustment}
+ onCheckedChange={(checked) => handleContractDocumentChange('priceAdjustment', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <div className="space-y-1">
+ <Label htmlFor="priceAdjustment" className="text-sm font-medium">
+ (7) 원재료 등 가격변동에 따른 대금 조정 요건/방법/절차를 명기하였는가?
+ </Label>
+ </div>
+ </div>
+ </div>
+ </div>
+ </AccordionContent>
+ </AccordionItem>
+
+ {/* 2. 부당하도급대금결정행위 */}
+ <AccordionItem value="unfair-pricing">
+ <AccordionTrigger className="text-lg font-semibold">
+ 2. 부당하도급대금결정행위
+ </AccordionTrigger>
+ <AccordionContent>
+ <div className="space-y-4 p-4">
+ <Alert>
+ <AlertDescription>
+ 본 계약에 해당하는 항목을 아래 안내사항에 따라 &apos;O&apos;인 경우 체크하세요.
+ <br />
+ <strong>※ &apos;X&apos; 항목에 다음 안내사항이 자동 표기됩니다:</strong>
+ </AlertDescription>
+ </Alert>
+
+ <div className="bg-yellow-50 border border-yellow-200 rounded-lg p-4 space-y-2">
+ <h4 className="font-medium text-yellow-800">안내사항:</h4>
+ <ul className="text-sm text-yellow-700 space-y-1">
+ <li>• 단가 인하時 객관/타당한 근거에 의해 산출하고 협력사와 합의</li>
+ <li>• 최저가 경쟁입찰 후 입찰자와 대금인하 협상 불가</li>
+ <li>• 협력사에 발주량 등 거래조건에 착오를 일으키게 하거나 타 사업자 견적 또는 거짓 견적을 보여주는 등 기만하여 대금을 결정할 수 없음</li>
+ <li>• 정당한 이유 없이 일률적 비율로 단가 인하 불가</li>
+ <li>• 정당한 이유 없이 특정 사업자를 차별 취급 하도록 대금 결정 불가</li>
+ </ul>
+ </div>
+
+ <div className="space-y-4">
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="priceReductionWithBasis"
+ checked={data.unfairSubcontractPricing.priceReductionWithBasis}
+ onCheckedChange={(checked) => handleUnfairPricingChange('priceReductionWithBasis', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <Label htmlFor="priceReductionWithBasis" className="text-sm font-medium">
+ 단가 인하時 객관/타당한 근거에 의해 산출하고 협력사와 합의
+ </Label>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="noNegotiationAfterLowestBid"
+ checked={data.unfairSubcontractPricing.noNegotiationAfterLowestBid}
+ onCheckedChange={(checked) => handleUnfairPricingChange('noNegotiationAfterLowestBid', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <Label htmlFor="noNegotiationAfterLowestBid" className="text-sm font-medium">
+ 최저가 경쟁입찰 후 입찰자와 대금인하 협상 불가
+ </Label>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="noDeceptionInPricing"
+ checked={data.unfairSubcontractPricing.noDeceptionInPricing}
+ onCheckedChange={(checked) => handleUnfairPricingChange('noDeceptionInPricing', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <Label htmlFor="noDeceptionInPricing" className="text-sm font-medium">
+ 협력사에 발주량 등 거래조건에 착오를 일으키게 하거나 타 사업자 견적 또는 거짓 견적을 보여주는 등 기만하여 대금을 결정할 수 없음
+ </Label>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="noUniformPriceReduction"
+ checked={data.unfairSubcontractPricing.noUniformPriceReduction}
+ onCheckedChange={(checked) => handleUnfairPricingChange('noUniformPriceReduction', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <Label htmlFor="noUniformPriceReduction" className="text-sm font-medium">
+ 정당한 이유 없이 일률적 비율로 단가 인하 불가
+ </Label>
+ </div>
+
+ <div className="flex items-start space-x-3">
+ <Checkbox
+ id="noDiscriminatoryTreatment"
+ checked={data.unfairSubcontractPricing.noDiscriminatoryTreatment}
+ onCheckedChange={(checked) => handleUnfairPricingChange('noDiscriminatoryTreatment', checked as boolean)}
+ disabled={!isEnabled || readOnly}
+ />
+ <Label htmlFor="noDiscriminatoryTreatment" className="text-sm font-medium">
+ 정당한 이유 없이 특정 사업자를 차별 취급 하도록 대금 결정 불가
+ </Label>
+ </div>
+ </div>
+ </div>
+ </AccordionContent>
+ </AccordionItem>
+
+ {/* 위반/위반의심 시 추가 정보 */}
+ {isViolationOrSuspected && (
+ <AccordionItem value="violation-details">
+ <AccordionTrigger className="text-lg font-semibold">
+ 위반/위반의심 상세 정보
+ </AccordionTrigger>
+ <AccordionContent>
+ <div className="space-y-4 p-4">
+ <Alert>
+ <AlertTriangle className="h-4 w-4" />
+ <AlertDescription>
+ 점검결과가 위반 또는 위반의심인 경우 아래 정보를 필수로 입력해주세요.
+ </AlertDescription>
+ </Alert>
+
+ <div className="grid grid-cols-1 md:grid-cols-2 gap-4">
+ <div className="space-y-2">
+ <Label htmlFor="responsibleDepartment">귀책부서 *</Label>
+ <Textarea
+ id="responsibleDepartment"
+ value={data.responsibleDepartment || ''}
+ onChange={(e) => handleFieldChange('responsibleDepartment', e.target.value)}
+ placeholder="귀책부서를 입력하세요"
+ rows={2}
+ disabled={!isEnabled || readOnly}
+ />
+ </div>
+
+ <div className="space-y-2">
+ <Label htmlFor="cause">원인 *</Label>
+ <Select
+ value={data.cause || ''}
+ onValueChange={(value) => handleFieldChange('cause', value)}
+ disabled={!isEnabled || readOnly}
+ >
+ <SelectTrigger disabled={!isEnabled || readOnly}>
+ <SelectValue placeholder="원인을 선택하세요" />
+ </SelectTrigger>
+ <SelectContent>
+ {causeOptions.map((option) => (
+ <SelectItem key={option.value} value={option.value}>
+ {option.label}
+ </SelectItem>
+ ))}
+ </SelectContent>
+ </Select>
+ {data.cause === '기타' && (
+ <Textarea
+ value={data.causeOther || ''}
+ onChange={(e) => handleFieldChange('causeOther', e.target.value)}
+ placeholder="기타 원인을 입력하세요"
+ rows={2}
+ disabled={!isEnabled || readOnly}
+ />
+ )}
+ </div>
+
+ <div className="space-y-2">
+ <Label htmlFor="countermeasure">대책 *</Label>
+ <Select
+ value={data.countermeasure || ''}
+ onValueChange={(value) => handleFieldChange('countermeasure', value)}
+ disabled={!isEnabled || readOnly}
+ >
+ <SelectTrigger disabled={!isEnabled || readOnly}>
+ <SelectValue placeholder="대책을 선택하세요" />
+ </SelectTrigger>
+ <SelectContent>
+ {countermeasureOptions.map((option) => (
+ <SelectItem key={option.value} value={option.value}>
+ {option.label}
+ </SelectItem>
+ ))}
+ </SelectContent>
+ </Select>
+ {data.countermeasure === '기타' && (
+ <Textarea
+ value={data.countermeasureOther || ''}
+ onChange={(e) => handleFieldChange('countermeasureOther', e.target.value)}
+ placeholder="기타 대책을 입력하세요"
+ rows={2}
+ disabled={!isEnabled || readOnly}
+ />
+ )}
+ </div>
+ </div>
+ </div>
+ </AccordionContent>
+ </AccordionItem>
+ )}
+ </Accordion>
+
+ {/* 저장 버튼 */}
+ {!readOnly && (
+ <div className="flex justify-end pt-4 border-t">
+ <Button onClick={handleSave} className="flex items-center gap-2">
+ <Save className="h-4 w-4" />
+ 체크리스트 저장
+ </Button>
+ </div>
+ )}
+ </CardContent>
+ </Card>
+ </AccordionContent>
+ </AccordionItem>
+ </Accordion>
+ )
+}