# 재고생산관리 기능 추가 **날짜:** 2026-03-16 **작업자:** Claude Code --- ## 변경 개요 수주 없이 재고 목적으로 생산하는 경우를 관리하는 **재고생산관리** 기능을 추가했다. 기존 `orders` 테이블을 공유하며, `order_type_code = 'STOCK'`으로 일반 수주와 구분한다. ### 설계 원칙 - **내부 오더(Internal Order)** 패턴 — 재고생산도 수주로 취급 - 기존 테이블/API 재사용 — 별도 테이블/엔드포인트 없음 - 하류 시스템(작업지시, 생산, 출하, 품질검사) 변경 없이 동작 --- ## 수정된 파일 ### 커밋 1: `feat: [order] 재고생산관리(STOCK) 타입 추가` | 파일 | 변경 내용 | |------|----------| | `app/Models/Orders/Order.php` | `TYPE_STOCK = 'STOCK'` 상수 추가 | | `app/Http/Requests/Order/StoreOrderRequest.php` | STOCK validation 허용, `production_reason`/`target_stock_qty` 옵션 추가 | | `app/Http/Requests/Order/UpdateOrderRequest.php` | 동일 | | `app/Services/OrderService.php` | STK 채번, stats `order_type` 필터, 매출 생성 스킵 | | `app/Http/Controllers/Api/V1/OrderController.php` | stats에 `order_type` 파라미터 전달 | ### 커밋 2: `feat: [order] 재고생산 생산지시 자동 처리` | 파일 | 변경 내용 | |------|----------| | `app/Services/OrderService.php` | `store()`: STOCK → `site_name='재고생산'` 자동 설정 | | `app/Services/OrderService.php` | `createProductionOrder()`: STOCK 분기 추가 (절곡 자동, project_name, scheduled_date) | | `lang/ko/error.php` | `bending_process_not_found` 에러 메시지 추가 | | `lang/en/error.php` | 동일 (영문) | --- ## 상세 변경 사항 ### 1. Order 모델 — 타입 상수 ```php public const TYPE_ORDER = 'ORDER'; // 수주 public const TYPE_PURCHASE = 'PURCHASE'; // 발주 public const TYPE_STOCK = 'STOCK'; // 재고생산 (신규) ``` ### 2. 채번 규칙 | 타입 | 접두사 | 형식 | 예시 | |------|--------|------|------| | ORDER | `ORD` | `ORD{YYYYMMDD}{NNNN}` | `ORD202603160001` | | STOCK | `STK` | `STK{YYYYMMDD}{NNNN}` | `STK202603160001` | ### 3. store() — STOCK 자동 처리 ```php if ($isStock) { $data['site_name'] = '재고생산'; } ``` ### 4. createProductionOrder() — STOCK 분기 | 항목 | ORDER (기존) | STOCK (신규) | |------|-------------|-------------| | 공정 매칭 | BOM item_id → process_items 매핑 | **절곡 공정 직접 할당** (BOM 스킵) | | project_name | `order.site_name ?? client_name` | `'재고생산'` 고정 | | scheduled_date | `order.delivery_date` | `now()` | | 매출 생성 | `sales_recognition` 정책 적용 | **생성 안 함** | 절곡 공정 조회: ```php $bendingProcess = Process::where('tenant_id', $tenantId) ->where('process_name', '절곡') ->where('is_active', true) ->first(); ``` ### 5. stats() — order_type 필터 ```php public function stats(?string $orderType = null): array ``` `GET /api/v1/orders/stats?order_type=STOCK` 으로 재고생산 전용 통계 조회 가능. ### 6. 매출 생성 스킵 ```php if ($status === Order::STATUS_CONFIRMED && $order->order_type_code !== Order::TYPE_STOCK // STOCK 제외 && $order->shouldCreateSaleOnConfirm()) { ``` --- ## 영향범위 분석 | 영역 | 영향 | 이유 | |------|------|------| | 기존 수주(ORDER) | ❌ 없음 | `$isStock` 조건 분기, else 블록에서 기존 코드 그대로 실행 | | 기존 발주(PURCHASE) | ❌ 없음 | 동일 | | 작업지시(WorkOrder) | ✅ 정상 동작 | `sales_order_id` FK로 연결, 절곡 공정 할당됨 | | 생산/품질검사 | ❌ 없음 | WorkOrder 기반 하류 시스템, Order 타입 무관 | | 출하(Shipment) | ❌ 없음 | WorkOrder 참조, Order.site_name 미사용 | | 캘린더 | ✅ 표시됨 | `project_name='재고생산'`, `scheduled_date=now()` | | 생산지시 목록 | ✅ 표시됨 | `site_name='재고생산'`으로 현장명 표시 | --- ## 버그 수정 (2026-03-17) ### 커밋 3: `fix: [production] 생산지시 생성 시 $isStock 미정의 오류 및 수량 정수 변환` | 파일 | 변경 내용 | |------|----------| | `app/Services/OrderService.php` | `DB::transaction` 클로저 `use`절에 `$isStock` 변수 추가 | | `app/Services/OrderService.php` | `work_order_items.quantity`를 `(int)` 캐스팅하여 정수로 저장 | **원인**: `$isStock`가 line 1242에서 정의되지만, `DB::transaction` 클로저의 `use`절에 포함되지 않아 클로저 내부에서 참조 불가 → 500 에러 발생 ### 커밋 4: `fix: [production] 생산지시 생성 시 $process 미정의 오류 수정` | 파일 | 변경 내용 | |------|----------| | `app/Services/OrderService.php` | `$process = null;` 초기화 추가 (if 블록 밖에서도 참조 가능하도록) | **원인**: `$process`가 `if ($processId)` 블록 안에서만 정의되지만, 블록 밖 line 1420에서 team_id 결정 시 참조 → 공정 없는 품목 처리 시 500 에러 발생 ### 커밋 5 (React): `fix: [stocks] 재고생산 수량을 정수로 표시` | 파일 | 변경 내용 | |------|----------| | `src/components/stocks/actions.ts` | `transformItemApiToFrontend`에서 `Math.floor(Number())` 적용 | | `src/components/stocks/actions.ts` | 금액 필드도 `Number()`로 안전한 형변환 적용 | **원인**: API의 Eloquent `decimal:4` 캐스트가 수량을 `"1.0000"` 문자열로 반환하여 프론트엔드에서 소수점 그대로 표시 --- ## 테스트 체크리스트 - [x] STOCK 수주 생성 → `order_no` STK 접두사 확인 - [x] STOCK 수주 생성 → `site_name='재고생산'` 자동 설정 확인 - [ ] STOCK 수주 확정 → 매출 자동 생성 안 됨 확인 - [x] STOCK 생산지시 생성 → 절곡 공정 자동 선택 확인 - [x] STOCK 생산지시 생성 → `project_name='재고생산'` 확인 - [x] STOCK 생산지시 생성 → `scheduled_date=today` 확인 - [ ] 기존 ORDER 수주 생산지시 → 기존 BOM 매칭 정상 동작 확인 - [ ] 생산지시 목록에서 STOCK 건 표시 확인 - [x] 생산지시 생성 시 `$isStock` 미정의 오류 수정 확인 - [x] 생산지시 생성 시 `$process` 미정의 오류 수정 확인 - [x] `work_order_items.quantity` 정수 저장 확인 - [x] 프론트엔드 수량 정수 표시 확인 --- ## 관련 문서 - [재고생산관리 기능 설명](../../features/sales/stock-production.md) - [재고생산관리 API 명세](../../frontend/api-specs/stock-production-api.md) - [프론트엔드 구현 요청서](../../frontend/requests/stock-production-react-request.md) --- **최종 업데이트**: 2026-03-17