# 바로빌 API SOAP 서비스 기술 참조

> **작성일**: 2026-03-17
> **상태**: 구축 완료 (MNG 100% 동등)
> **코드 위치**: `api/app/Services/Barobill/`

---

## 1. 개요

API 프로젝트에 독립적으로 구축된 바로빌 SOAP 연동 서비스. MNG의 `BarobillService`(1,761줄)를 참고하되 수정하지 않고, API용으로 새로 작성했다. MNG(본사 tenant_id=1)와 API(서비스 tenant_id=2~N)가 각각 독립적으로 SOAP 호출하며, 같은 DB(samdb)를 공유한다.

### 1.1 설계 원칙

```
✅ MNG 코드는 절대 수정/삭제하지 않는다
✅ API와 MNG는 같은 DB를 공유하지만, 각자 독립적으로 SOAP 호출
✅ API Service는 extends Service (tenantId(), apiUserId() 사용)
✅ SOAP 클라이언트는 lazy 초기화, 모드 전환 시 리셋
```

---

## 2. 파일 구조

```
api/app/
├── Services/
│   ├── Barobill/
│   │   ├── BarobillSoapService.php      ← SOAP 클라이언트 래퍼 (핵심)
│   │   ├── BarobillBankSyncService.php  ← 은행 거래 동기화
│   │   ├── BarobillCardSyncService.php  ← 카드 거래 동기화
│   │   └── HometaxSyncService.php       ← 홈택스 세금계산서 동기화
│   └── BarobillService.php              ← 기존 REST (세금계산서 발행 등)
├── Http/Controllers/Api/V1/
│   ├── BarobillSyncController.php       ← 동기화/회원/인증서 API (신규)
│   └── BarobillController.php           ← 기존 설정/URL API (보강됨)
├── Jobs/Barobill/
│   └── SyncBarobillDataJob.php          ← 자동 동기화 스케줄러 Job
└── Models/Barobill/                     ← 기존 16개 모델
```

---

## 3. BarobillSoapService — 전체 메서드 목록

### 3.1 설정/초기화 (7개)

| 메서드 | 설명 |
|--------|------|
| `__construct()` | `.env` 기본 설정 로드 |
| `switchServerMode(bool)` | 테스트/운영 전환 (클라이언트 리셋) |
| `setServerMode(string)` | `'test'` / `'production'` 문자열로 전환 |
| `getServerMode()` | 현재 모드 반환 |
| `checkConfiguration()` | CERTKEY/corpNum 설정 상태 확인 |
| `initForMember(BarobillMember)` | 회원사 기반 모드 자동 전환 |
| `call(service, method, params)` | 범용 SOAP 호출 (에러코드 매핑) |

### 3.2 CORPSTATE — 회원관리 (3개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `registCorp(data)` | `RegistCorp` | 회원사 등록 |
| `updateCorpInfo(data)` | `UpdateCorpInfo` | 회원사 정보 수정 |
| `getCorpState(corpNum)` | `GetCorpState` | 회원사 상태 조회 |

### 3.3 BANKACCOUNT — 계좌조회 (13개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `getBankAccounts(corpNum, availOnly)` | `GetBankAccountEx` | 등록계좌 목록 |
| `getPeriodBankAccountTransLog(...)` | `GetPeriodBankAccountTransLog` | 기간별 입출금 |
| `getDailyBankAccountTransLog(...)` | `GetDailyBankAccountTransLog` | 일별 입출금 |
| `getMonthlyBankAccountTransLog(...)` | `GetMonthlyBankAccountTransLog` | 월별 입출금 |
| `getBankAccountScrapRequestUrl(...)` | `GetBankAccountScrapRequestURL` | 계좌 등록 URL |
| `getBankAccountManagementUrl(...)` | `GetBankAccountManagementURL` | 계좌 관리 URL |
| `getBankAccountLogUrl(...)` | `GetBankAccountLogURL` | 입출금내역 URL |
| `getCertificateRegistUrl(...)` | `GetCertificateRegistURL` | 인증서 등록 URL |
| `checkCertificateValid(corpNum)` | `CheckCERTIsValid` | 인증서 유효성 |
| `getCertificateExpireDate(corpNum)` | `GetCertificateExpireDate` | 인증서 만료일 |
| `getCertificateRegistDate(corpNum)` | `GetCertificateRegistDate` | 인증서 등록일 |
| `getBalanceCostAmount(corpNum)` | `GetBalanceCostAmountEx` | 충전잔액 |
| `getCashChargeUrl(...)` | `GetCashChargeURL` | 현금충전 URL |
| `getBarobillUrl(...)` | `GetBaroBillURL` | 바로빌 범용 URL |

### 3.4 CARD — 카드조회 (11개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `getCards(corpNum, availOnly)` | `GetCardEx2` | 등록카드 목록 |
| `registCard(corpNum, cardData)` | `RegistCardEx` | 카드 등록 |
| `updateCard(corpNum, cardData)` | `UpdateCard` | 카드 정보 수정 |
| `stopCard(corpNum, cardNum)` | `StopCard` | 카드 해지 |
| `cancelStopCard(corpNum, cardNum)` | `CancelStopCard` | 카드 해지 취소 |
| `getPeriodCardLog(...)` | `GetPeriodCardLog` | 기간별 사용내역 |
| `getDailyCardLog(...)` | `GetDailyCardLog` | 일별 사용내역 |
| `getMonthlyCardLog(...)` | `GetMonthlyCardLog` | 월별 사용내역 |
| `getCardScrapRequestUrl(...)` | `GetCardScrapRequestURL` | 카드 등록 URL |
| `getCardManagementUrl(...)` | `GetCardManagementURL` | 카드 관리 URL |
| `getCardLogUrl(...)` | `GetCardLogURL` | 사용내역 URL |

### 3.5 TI — 세금계산서 (3개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `getHomeTaxUrl(...)` | `GetHomeTaxURL` | 매입/매출 관리 URL |
| `getTaxInvoiceIssueUrl(...)` | `GetTaxInvoiceIssueURL` | 세금계산서 발행 URL |
| `getTaxInvoiceListUrl(...)` | `GetTaxInvoiceListURL` | 세금계산서 목록 URL |

### 3.6 KAKAOTALK — 카카오톡 (15개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `getKakaotalkChannels(corpNum)` | `GetKakaotalkChannels` | 채널 목록 |
| `getKakaotalkChannelManagementUrl(...)` | `GetKakaotalkChannelManagementURL` | 채널 관리 URL |
| `getKakaotalkTemplates(corpNum, channelId)` | `GetKakaotalkTemplates` | 템플릿 목록 |
| `getKakaotalkTemplateManagementUrl(...)` | `GetKakaotalkTemplateManagementURL` | 템플릿 관리 URL |
| `sendATKakaotalk(...)` | `SendATKakaotalk` | 알림톡 단건 |
| `sendATKakaotalkEx(...)` | `SendATKakaotalkEx` | 알림톡 단건 (버튼) |
| `sendATKakaotalks(...)` | `SendATKakaotalks` | 알림톡 대량 |
| `sendFTKakaotalk(...)` | `SendFTKakaotalk` | 친구톡 텍스트 |
| `sendFTKakaotalks(...)` | `SendFTKakaotalks` | 친구톡 대량 |
| `sendFIKakaotalk(...)` | `SendFIKakaotalk` | 친구톡 이미지 |
| `sendFWKakaotalk(...)` | `SendFWKakaotalk` | 친구톡 와이드 이미지 |
| `getSendKakaotalk(corpNum, sendKey)` | `GetSendKakaotalk` | 전송결과 단건 |
| `getSendKakaotalks(corpNum, sendKeyList)` | `GetSendKakaotalks` | 전송결과 다건 |
| `cancelReservedKakaotalk(corpNum, sendKey)` | `CancelReservedKakaotalk` | 예약 취소 |

### 3.7 SMS — 문자전송 (4개)

| 메서드 | SOAP 메서드 | 설명 |
|--------|-----------|------|
| `sendSMSMessage(...)` | `SendSMSMessage` | SMS 단문 발송 |
| `checkSMSFromNumber(corpNum, fromNumber)` | `CheckSMSFromNumber` | 발신번호 확인 |
| `getSMSFromNumbers(corpNum)` | `GetSMSFromNumbers` | 발신번호 목록 |
| `getSMSSendState(corpNum, sendKey)` | `GetSMSSendState` | 전송 상태 |

### 3.8 메서드 수 비교

| 카테고리 | MNG | API | 구현율 |
|---------|:---:|:---:|:------:|
| CORPSTATE | 3 | 3 | 100% |
| BANKACCOUNT | 13 | 14 | 100%+ |
| CARD | 11 | 11 | 100% |
| TI | 3 | 3 | 100% |
| KAKAOTALK | 15 | 15 | 100% |
| SMS | 4 | 4 | 100% |
| 유틸리티 | 5 | 7 | — |
| **합계** | **54** | **57** | **100%** |

---

## 4. 동기화 서비스

### 4.1 BarobillBankSyncService

은행 거래내역을 바로빌 SOAP에서 조회하여 `barobill_bank_transactions` 테이블에 캐시한다.

```
syncIfNeeded(tenantId, startYmd, endYmd)
  ├─ BarobillMember 조회 → initForMember()
  ├─ getRegisteredAccounts() — SOAP GetBankAccountEx
  ├─ 월별 청크 분할 (splitDateRangeMonthly)
  ├─ 캐시 판단:
  │   ├─ 과거 월: 항상 캐시 (API 호출 안 함)
  │   └─ 현재 월: 10분 이내면 캐시
  ├─ fetchAndCache() — SOAP GetPeriodBankAccountTransLog
  ├─ cacheTransactions() — insertOrIgnore (100건씩 배치)
  └─ updateSyncStatus() — BankSyncStatus 기록
```

### 4.2 BarobillCardSyncService

카드 거래내역을 바로빌 SOAP에서 조회하여 `barobill_card_transactions` 테이블에 캐시한다.

```
syncCardTransactions(tenantId, startYmd, endYmd)
  ├─ BarobillMember 조회 → initForMember()
  ├─ getRegisteredCards() — SOAP GetCardEx2
  ├─ 카드별 루프:
  │   ├─ getPeriodCardLog() — SOAP 호출
  │   └─ cacheTransactions() — insertOrIgnore (100건씩 배치)
  └─ 결과 반환 {synced, cards}
```

### 4.3 HometaxSyncService

API 응답 데이터를 `hometax_invoices` 테이블에 upsert한다.

```
syncInvoices(invoices, tenantId, invoiceType)
  ├─ nts_confirm_num 기준 upsert
  ├─ 기존 레코드: API 필드만 업데이트 (memo/category/is_checked 보존)
  ├─ 신규 레코드: create
  └─ 트랜잭션 래핑 (실패 시 rollback)
```

---

## 5. API 엔드포인트

### 5.1 신규 추가 (11개)

| Method | Path | 용도 |
|--------|------|------|
| `POST` | `/v1/barobill/sync/bank` | 수동 은행 동기화 |
| `POST` | `/v1/barobill/sync/card` | 수동 카드 동기화 |
| `POST` | `/v1/barobill/sync/hometax` | 수동 홈택스 동기화 |
| `GET` | `/v1/barobill/accounts` | 등록계좌 목록 (SOAP 실시간) |
| `GET` | `/v1/barobill/cards` | 등록카드 목록 (SOAP 실시간) |
| `GET` | `/v1/barobill/certificate` | 인증서 상태 (유효성/만료일) |
| `GET` | `/v1/barobill/balance` | 충전잔액 조회 |
| `POST` | `/v1/barobill/members` | 바로빌 회원 등록 (RegistCorp) |
| `PUT` | `/v1/barobill/members` | 바로빌 회원 수정 (UpdateCorpInfo) |
| `GET` | `/v1/barobill/members/status` | 바로빌 회원 상태 (GetCorpState) |

### 5.2 기존 보강 (1개)

| Method | Path | 변경 내용 |
|--------|------|----------|
| `GET` | `/v1/barobill/status` | 실제 계좌/카드 수 표시 (BarobillMember 연동) |

### 5.3 기존 유지 (42개)

은행 13개 + 카드 16개 + 홈택스 13개 — 변경 없음.

---

## 6. 자동 동기화 스케줄러

### 6.1 Job 정의

`app/Jobs/Barobill/SyncBarobillDataJob.php`

```php
// 생성자 파라미터로 동기화 유형 지정
new SyncBarobillDataJob('bank')   // 은행만
new SyncBarobillDataJob('card')   // 카드만
new SyncBarobillDataJob('all')    // 은행+카드
```

### 6.2 스케줄러 등록 (`routes/console.php`)

| 시간 | 유형 | 대상 |
|------|------|------|
| 매일 06:00 | `bank` | 전일 은행 거래내역 |
| 매일 06:30 | `card` | 전일 카드 거래내역 |

### 6.3 대상 조건

`server_mode=production` AND `status=active`인 `barobill_members`만 동기화.

---

## 7. 설정 구조

### 7.1 DB 설정 (`barobill_configs`)

| id | environment | cert_key | corp_num | is_active |
|----|------------|----------|----------|-----------|
| 1 | test | `2DD6C76C-0...` | `6648603713` | true |
| 2 | production | `C0B36577-2...` | `6648603713` | true |

### 7.2 설정 우선순위

```
1. DB (barobill_configs) — BarobillConfig::getActive(isTestMode)
2. .env 폴백 — BAROBILL_CERT_KEY_TEST / BAROBILL_CERT_KEY_PROD
```

### 7.3 모드 결정 흐름

```
BarobillMember.server_mode ('test' | 'production')
  → BarobillSoapService.initForMember(member)
    → switchServerMode(member.isTestMode())
      → initializeConfig() — DB 또는 .env에서 설정 로드
        → SOAP URL 구성 (testws / ws)
```

---

## 8. 현재 테스트 환경 데이터

### 8.1 등록된 바로빌 회원 (2026-03-17 기준)

| id | tenant_id | 회사 | 바로빌 ID | 모드 | 상태 |
|----|-----------|------|----------|------|------|
| 1 | 1 | 테스트기업_wcg5c8 | `test_wcg5c8` | test | active |
| 2 | 1 | (주)코드브릿지엑스 | `cbx0913` | production | active |
| 3 | 290 | (주)주일기업 | `juil5130` | test | active |
| 4 | 289 | (주)경동기업 | `kd5130` | test | active |
| 5 | 287 | 프론트_테스트회사 | `testpro1` | test | active |
| 7 | 288 | 기획_테스트회사 | (없음) | test | pending |

### 8.2 테스트 가능 테넌트

| 테넌트 | 사업자번호 | 바로빌 회원 | 테스트 적합성 |
|--------|----------|-----------|:----------:|
| 290 (주일기업) | 1388166437 | `juil5130` (test) | 즉시 테스트 가능 |
| 289 (경동기업) | 1398700333 | `kd5130` (test) | 즉시 테스트 가능 |
| 291 (미생성) | — | — | 풀 온보딩 테스트용 생성 필요 |
| 292 (데모제조) | 000-00-00000 | 없음 | 더미 사업자번호로 제한적 |

### 8.3 온보딩 테스트 시나리오

**빠른 테스트** (기존 회원 활용):
```bash
# tenant_id=290으로 SOAP 연결 테스트
docker exec sam-api-1 php artisan tinker --execute="
\$soap = app(\App\Services\Barobill\BarobillSoapService::class);
\$member = \App\Models\Barobill\BarobillMember::withoutGlobalScopes()->find(3);
\$soap->initForMember(\$member);
dump(\$soap->checkConfiguration());
dump(\$soap->getCorpState(\$member->biz_no));
"
```

**풀 온보딩 테스트** (신규 테넌트):
```
1. tinker로 tenant_id=291 생성
2. POST /v1/barobill/members → RegistCorp
3. GET /v1/barobill/certificate-url → URL 확인
4. GET /v1/barobill/accounts → 계좌 목록
5. POST /v1/barobill/sync/bank → 동기화 테스트
```

---

## 9. MNG 코드와의 대응 관계

| MNG 파일 | API 파일 | 비고 |
|----------|---------|------|
| `Services/Barobill/BarobillService.php` | `Services/Barobill/BarobillSoapService.php` | 독립 신규 작성, MNG 수정 없음 |
| `Services/Barobill/BarobillBankSyncService.php` | `Services/Barobill/BarobillBankSyncService.php` | 독립 신규 작성 |
| (EcardController 내 카드 동기화) | `Services/Barobill/BarobillCardSyncService.php` | 서비스로 분리 |
| `Services/Barobill/HometaxSyncService.php` | `Services/Barobill/HometaxSyncService.php` | 독립 신규 작성 |
| (MNG에 없음) | `Jobs/Barobill/SyncBarobillDataJob.php` | API 전용 신규 |
| `Controllers/Api/Admin/Barobill/*` | `Controllers/Api/V1/BarobillSyncController.php` | API용 컨트롤러 |

---

## 관련 문서

| 문서 | 설명 |
|------|------|
| [바로빌 연동 시스템](./README.md) | 전체 구조, 모드, 과금, 테이블 |
| [테넌트 온보딩](./tenant-onboarding.md) | 6단계 프로세스 개념 |
| [온보딩 실행 가이드](../../guides/barobill-onboarding-guide.md) | 7단계 실행 절차 + API 예시 |
| [온보딩 실행 가이드 PPT](../../guides/barobill-onboarding-guide.pptx) | 12슬라이드 프레젠테이션 |

---

**최종 업데이트**: 2026-03-17
