'use client' import React, { useState, useEffect } from 'react' import { useSession } from 'next-auth/react' import { Input } from '@/components/ui/input' import { Button } from '@/components/ui/button' import { Accordion, AccordionContent, AccordionItem, AccordionTrigger } from '@/components/ui/accordion' import { Checkbox } from '@/components/ui/checkbox' import { Plus, Trash2, Save, LoaderIcon, DollarSign } from 'lucide-react' import { getFieldServiceRate, updateFieldServiceRate } from '../service' import { toast } from 'sonner' interface FieldServiceRateProps { contractId: number contractType?: string } interface FieldServiceRateItem { id: string levelOfSpecialist: string description: string rateCurrency: string onshoreRate: string offshoreRate: string rateUnit: string remark: string } export function FieldServiceRate({ contractId }: FieldServiceRateProps) { const session = useSession() const [isLoading, setIsLoading] = useState(false) const [isEnabled, setIsEnabled] = useState(true) // 특정 계약종류를 제외한 일반계약은 Default로 표시 const isDisabled = false const [fieldServiceRates, setFieldServiceRates] = useState([]) // 초기 데이터 로드 useEffect(() => { const loadFieldServiceRate = async () => { try { const data = await getFieldServiceRate(contractId) if (data && data.enabled !== undefined) { setIsEnabled(data.enabled) setFieldServiceRates(data.fieldServiceRates || []) } else { } } catch (error) { console.error('Field Service Rate 데이터 로드 실패:', error) toast.error('Field Service Rate 데이터를 불러오는데 실패했습니다.') } } loadFieldServiceRate() }, [contractId]) const addFieldServiceRateRow = () => { const newRow: FieldServiceRateItem = { id: Date.now().toString(), levelOfSpecialist: '', description: '', rateCurrency: 'USD', onshoreRate: '', offshoreRate: '', rateUnit: 'day', remark: '' } setFieldServiceRates([...fieldServiceRates, newRow]) } const removeFieldServiceRateRow = (id: string) => { setFieldServiceRates(fieldServiceRates.filter(item => item.id !== id)) } const updateFieldServiceRateData = (id: string, field: keyof FieldServiceRateItem, value: string) => { setFieldServiceRates(prev => prev.map(item => item.id === id ? { ...item, [field]: value } : item ) ) } const handleSaveFieldServiceRate = async () => { if (!session.data?.user?.id) { toast.error('로그인이 필요합니다.') return } setIsLoading(true) try { const fieldServiceRateData = { enabled: isEnabled, fieldServiceRates: fieldServiceRates } await updateFieldServiceRate(contractId, fieldServiceRateData, Number(session.data.user.id)) toast.success('Field Service Rate가 성공적으로 저장되었습니다.') } catch (error) { console.error('Field Service Rate 저장 실패:', error) toast.error('Field Service Rate 저장에 실패했습니다.') } finally { setIsLoading(false) } } return (
Field Service Rate
{/* 체크박스 */}
{ if (!isDisabled) { setIsEnabled(checked as boolean) } }} /> Field Service Rate 활성화
{/* Field Service Rate 테이블 */}

Field Service Rate

{fieldServiceRates.map((item, index) => ( ))}
No. Level of Specialist Description Rate Currency Onshore Rate Offshore Rate Rate Unit Remark Action
{index + 1} updateFieldServiceRateData(item.id, 'levelOfSpecialist', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'description', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'rateCurrency', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'onshoreRate', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'offshoreRate', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'rateUnit', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" /> updateFieldServiceRateData(item.id, 'remark', e.target.value)} disabled={isDisabled || !isEnabled} className="border-0 bg-transparent p-0 h-auto" />
{/* Note 정보 */}

Note #1: Air fare, travelling costs and hours, Visa, training, medical test and any additional applications are included.

Note #2: Accommodation, meal and local transportation are included.

{/* 저장 버튼 */}
) }