"use client"; import React, { useState, useEffect } from "react"; import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter, } from "@/components/ui/dialog"; import { Button } from "@/components/ui/button"; import { Input } from "@/components/ui/input"; import { Label } from "@/components/ui/label"; import { Textarea } from "@/components/ui/textarea"; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue, } from "@/components/ui/select"; import { Switch } from "@/components/ui/switch"; import { Badge } from "@/components/ui/badge"; import { toast } from "sonner"; import { BatchAPI, BatchJob } from "@/lib/api/batch"; import { CollectionAPI } from "@/lib/api/collection"; interface BatchJobModalProps { isOpen: boolean; onClose: () => void; onSave: () => void; job?: BatchJob | null; } export default function BatchJobModal({ isOpen, onClose, onSave, job, }: BatchJobModalProps) { const [formData, setFormData] = useState>({ job_name: "", description: "", job_type: "collection", schedule_cron: "", is_active: "Y", config_json: {}, execution_count: 0, success_count: 0, failure_count: 0, }); const [isLoading, setIsLoading] = useState(false); const [jobTypes, setJobTypes] = useState>([]); const [schedulePresets, setSchedulePresets] = useState>([]); const [collectionConfigs, setCollectionConfigs] = useState([]); useEffect(() => { if (isOpen) { loadJobTypes(); loadSchedulePresets(); loadCollectionConfigs(); if (job) { setFormData({ ...job, config_json: job.config_json || {}, }); } else { setFormData({ job_name: "", description: "", job_type: "collection", schedule_cron: "", is_active: "Y", config_json: {}, execution_count: 0, success_count: 0, failure_count: 0, }); } } }, [isOpen, job]); const loadJobTypes = async () => { try { const types = await BatchAPI.getSupportedJobTypes(); setJobTypes(types); } catch (error) { console.error("작업 타입 조회 오류:", error); } }; const loadSchedulePresets = async () => { try { const presets = await BatchAPI.getSchedulePresets(); setSchedulePresets(presets); } catch (error) { console.error("스케줄 프리셋 조회 오류:", error); } }; const loadCollectionConfigs = async () => { try { const configs = await CollectionAPI.getCollectionConfigs({ is_active: "Y", }); setCollectionConfigs(configs); } catch (error) { console.error("수집 설정 조회 오류:", error); } }; const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); if (!formData.job_name || !formData.job_type) { toast.error("필수 필드를 모두 입력해주세요."); return; } setIsLoading(true); try { if (job?.id) { await BatchAPI.updateBatchJob(job.id, formData); toast.success("배치 작업이 수정되었습니다."); } else { await BatchAPI.createBatchJob(formData as BatchJob); toast.success("배치 작업이 생성되었습니다."); } onSave(); onClose(); } catch (error) { console.error("배치 작업 저장 오류:", error); toast.error( error instanceof Error ? error.message : "배치 작업 저장에 실패했습니다." ); } finally { setIsLoading(false); } }; const handleSchedulePresetSelect = (preset: string) => { setFormData(prev => ({ ...prev, schedule_cron: preset, })); }; const handleJobTypeChange = (jobType: string) => { setFormData(prev => ({ ...prev, job_type: jobType as any, config_json: {}, })); }; const handleCollectionConfigChange = (configId: string) => { setFormData(prev => ({ ...prev, config_json: { ...prev.config_json, collectionConfigId: parseInt(configId), }, })); }; const getJobTypeIcon = (type: string) => { switch (type) { case 'collection': return '📥'; case 'sync': return '🔄'; case 'cleanup': return '🧹'; case 'custom': return '⚙️'; default: return '📋'; } }; const getStatusColor = (status: string) => { switch (status) { case 'Y': return 'bg-green-100 text-green-800'; case 'N': return 'bg-red-100 text-red-800'; default: return 'bg-gray-100 text-gray-800'; } }; return ( {job ? "배치 작업 수정" : "새 배치 작업"}
{/* 기본 정보 */}

기본 정보

setFormData(prev => ({ ...prev, job_name: e.target.value })) } placeholder="배치 작업명을 입력하세요" required />