diff --git a/src/app/(service)/(my)/my-page/_components/withdrawal-confirm-modal.tsx b/src/app/(service)/(my)/my-page/_components/withdrawal-confirm-modal.tsx index 6f18a6658..5aa25b616 100644 --- a/src/app/(service)/(my)/my-page/_components/withdrawal-confirm-modal.tsx +++ b/src/app/(service)/(my)/my-page/_components/withdrawal-confirm-modal.tsx @@ -3,20 +3,21 @@ import { cn } from '@/components/common/ui/(shadcn)/lib/utils'; import Button from '@/components/common/ui/button'; import { Modal } from '@/components/common/ui/modal'; +import { useWithdrawMemberMutation } from '@/hooks/queries/user/use-withdraw-member-mutation'; interface WithdrawalConfirmModalProps { open: boolean; onOpenChange: (open: boolean) => void; } -// TODO: withdrawal API not yet available — wire DELETE /api/v1/members/me when added export default function WithdrawalConfirmModal({ open, onOpenChange, }: WithdrawalConfirmModalProps) { - const handleConfirm = async () => { - // TODO: call DELETE /api/v1/members/me and redirect to / - onOpenChange(false); + const { mutate: withdraw, isPending } = useWithdrawMemberMutation(); + + const handleConfirm = () => { + withdraw(); }; return ( @@ -88,6 +89,7 @@ export default function WithdrawalConfirmModal({ color="secondary" size="medium" className="flex-1" + disabled={isPending} onClick={() => onOpenChange(false)} > 취소 @@ -96,9 +98,10 @@ export default function WithdrawalConfirmModal({ color="primary" size="medium" className="flex-1" + disabled={isPending} onClick={handleConfirm} > - 탈퇴하기 + {isPending ? '탈퇴 중...' : '탈퇴하기'} diff --git a/src/hooks/queries/user/use-withdraw-member-mutation.ts b/src/hooks/queries/user/use-withdraw-member-mutation.ts new file mode 100644 index 000000000..ef40ff528 --- /dev/null +++ b/src/hooks/queries/user/use-withdraw-member-mutation.ts @@ -0,0 +1,25 @@ +import { useMutation } from '@tanstack/react-query'; +import { axiosInstanceV6 } from '@/api/client/axios'; +import { AUTH_ROUTE_PATHS } from '@/features/auth/model/auth-route'; +import { clearClientAuthStateAndRedirect } from '@/features/auth/model/client-auth-cleanup'; +import { useToastStore } from '@/stores/use-toast-store'; +import { analyzeError, sendErrorToSentry } from '@/utils/error-handler'; + +export const useWithdrawMemberMutation = () => { + const showToast = useToastStore((state) => state.showToast); + + return useMutation({ + mutationFn: () => + axiosInstanceV6.delete('mypage/class/withdraw', { + data: { agreedToClassWithdrawalNotice: true }, + }), + onSuccess: () => { + clearClientAuthStateAndRedirect(AUTH_ROUTE_PATHS.LANDING); + }, + onError: (error) => { + const errorInfo = analyzeError(error); + showToast(errorInfo.userMessage, 'error'); + sendErrorToSentry(errorInfo, { source: 'useWithdrawMemberMutation' }); + }, + }); +};