데이터 관계도 삭제, 복사 구현

This commit is contained in:
hyeonsu
2025-09-09 13:10:03 +09:00
parent 3a24fd3ebd
commit 142cfe022b
5 changed files with 393 additions and 33 deletions

View File

@@ -1,6 +1,6 @@
"use client";
import { useState, useEffect } from "react";
import { useState, useEffect, useCallback } from "react";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Badge } from "@/components/ui/badge";
@@ -12,6 +12,14 @@ import {
DropdownMenuItem,
DropdownMenuTrigger,
} from "@/components/ui/dropdown-menu";
import {
Dialog,
DialogContent,
DialogDescription,
DialogFooter,
DialogHeader,
DialogTitle,
} from "@/components/ui/dialog";
import { MoreHorizontal, Trash2, Copy, Plus, Search, Network, Database, Calendar, User } from "lucide-react";
import { DataFlowAPI, DataFlowDiagram } from "@/lib/api/dataflow";
import { toast } from "sonner";
@@ -30,49 +38,86 @@ export default function DataFlowList({ onDiagramSelect, selectedDiagram, onDesig
const [totalPages, setTotalPages] = useState(1);
const [total, setTotal] = useState(0);
// 모달 상태
const [showCopyModal, setShowCopyModal] = useState(false);
const [showDeleteModal, setShowDeleteModal] = useState(false);
const [selectedDiagramForAction, setSelectedDiagramForAction] = useState<DataFlowDiagram | null>(null);
// 목록 로드 함수 분리
const loadDiagrams = useCallback(async () => {
try {
setLoading(true);
const response = await DataFlowAPI.getDataFlowDiagrams(currentPage, 20, searchTerm);
setDiagrams(response.diagrams || []);
setTotal(response.total || 0);
setTotalPages(Math.max(1, Math.ceil((response.total || 0) / 20)));
} catch (error) {
console.error("관계도 목록 조회 실패", error);
toast.error("관계도 목록을 불러오는데 실패했습니다.");
} finally {
setLoading(false);
}
}, [currentPage, searchTerm]);
// 관계도 목록 로드
useEffect(() => {
let abort = false;
const load = async () => {
try {
setLoading(true);
const response = await DataFlowAPI.getDataFlowDiagrams(currentPage, 20, searchTerm);
if (abort) return;
setDiagrams(response.diagrams || []);
setTotal(response.total || 0);
setTotalPages(Math.max(1, Math.ceil((response.total || 0) / 20)));
} catch (error) {
console.error("관계도 목록 조회 실패", error);
setDiagrams([]);
setTotalPages(1);
setTotal(0);
toast.error("관계도 목록을 불러오는데 실패했습니다.");
} finally {
if (!abort) setLoading(false);
}
};
load();
return () => {
abort = true;
};
}, [currentPage, searchTerm]);
loadDiagrams();
}, [loadDiagrams]);
const handleDiagramSelect = (diagram: DataFlowDiagram) => {
onDiagramSelect(diagram);
};
const handleDelete = (diagram: DataFlowDiagram) => {
if (confirm(`"${diagram.diagramName}" 관계도를 삭제하시겠습니까?`)) {
// 삭제 API 호출
console.log("삭제:", diagram);
toast.info("삭제 기능은 아직 구현되지 않았습니다.");
}
setSelectedDiagramForAction(diagram);
setShowDeleteModal(true);
};
const handleCopy = (diagram: DataFlowDiagram) => {
console.log("복사:", diagram);
toast.info("복사 기능은 아직 구현되지 않았습니다.");
setSelectedDiagramForAction(diagram);
setShowCopyModal(true);
};
// 복사 확인
const handleConfirmCopy = async () => {
if (!selectedDiagramForAction) return;
try {
setLoading(true);
const newDiagramName = await DataFlowAPI.copyDiagram(selectedDiagramForAction.diagramName);
toast.success(`관계도가 성공적으로 복사되었습니다: ${newDiagramName}`);
// 목록 새로고침
await loadDiagrams();
} catch (error) {
console.error("관계도 복사 실패:", error);
toast.error("관계도 복사에 실패했습니다.");
} finally {
setLoading(false);
setShowCopyModal(false);
setSelectedDiagramForAction(null);
}
};
// 삭제 확인
const handleConfirmDelete = async () => {
if (!selectedDiagramForAction) return;
try {
setLoading(true);
const deletedCount = await DataFlowAPI.deleteDiagram(selectedDiagramForAction.diagramName);
toast.success(`관계도가 삭제되었습니다 (${deletedCount}개 관계 삭제)`);
// 목록 새로고침
await loadDiagrams();
} catch (error) {
console.error("관계도 삭제 실패:", error);
toast.error("관계도 삭제에 실패했습니다.");
} finally {
setLoading(false);
setShowDeleteModal(false);
setSelectedDiagramForAction(null);
}
};
// 연결 타입에 따른 배지 색상
@@ -291,6 +336,52 @@ export default function DataFlowList({ onDiagramSelect, selectedDiagram, onDesig
</Button>
</div>
)}
{/* 복사 확인 모달 */}
<Dialog open={showCopyModal} onOpenChange={setShowCopyModal}>
<DialogContent>
<DialogHeader>
<DialogTitle> </DialogTitle>
<DialogDescription>
&ldquo;{selectedDiagramForAction?.diagramName}&rdquo; ?
<br />
(1), (2), (3)... .
</DialogDescription>
</DialogHeader>
<DialogFooter>
<Button variant="outline" onClick={() => setShowCopyModal(false)}>
</Button>
<Button onClick={handleConfirmCopy} disabled={loading}>
{loading ? "복사 중..." : "복사"}
</Button>
</DialogFooter>
</DialogContent>
</Dialog>
{/* 삭제 확인 모달 */}
<Dialog open={showDeleteModal} onOpenChange={setShowDeleteModal}>
<DialogContent>
<DialogHeader>
<DialogTitle className="text-red-600"> </DialogTitle>
<DialogDescription>
&ldquo;{selectedDiagramForAction?.diagramName}&rdquo; ?
<br />
<span className="font-medium text-red-600">
, .
</span>
</DialogDescription>
</DialogHeader>
<DialogFooter>
<Button variant="outline" onClick={() => setShowDeleteModal(false)}>
</Button>
<Button variant="destructive" onClick={handleConfirmDelete} disabled={loading}>
{loading ? "삭제 중..." : "삭제"}
</Button>
</DialogFooter>
</DialogContent>
</Dialog>
</div>
);
}