feat: [quote] 견적 API Phase 2-3 완료 (Service + Controller Layer)

Phase 2 - Service Layer:
- QuoteService: 견적 CRUD + 상태관리 (확정/전환)
- QuoteNumberService: 견적번호 채번 (KD-{PREFIX}-YYMMDD-SEQ)
- FormulaEvaluatorService: 수식 평가 엔진 (SUM, IF, ROUND 등)
- QuoteCalculationService: 자동산출 (스크린/철재 제품)
- QuoteDocumentService: PDF 생성 및 이메일/카카오 발송

Phase 3 - Controller Layer:
- QuoteController: 16개 엔드포인트
- FormRequest 7개: Index, Store, Update, BulkDelete, Calculate, SendEmail, SendKakao
- QuoteApi.php: Swagger 문서 (12개 스키마, 16개 엔드포인트)
- routes/api.php: 16개 라우트 등록

i18n 키 추가:
- error.php: quote_not_found, formula_* 등
- message.php: quote.* 성공 메시지
This commit is contained in:
2025-12-04 22:03:40 +09:00
parent d164bb4c4a
commit 40ca8b8697
18 changed files with 3264 additions and 3 deletions

View File

@@ -1,5 +1,250 @@
# SAM API 작업 현황
## 2025-12-04 (수) - 견적 API Phase 3: Controller + FormRequest + Routes + Swagger 완료
### 작업 목표
- 견적 API Phase 3 Controller Layer 구현
- 16개 API 엔드포인트 구현 완료
### 생성된 파일
**Controller (1개):**
- `app/Http/Controllers/Api/V1/QuoteController.php`
- 16개 메서드: index, show, store, update, destroy, bulkDestroy, finalize, cancelFinalize, convertToOrder, previewNumber, calculate, calculationSchema, generatePdf, sendEmail, sendKakao, sendHistory
- 4개 Service DI: QuoteService, QuoteNumberService, QuoteCalculationService, QuoteDocumentService
- ApiResponse::handle() 패턴 적용
**FormRequest (7개):**
| 파일 | 설명 |
|------|------|
| `QuoteIndexRequest.php` | 목록 조회 파라미터 검증 |
| `QuoteStoreRequest.php` | 견적 생성 검증 (items 배열 포함) |
| `QuoteUpdateRequest.php` | 견적 수정 검증 |
| `QuoteBulkDeleteRequest.php` | 일괄 삭제 IDs 검증 |
| `QuoteCalculateRequest.php` | 자동산출 입력값 검증 |
| `QuoteSendEmailRequest.php` | 이메일 발송 검증 |
| `QuoteSendKakaoRequest.php` | 카카오 발송 검증 |
**Swagger (1개):**
- `app/Swagger/v1/QuoteApi.php`
- 12개 스키마: Quote, QuoteItem, QuotePagination, QuoteCreateRequest, QuoteUpdateRequest 등
- 16개 엔드포인트 문서화
### API 엔드포인트 (16개)
| Method | Endpoint | 설명 |
|--------|----------|------|
| GET | `/api/v1/quotes` | 견적 목록 (페이지네이션) |
| POST | `/api/v1/quotes` | 견적 생성 |
| GET | `/api/v1/quotes/number/preview` | 견적번호 미리보기 |
| POST | `/api/v1/quotes/calculate` | 자동산출 |
| GET | `/api/v1/quotes/calculate/schema` | 산출 스키마 조회 |
| DELETE | `/api/v1/quotes/bulk` | 일괄 삭제 |
| GET | `/api/v1/quotes/{id}` | 견적 상세 |
| PUT | `/api/v1/quotes/{id}` | 견적 수정 |
| DELETE | `/api/v1/quotes/{id}` | 견적 삭제 |
| POST | `/api/v1/quotes/{id}/finalize` | 확정 |
| POST | `/api/v1/quotes/{id}/cancel-finalize` | 확정 취소 |
| POST | `/api/v1/quotes/{id}/convert` | 주문 전환 |
| GET | `/api/v1/quotes/{id}/pdf` | PDF 생성 |
| POST | `/api/v1/quotes/{id}/send/email` | 이메일 발송 |
| POST | `/api/v1/quotes/{id}/send/kakao` | 카카오 발송 |
| GET | `/api/v1/quotes/{id}/send/history` | 발송 이력 |
### 검증 결과
- PHP 문법 검사: ✅ 9개 파일 통과
- Pint 코드 포맷팅: ✅ 완료
- Swagger 문서 생성: ✅ 완료
- 라우트 등록: ✅ 16개 라우트 확인
### 다음 작업 (Phase 4)
- [ ] 단위 테스트 작성
- [ ] 통합 테스트 작성
- [ ] 마이그레이션 실행 및 실제 데이터 검증
---
## 2025-12-04 (수) - 견적 API Phase 2: Service Layer 구현 완료
### 작업 목표
- 견적 API Phase 2 Service Layer 구현
- 5개 Service 파일 생성 완료
### 생성된 파일
**Service Layer (5개):**
| 파일 | 설명 | 주요 기능 |
|------|------|----------|
| `QuoteService.php` | 견적 CRUD + 상태관리 | index, show, store, update, destroy, bulkDestroy, finalize, cancelFinalize, convertToOrder |
| `QuoteNumberService.php` | 견적번호 채번 | generate, preview, validate, parse, isUnique |
| `FormulaEvaluatorService.php` | 수식 평가 엔진 | validateFormula, evaluate, evaluateMultiple, evaluateRange, evaluateMapping |
| `QuoteCalculationService.php` | 견적 자동산출 | calculate, preview, recalculate, getInputSchema |
| `QuoteDocumentService.php` | 문서 생성/발송 | generatePdf, sendEmail, sendKakao, getSendHistory |
### 견적번호 형식
```
KD-{PREFIX}-{YYMMDD}-{SEQ}
예: KD-SC-251204-01 (스크린), KD-ST-251204-01 (철재)
```
### FormulaEvaluatorService 지원 함수
- 수학: `SUM`, `ROUND`, `CEIL`, `FLOOR`, `ABS`, `MIN`, `MAX`
- 논리: `IF`, `AND`, `OR`, `NOT`
### QuoteCalculationService 입력 스키마
**공통 입력:**
- `W0`: 개구부 폭 (mm)
- `H0`: 개구부 높이 (mm)
- `QTY`: 수량
**스크린 제품 추가:**
- `INSTALL_TYPE`: 설치 유형 (wall/ceiling/floor)
- `MOTOR_TYPE`: 모터 유형 (standard/heavy)
- `CONTROL_TYPE`: 제어 방식 (switch/remote/smart)
- `CHAIN_SIDE`: 체인 위치 (left/right)
**철재 제품 추가:**
- `MATERIAL`: 재질 (ss304/ss316/galvanized)
- `THICKNESS`: 두께 (mm)
- `FINISH`: 표면처리 (hairline/mirror/matte)
- `WELDING`: 용접 방식 (tig/mig/spot)
### i18n 키 추가
**에러 메시지 (error.php):**
- `quote_not_found`, `quote_not_editable`, `quote_not_deletable`
- `quote_not_finalizable`, `quote_not_finalized`, `quote_already_converted`
- `quote_not_convertible`, `quote_email_not_found`, `quote_phone_not_found`
- `formula_empty`, `formula_parentheses_mismatch`, `formula_unsupported_function`, `formula_calculation_error`
**성공 메시지 (message.php):**
- `quote.fetched`, `quote.created`, `quote.updated`, `quote.deleted`
- `quote.bulk_deleted`, `quote.finalized`, `quote.finalize_cancelled`
- `quote.converted`, `quote.calculated`, `quote.pdf_generated`
- `quote_email_sent`, `quote_kakao_sent`
### 검증 결과
- PHP 문법 검사: ✅ 5개 파일 통과
- Pint 코드 포맷팅: ✅ 완료
### 다음 작업 (Phase 3)
- [ ] QuoteController.php 생성
- [ ] FormRequest 생성 (QuoteStoreRequest, QuoteUpdateRequest 등)
- [ ] Swagger 문서 작성 (QuoteApi.php)
- [ ] 라우트 등록
---
## 2025-12-04 (수) - 거래처 API 2차 필드 추가 및 견적 API 계획 업데이트
### 작업 목표
- 거래처 API에 2차 필드 추가 (17개 신규 필드)
- 견적 API 변경사항 분석 및 계획 문서 업데이트
### 거래처 API 2차 필드 추가
**추가된 필드 (7개 섹션, 20개 필드):**
| 섹션 | 필드 | 설명 |
|------|------|------|
| 거래처 유형 | `client_type` | 매입/매출/매입매출 |
| 연락처 | `mobile`, `fax` | 모바일, 팩스 |
| 담당자 | `manager_name`, `manager_tel`, `system_manager` | 담당자 정보 |
| 발주처 설정 | `account_id`, `account_password`, `purchase_payment_day`, `sales_payment_day` | 계정 및 결제일 |
| 약정 세금 | `tax_agreement`, `tax_amount`, `tax_start_date`, `tax_end_date` | 세금 약정 정보 |
| 악성채권 | `bad_debt`, `bad_debt_amount`, `bad_debt_receive_date`, `bad_debt_end_date`, `bad_debt_progress` | 채권 정보 |
| 기타 | `memo` | 메모 |
**수정된 파일:**
- `database/migrations/2025_12_04_205603_add_extended_fields_to_clients_table.php` (NEW)
- `app/Models/Orders/Client.php` - fillable, casts, hidden 업데이트
- `app/Http/Requests/Client/ClientStoreRequest.php` - 검증 규칙 추가
- `app/Http/Requests/Client/ClientUpdateRequest.php` - 검증 규칙 추가
- `app/Services/ClientService.php` - store/update 검증 추가
- `app/Swagger/v1/ClientApi.php` - 3개 스키마 업데이트
### 견적 API 계획 업데이트
**신규 요청 - 문서 발송 API (Section 3.5):**
| Method | Endpoint | 설명 |
|--------|----------|------|
| POST | `/api/v1/quotes/{id}/send/email` | 이메일 발송 |
| POST | `/api/v1/quotes/{id}/send/fax` | 팩스 발송 |
| POST | `/api/v1/quotes/{id}/send/kakao` | 카카오톡 발송 |
**계획 문서 업데이트 내용:**
- Phase 2: `QuoteDocumentService` 추가
- Phase 3: `QuoteSendEmailRequest`, `QuoteSendFaxRequest`, `QuoteSendKakaoRequest` 추가
- Service 5개, FormRequest 8개로 조정
### Git 커밋
```
commit d164bb4
feat: [client] 거래처 API 2차 필드 추가 및 견적 계획 업데이트
```
### 다음 작업
- 견적 API Phase 2: Service Layer 구현
---
## 2025-12-04 (수) - 견적수식 시드 데이터 구현
### 작업 목표
- design/src/components/utils/formulaSampleData.ts의 데이터를 MNG에서 관리할 수 있도록 시드 데이터 구현
- 26개 수식 규칙, 11개 카테고리를 DB에 입력
### 추가된 파일
**Seeder (2개):**
- `database/seeders/QuoteFormulaCategorySeeder.php`
- 11개 카테고리 시드 (OPEN_SIZE, MAKE_SIZE, AREA, WEIGHT, GUIDE_RAIL, CASE, MOTOR, CONTROLLER, EDGE_WING, INSPECTION, PRICE_FORMULA)
- updateOrInsert 패턴으로 멱등성 보장
- `database/seeders/QuoteFormulaSeeder.php`
- 29개 수식 시드 (input 2개, calculation 18개, range 3개, mapping 1개, 단가수식 8개)
- 8개 범위 데이터 (quote_formula_ranges)
- 카테고리 코드 → ID 매핑으로 FK 참조
### 시드 데이터 상세
| 카테고리 | 코드 | 수식 수 | 설명 |
|----------|------|---------|------|
| 오픈사이즈 | OPEN_SIZE | 2 | W0, H0 입력 |
| 제작사이즈 | MAKE_SIZE | 4 | W1/H1 (스크린/철재) |
| 면적 | AREA | 1 | W1 × H1 / 1000000 |
| 중량 | WEIGHT | 2 | 스크린/철재 중량 계산 |
| 가이드레일 | GUIDE_RAIL | 5 | 길이, 자동선택, 설치유형별 수량 |
| 케이스 | CASE | 3 | 사이즈, 자재 자동선택 |
| 모터 | MOTOR | 1 | 중량 기반 자동선택 |
| 제어기 | CONTROLLER | 1 | 유형별 자동선택 |
| 마구리 | EDGE_WING | 1 | 날개 수량 계산 |
| 검사 | INSPECTION | 1 | 검사비 고정 |
| 단가수식 | PRICE_FORMULA | 8 | 품목별 단가 계산 |
### 실행 명령어
```bash
# 순서대로 실행
php artisan db:seed --class=QuoteFormulaCategorySeeder
php artisan db:seed --class=QuoteFormulaSeeder
```
### 검증 결과
- 카테고리: 11개 생성 완료 ✅
- 수식: 29개 생성 완료 ✅
- 범위 데이터: 8개 생성 완료 ✅
### 참조 문서
- `mng/docs/QUOTE_FORMULA_SEED_PLAN.md` - 구현 계획서
- `design/src/components/utils/formulaSampleData.ts` - 소스 데이터
---
## 2025-12-02 (월) - 메뉴 통합관리 시스템 구현 (Phase 1-2)
### 작업 목표