/** * 월 예상 지출 (MonthlyExpense) + 카드/가지급금 (CardManagement) 변환 */ import type { ExpectedExpenseApiResponse, CardTransactionApiResponse, LoanDashboardApiResponse, TaxSimulationApiResponse, } from '../types'; import type { MonthlyExpenseData, CardManagementData, CheckPoint, CheckPointType, } from '@/components/business/CEODashboard/types'; import { formatAmount } from './common'; // ============================================ // 월 예상 지출 (MonthlyExpense) // ============================================ /** * 당월 예상 지출 CheckPoints 생성 */ function generateMonthlyExpenseCheckPoints(api: ExpectedExpenseApiResponse): CheckPoint[] { const checkPoints: CheckPoint[] = []; // 총 예상 지출 checkPoints.push({ id: 'me-total', type: 'info' as CheckPointType, message: `이번 달 예상 지출은 ${formatAmount(api.total_amount)}입니다.`, highlights: [ { text: formatAmount(api.total_amount), color: 'blue' as const }, ], }); return checkPoints; } /** * ExpectedExpense API 응답 → Frontend 타입 변환 * 주의: 실제 API는 상세 분류(매입/카드/어음 등)를 제공하지 않음 * by_transaction_type에서 추출하거나 기본값 사용 */ export function transformMonthlyExpenseResponse(api: ExpectedExpenseApiResponse): MonthlyExpenseData { // transaction_type별 금액 추출 const purchaseTotal = api.by_transaction_type['purchase']?.total ?? 0; const cardTotal = api.by_transaction_type['card']?.total ?? 0; const billTotal = api.by_transaction_type['bill']?.total ?? 0; return { cards: [ { id: 'me1', label: '매입', amount: purchaseTotal, }, { id: 'me2', label: '카드', amount: cardTotal, }, { id: 'me3', label: '발행어음', amount: billTotal, }, { id: 'me4', label: '총 예상 지출 합계', amount: api.total_amount, }, ], checkPoints: generateMonthlyExpenseCheckPoints(api), }; } // ============================================ // 카드/가지급금 (CardManagement) — D1.7 5장 카드 구조 // ============================================ /** * 카드/가지급금 CheckPoints 생성 (D1.7) * * CP1: 법인카드 → 가지급금 전환 경고 * CP2: 인정이자 발생 현황 * CP3: 접대비 불인정 항목 감지 * CP4: 주말 카드 사용 감지 (향후 확장) */ function generateCardManagementCheckPoints( loanApi?: LoanDashboardApiResponse | null, taxApi?: TaxSimulationApiResponse | null, cardApi?: CardTransactionApiResponse | null, ): CheckPoint[] { const checkPoints: CheckPoint[] = []; const totalOutstanding = loanApi?.summary?.total_outstanding ?? 0; const interestRate = taxApi?.loan_summary?.interest_rate ?? 4.6; const recognizedInterest = taxApi?.loan_summary?.recognized_interest ?? 0; // CP1: 법인카드 사용 중 가지급금 전환 경고 if (totalOutstanding > 0) { checkPoints.push({ id: 'cm-cp1', type: 'success' as CheckPointType, message: `법인카드 사용 중 ${formatAmount(totalOutstanding)}이 가지급금으로 전환되었습니다. 연 ${interestRate}% 인정이자가 발생합니다.`, highlights: [ { text: formatAmount(totalOutstanding), color: 'red' as const }, { text: '가지급금', color: 'red' as const }, { text: `연 ${interestRate}% 인정이자`, color: 'red' as const }, ], }); } // CP2: 인정이자 발생 현황 if (totalOutstanding > 0 && recognizedInterest > 0) { checkPoints.push({ id: 'cm-cp2', type: 'success' as CheckPointType, message: `현재 가지급금 ${formatAmount(totalOutstanding)} × ${interestRate}% = 연간 약 ${formatAmount(recognizedInterest)}의 인정이자가 발생 중입니다.`, highlights: [ { text: `연간 약 ${formatAmount(recognizedInterest)}의 인정이자`, color: 'red' as const }, ], }); } // CP3: 접대비 불인정 항목 감지 const entertainmentCount = loanApi?.category_breakdown?.entertainment?.unverified_count ?? 0; if (entertainmentCount > 0) { checkPoints.push({ id: 'cm-cp3', type: 'success' as CheckPointType, message: '상품권/귀금속 등 접대비 불인정 항목 결제 감지. 가지급금 처리 예정입니다.', highlights: [ { text: '불인정 항목 결제 감지', color: 'red' as const }, ], }); } // CP4: 주말 카드 사용 감지 (향후 card-transactions API 확장 시) // 현재는 cardApi 데이터에서 주말 사용 정보가 없으므로 placeholder if (cardApi && cardApi.current_month_total > 0) { // 향후 weekend_amount 필드 추가 시 활성화 } return checkPoints; } /** * CardTransaction API 응답 → Frontend 타입 변환 * D1.7 5장 카드 구조: * - cm1: 카드 (loans category_breakdown.card) * - cm2: 경조사 (loans category_breakdown.congratulatory) * - cm3: 상품권 (loans category_breakdown.gift_certificate) * - cm4: 접대비 (loans category_breakdown.entertainment) * - cm_total: 총 가지급금 합계 (loans summary.total_outstanding) */ export function transformCardManagementResponse( summaryApi: CardTransactionApiResponse, loanApi?: LoanDashboardApiResponse | null, taxApi?: TaxSimulationApiResponse | null, fallbackData?: CardManagementData ): CardManagementData { const breakdown = loanApi?.category_breakdown; const totalOutstanding = loanApi?.summary?.total_outstanding ?? 0; // 카테고리별 금액 추출 const cardAmount = breakdown?.card?.outstanding_amount ?? fallbackData?.cards[0]?.amount ?? 0; const congratulatoryAmount = breakdown?.congratulatory?.outstanding_amount ?? fallbackData?.cards[1]?.amount ?? 0; const giftCertificateAmount = breakdown?.gift_certificate?.outstanding_amount ?? fallbackData?.cards[2]?.amount ?? 0; const entertainmentAmount = breakdown?.entertainment?.outstanding_amount ?? fallbackData?.cards[3]?.amount ?? 0; // 카테고리별 미증빙/미정리 건수 const cardUnverified = breakdown?.card?.unverified_count ?? 0; const congratulatoryUnverified = breakdown?.congratulatory?.unverified_count ?? 0; const giftCertificateUnverified = breakdown?.gift_certificate?.unverified_count ?? 0; const entertainmentUnverified = breakdown?.entertainment?.unverified_count ?? 0; // 총 합계 (API summary 또는 카테고리 합산) const totalAmount = totalOutstanding > 0 ? totalOutstanding : cardAmount + congratulatoryAmount + giftCertificateAmount + entertainmentAmount; // 가지급금 경고 배너 표시 여부 (가지급금 잔액 > 0이면 표시) const hasLoanWarning = totalAmount > 0; return { warningBanner: hasLoanWarning ? (fallbackData?.warningBanner ?? '가지급금 인정이자 4.6%, 법인세 및 연말정산 시 대표자 종합세 가중 주의') : undefined, cards: [ // cm1: 카드 { id: 'cm1', label: '카드', amount: cardAmount, subLabel: cardUnverified > 0 ? `미정리 ${cardUnverified}건` : undefined, subAmount: cardUnverified > 0 ? cardAmount : undefined, isHighlighted: cardUnverified > 0, }, // cm2: 경조사 { id: 'cm2', label: '경조사', amount: congratulatoryAmount, subLabel: congratulatoryUnverified > 0 ? `미증빙 ${congratulatoryUnverified}건` : undefined, subAmount: congratulatoryUnverified > 0 ? congratulatoryAmount : undefined, isHighlighted: congratulatoryUnverified > 0, }, // cm3: 상품권 { id: 'cm3', label: '상품권', amount: giftCertificateAmount, subLabel: giftCertificateUnverified > 0 ? `미증빙 ${giftCertificateUnverified}건` : undefined, subAmount: giftCertificateUnverified > 0 ? giftCertificateAmount : undefined, isHighlighted: giftCertificateUnverified > 0, }, // cm4: 접대비 { id: 'cm4', label: '접대비', amount: entertainmentAmount, subLabel: entertainmentUnverified > 0 ? `미증빙 ${entertainmentUnverified}건` : undefined, subAmount: entertainmentUnverified > 0 ? entertainmentAmount : undefined, isHighlighted: entertainmentUnverified > 0, }, // cm_total: 총 가지급금 합계 { id: 'cm_total', label: '총 가지급금 합계', amount: totalAmount, }, ], checkPoints: generateCardManagementCheckPoints(loanApi, taxApi, summaryApi), }; }