Files
sam-docs/frontend/api-specs/account-ledger-service-api.md

12 KiB

계정별원장 API 명세 (서비스 이관)

작성일: 2026-03-20 상태: API 완료, React 구현 대기 대상: React 프론트엔드 개발자


1. 개요

회계관리 메뉴에 계정별원장 화면을 구현한다. 선택한 계정과목의 기간별 거래 내역을 조회하고, 월별 소계/누계/잔액을 표시한다. 카드거래인 경우 카드사·가맹점 정보를 추가로 표시하고, 행 클릭 시 전표 상세를 모달로 보여준다.

메뉴 위치

회계관리
├── 일반전표입력       ← 기존
├── 계정별원장         ← 이 화면
├── 손익계산서         ← 기존
├── ...

2. API 엔드포인트

2.1 계정별원장 조회

GET /api/v1/account-ledger

요청 파라미터 (Query String):

파라미터 타입 필수 설명 예시
start_date string(date) Y 조회 시작일 2026-01-01
end_date string(date) Y 조회 종료일 2026-03-20
account_code string Y 계정과목 코드 81100

응답 예시:

{
  "success": true,
  "message": "조회되었습니다.",
  "data": {
    "account": {
      "code": "81100",
      "name": "복리후생비",
      "category": "expense"
    },
    "period": {
      "start_date": "2026-01-01",
      "end_date": "2026-03-20"
    },
    "carry_forward": {
      "debit": 0,
      "credit": 0,
      "balance": 0
    },
    "monthly_data": [
      {
        "month": "2026-01",
        "items": [
          {
            "date": "2026-01-11",
            "description": "복리후생비",
            "trading_partner_name": "스타벅스 강남점",
            "biz_no": "1234567890",
            "debit_amount": 160000,
            "credit_amount": 0,
            "balance": 160000,
            "source_type": "ecard_transaction",
            "source_id": 45,
            "card_tx": {
              "card_num": "9411320012345678",
              "card_company_name": "삼성카드",
              "merchant_name": "스타벅스 강남점",
              "merchant_biz_num": "1234567890",
              "deduction_type": "deductible",
              "supply_amount": 145455,
              "tax_amount": 14545,
              "approval_amount": 160000
            }
          },
          {
            "date": "2026-01-15",
            "description": "직원 야근 식대",
            "trading_partner_name": null,
            "biz_no": null,
            "debit_amount": 50000,
            "credit_amount": 0,
            "balance": 210000,
            "source_type": "journal",
            "source_id": 52,
            "card_tx": null
          }
        ],
        "subtotal": { "debit": 210000, "credit": 0 },
        "cumulative": { "debit": 210000, "credit": 0 }
      }
    ],
    "grand_total": {
      "debit": 210000,
      "credit": 0,
      "balance": 210000
    }
  }
}

2.2 관련 API

API 용도 비고
GET /api/v1/account-subjects?selectable=true 계정과목 목록 (필터 드롭다운) selectable=true → depth=3 입력 가능 계정만
GET /api/v1/general-journal-entries/{id} 전표 상세 (드릴다운 모달) source_id로 조회

3. TypeScript 인터페이스

// 계정별원장 응답
interface AccountLedgerResponse {
  success: boolean;
  message: string;
  data: {
    account: {
      code: string;
      name: string;
      category: 'asset' | 'liability' | 'capital' | 'revenue' | 'expense';
    } | null;
    period: {
      start_date: string;
      end_date: string;
    };
    carry_forward: {
      debit: number;
      credit: number;
      balance: number;
    };
    monthly_data: MonthlyData[];
    grand_total: {
      debit: number;
      credit: number;
      balance: number;
    };
  };
}

interface MonthlyData {
  month: string;            // "2026-03"
  items: LedgerItem[];
  subtotal: { debit: number; credit: number };
  cumulative: { debit: number; credit: number };
}

interface LedgerItem {
  date: string;                          // "2026-03-01"
  description: string | null;
  trading_partner_name: string | null;   // 카드거래 시 가맹점명으로 대체됨
  biz_no: string | null;                // 카드거래 시 가맹점 사업자번호로 대체됨
  debit_amount: number;
  credit_amount: number;
  balance: number;                       // 누적 잔액
  source_type: string;                   // 'journal' | 'ecard_transaction' | 'bank_transaction' 등
  source_id: number;                     // 전표 ID
  card_tx: CardTransaction | null;       // 카드거래 상세 (없으면 null)
}

interface CardTransaction {
  card_num: string;           // 카드번호 전체 (프론트에서 마스킹: ····끝4자리)
  card_company_name: string;  // "삼성카드"
  merchant_name: string;      // "스타벅스 강남점"
  merchant_biz_num: string;   // "1234567890"
  deduction_type: string;     // "deductible" | "non_deductible"
  supply_amount: number;      // 공급가액
  tax_amount: number;         // 세액
  approval_amount: number;    // 승인금액 (공급가 + 세액)
}

// 전표 상세 (드릴다운 모달용)
interface JournalEntryDetail {
  id: number;
  entry_no: string;           // "JE-20260311-001"
  entry_date: string;
  entry_type: string;
  description: string | null;
  total_debit: number;
  total_credit: number;
  status: 'draft' | 'confirmed';
  source_type: string | null;
  created_by_name: string | null;
  lines: JournalEntryLine[];
}

interface JournalEntryLine {
  line_no: number;
  dc_type: 'debit' | 'credit';
  account_code: string;
  account_name: string;
  trading_partner_name: string | null;
  debit_amount: number;
  credit_amount: number;
  description: string | null;
}

4. 화면 구현 가이드

4.1 화면 구조

┌──────────────────────────────────────────────────┐
│ 📖 계정별원장                              [인쇄] │
├──────────────────────────────────────────────────┤
│ 조회기간: [시작일] ~ [종료일]                       │
│ 계정과목: [코드/이름 자동완성 검색]        [조회]   │
├──────────────────────────────────────────────────┤
│ 81100 복리후생비  (2026-01-01 ~ 2026-03-20)      │
├───────┬────────────────┬──────┬──────┬─────┬─────┬───────┤
│ 날짜  │ 적요            │거래처│사업자│차변  │대변  │ 잔액  │
├───────┼────────────────┼──────┼──────┼─────┼─────┼───────┤
│   -   │ 이월잔액        │      │      │  0  │  0  │   0   │
│01-11  │ 💳복리후생 [공제]│스타벅│12345 │160K │     │ 160K  │
│       │ 삼성 ····5678   │      │      │     │     │       │
│01-15  │ 직원 야근 식대  │      │      │ 50K │     │ 210K  │
│-------│---  2026-01 계 ─│──────│──────│210K │  0  │       │
│       │    누 계        │      │      │210K │  0  │       │
│02-03  │ ...             │      │      │     │     │       │
│-------│--- 총 합 계 ────│──────│──────│합계 │합계 │최종잔│
└───────┴────────────────┴──────┴──────┴─────┴─────┴───────┘

4.2 조회 필터

계정과목 검색 드롭다운:

GET /api/v1/account-subjects?selectable=true
  • 텍스트 입력 시 코드 + 이름으로 클라이언트 필터링
  • 키보드 방향키(↑↓) + Enter로 선택 가능
  • 최대 50개까지 드롭다운 표시
  • 선택 후 코드 이름 형태로 입력창에 표시 (예: "81100 복리후생비")

기간 기본값: 당월 1일 ~ 오늘

4.3 테이블 행 유형

행 유형 조건 스타일
이월잔액 carry_forward.balance !== 0 노란 배경, 굵은 글씨
거래 행 items[] 일반 + hover 효과, 클릭 가능
카드거래 행 item.card_tx !== null 💳 아이콘 + 배지 + 서브텍스트
월 소계 매월 마지막 회색 배경, 굵은 글씨
누계 매월 마지막 회색 배경, 굵은 글씨
총합계 마지막 인디고 배경, 굵은 글씨

4.4 카드거래 행 표시

card_tx !== null인 행은 적요 셀에 추가 정보를 표시한다:

┌──────────────────────────────────────────────┐
│ 💳 복리후생비                    ┌─────────┐  │
│                                 │  공제   │  │  ← deduction_type === 'deductible'
│ 삼성카드 ····5678               └─────────┘  │  ← card_company_name + 끝4자리
└──────────────────────────────────────────────┘
  • deduction_type === 'deductible' → 초록 배지 [공제]
  • deduction_type === 'non_deductible' → 빨간 배지 [불공제]
  • 카드번호 마스킹: '····' + card_tx.card_num.slice(-4)

4.5 드릴다운 (전표 상세 모달)

거래 행 클릭 시 source_type에 따라 전표 상세를 모달로 표시:

const handleRowClick = async (item: LedgerItem) => {
  if (['journal', 'ecard_transaction', 'bank_transaction'].includes(item.source_type)) {
    const res = await authenticatedFetch(`/api/v1/general-journal-entries/${item.source_id}`);
    // → 전표 상세 모달 오픈
    //   - 전표 헤더: 전표번호, 일자, 적요, 상태
    //   - 분개 라인 테이블: No, 차/대, 계정코드, 계정명, 거래처, 차변, 대변, 적요
    //   - 카드정보 (card_tx가 있으면): 카드번호, 카드사, 가맹점, 공급가, 세액
    //   - [원본 보기] 버튼: 일반전표 화면으로 이동
  }
};

모달 구성:

섹션 내용
헤더 전표번호, 일자, [원본 보기] 버튼, [닫기] 버튼
전표 요약 전표번호, 일자, 적요, 작성자, 상태, 출처(source_type)
카드정보 (card_tx 있을 때) 카드번호(마스킹), 카드사, 가맹점, 사업자번호, 공급가, 세액, [공제]/[불공제]
분개 테이블 No, 구분(차/대), 계정코드, 계정명, 거래처, 차변, 대변, 적요
합계 차변 합계, 대변 합계

4.6 잔액 계산

서버에서 이미 계산된 balance 값을 사용한다. 프론트에서 별도 계산 불필요.

음수 잔액 표시: (100,000) 괄호 형식 또는 음수 표시

4.7 숫자 포맷

const fmt = (n: number): string => {
  if (n === 0 || n === null || n === undefined) return '';
  if (n < 0) return '(' + Math.abs(n).toLocaleString() + ')';
  return n.toLocaleString();
};
  • 0은 빈 문자열로 표시 (공란)
  • 음수는 괄호 표시
  • 천 단위 콤마

4.8 인쇄

  • window.print() 사용
  • CSS @media print { .no-print { display: none !important; } }
  • 조회 조건 패널, 인쇄 버튼에 no-print 클래스 적용

5. MNG 참고 화면

MNG 개발서버에서 동일 기능을 확인할 수 있다:

https://admin.codebridge-x.com → 회계/세무관리 > 계정별원장


관련 문서


최종 업데이트: 2026-03-20