diff options
Diffstat (limited to 'components/knox/approval')
| -rw-r--r-- | components/knox/approval/ApprovalCancel.tsx | 127 | ||||
| -rw-r--r-- | components/knox/approval/ApprovalDetail.tsx | 2 | ||||
| -rw-r--r-- | components/knox/approval/ApprovalList.tsx | 2 |
3 files changed, 83 insertions, 48 deletions
diff --git a/components/knox/approval/ApprovalCancel.tsx b/components/knox/approval/ApprovalCancel.tsx index b40b43df..62afce94 100644 --- a/components/knox/approval/ApprovalCancel.tsx +++ b/components/knox/approval/ApprovalCancel.tsx @@ -7,6 +7,7 @@ import { Input } from '@/components/ui/input'; import { Label } from '@/components/ui/label'; import { Badge } from '@/components/ui/badge'; import { Separator } from '@/components/ui/separator'; +import { Textarea } from '@/components/ui/textarea'; import { AlertDialog, AlertDialogAction, AlertDialogCancel, AlertDialogContent, AlertDialogDescription, AlertDialogFooter, AlertDialogHeader, AlertDialogTitle, AlertDialogTrigger } from '@/components/ui/alert-dialog'; import { toast } from 'sonner'; import { Loader2, XCircle, AlertTriangle, CheckCircle } from 'lucide-react'; @@ -47,6 +48,7 @@ export default function ApprovalCancel({ const [isCancelling, setIsCancelling] = useState(false); const [error, setError] = useState<string | null>(null); const [cancelResult, setCancelResult] = useState<{ apInfId: string } | null>(null); + const [cancelOpinion, setCancelOpinion] = useState(''); const fetchApprovalDetail = async () => { if (!apInfId.trim()) { @@ -58,11 +60,12 @@ export default function ApprovalCancel({ setError(null); setApprovalDetail(null); setCancelResult(null); + setCancelOpinion(''); try { const response = await getApprovalDetail(apInfId); - if (response.result === 'SUCCESS') { + if (response.result === 'success') { setApprovalDetail(response.data); } else { setError('결재 정보를 가져오는데 실패했습니다.'); @@ -80,12 +83,17 @@ export default function ApprovalCancel({ const handleCancelApproval = async () => { if (!approvalDetail) return; + if (!cancelOpinion.trim()) { + toast.error('상신취소 의견을 입력해주세요.'); + return; + } + setIsCancelling(true); try { - const response = await cancelApproval(approvalDetail.apInfId); + const response = await cancelApproval(approvalDetail.apInfId, cancelOpinion); - if (response.result === 'SUCCESS') { + if (response.result === 'success') { setCancelResult({ apInfId: response.data.apInfId }); toast.success('결재가 성공적으로 취소되었습니다.'); onCancelSuccess?.(response.data.apInfId); @@ -95,6 +103,9 @@ export default function ApprovalCancel({ ...approvalDetail, status: '4' // 상신취소 }); + + // 의견 초기화 + setCancelOpinion(''); } else { toast.error('결재 취소에 실패했습니다.'); } @@ -288,54 +299,78 @@ export default function ApprovalCancel({ </div> </div> - {/* 취소 버튼 */} + {/* 취소 의견 및 버튼 */} {canCancelApproval(approvalDetail.status) && ( <> <Separator /> - <div className="flex justify-end"> - <AlertDialog> - <AlertDialogTrigger asChild> - <Button variant="destructive" disabled={isCancelling}> - {isCancelling ? ( - <> - <Loader2 className="w-4 h-4 mr-2 animate-spin" /> - 취소 중... - </> - ) : ( - <> - <XCircle className="w-4 h-4 mr-2" /> - 결재 취소 - </> - )} - </Button> - </AlertDialogTrigger> - <AlertDialogContent> - <AlertDialogHeader> - <AlertDialogTitle>결재 취소 확인</AlertDialogTitle> - <AlertDialogDescription> - 정말로 이 결재를 취소하시겠습니까? - <br /> - <br /> - <strong>결재 ID:</strong> {approvalDetail.apInfId} - <br /> - <strong>제목:</strong> {approvalDetail.subject} - <br /> - <br /> - 이 작업은 되돌릴 수 없습니다. - </AlertDialogDescription> - </AlertDialogHeader> - <AlertDialogFooter> - <AlertDialogCancel>취소</AlertDialogCancel> - <AlertDialogAction - onClick={handleCancelApproval} - className="bg-red-600 hover:bg-red-700" + <div className="space-y-4"> + <div> + <Label htmlFor="cancelOpinion" className="text-sm font-medium"> + 상신취소 의견 <span className="text-red-500">*</span> + </Label> + <Textarea + id="cancelOpinion" + placeholder="상신취소 사유를 입력해주세요" + value={cancelOpinion} + onChange={(e) => setCancelOpinion(e.target.value)} + className="mt-1" + rows={3} + /> + <p className="text-xs text-gray-500 mt-1"> + 상신취소 의견은 필수 입력 항목입니다. + </p> + </div> + + <div className="flex justify-end"> + <AlertDialog> + <AlertDialogTrigger asChild> + <Button + variant="destructive" + disabled={isCancelling || !cancelOpinion.trim()} > - 결재 취소 - </AlertDialogAction> - </AlertDialogFooter> - </AlertDialogContent> - </AlertDialog> + {isCancelling ? ( + <> + <Loader2 className="w-4 h-4 mr-2 animate-spin" /> + 취소 중... + </> + ) : ( + <> + <XCircle className="w-4 h-4 mr-2" /> + 결재 취소 + </> + )} + </Button> + </AlertDialogTrigger> + <AlertDialogContent> + <AlertDialogHeader> + <AlertDialogTitle>결재 취소 확인</AlertDialogTitle> + <AlertDialogDescription> + 정말로 이 결재를 취소하시겠습니까? + <br /> + <br /> + <strong>결재 ID:</strong> {approvalDetail.apInfId} + <br /> + <strong>제목:</strong> {approvalDetail.subject} + <br /> + <strong>취소 의견:</strong> {cancelOpinion} + <br /> + <br /> + 이 작업은 되돌릴 수 없습니다. + </AlertDialogDescription> + </AlertDialogHeader> + <AlertDialogFooter> + <AlertDialogCancel>취소</AlertDialogCancel> + <AlertDialogAction + onClick={handleCancelApproval} + className="bg-red-600 hover:bg-red-700" + > + 결재 취소 + </AlertDialogAction> + </AlertDialogFooter> + </AlertDialogContent> + </AlertDialog> + </div> </div> </> )} diff --git a/components/knox/approval/ApprovalDetail.tsx b/components/knox/approval/ApprovalDetail.tsx index d6c883cb..c36137b4 100644 --- a/components/knox/approval/ApprovalDetail.tsx +++ b/components/knox/approval/ApprovalDetail.tsx @@ -86,7 +86,7 @@ export default function ApprovalDetail({ getApprovalContent(id) ]); - if (detailResponse.result === 'SUCCESS' && contentResponse.result === 'SUCCESS') { + if (detailResponse.result.toLowerCase() === 'success' && contentResponse.result.toLowerCase() === 'success') { setApprovalData({ detail: detailResponse.data, content: contentResponse.data diff --git a/components/knox/approval/ApprovalList.tsx b/components/knox/approval/ApprovalList.tsx index 3a766901..13a13936 100644 --- a/components/knox/approval/ApprovalList.tsx +++ b/components/knox/approval/ApprovalList.tsx @@ -67,7 +67,7 @@ export default function ApprovalList({ response = await getApprovalHistory(); } - if (response.result === 'SUCCESS') { + if (response.result === 'success') { setListData(response.data as unknown as ListItem[]); } else { setError('목록을 가져오는데 실패했습니다.'); |
