Commit Graph

3063 Commits

Author SHA1 Message Date
hjjeong fa2f232924 주문관리 수주등록 폼 분기 — wace orderRegistFormPopup 1:1 별도 컴포넌트
- 견적요청에서 시작된 행(is_direct_order != 'Y')은 별도 다이얼로그(OrderRegistDialog)
  · 헤더 4개(발주번호/발주일*/견적환종/견적환율)
  · 라인은 contract_item 자동 로드, 추가/삭제 불가
  · 입력은 제품구분 + ORDER_*(수주수량/단가/공급가액/부가세/총액)만
  · 자동계산(수량×단가→공급가액, ×10%→부가세, 공급+부가세→총액)
  · Total 합계 행
- 통합폼은 항상 is_direct_order='Y' 케이스만 노출 — 토글 로직 제거
- list SQL/OrderRow에 is_direct_order 노출 (행 분기 판별용)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 11:12:23 +09:00
hjjeong 12c23d2cb6 주문관리 수주입력 보강: 자동계산 + 행 선택 시 수정 분기 + is_direct_order 따라 폼 모드
- 라인 자동계산 (wace fn_calculateItemAmount / fn_calculateFromSupplyPrice / fn_calculateTotalFromVat 이식)
  · 수량/단가 → 공급가액 = 수량×단가, 부가세 = round(공급가액×0.1), 총액 = 공급가액+부가세
  · 공급가액 직접 → 부가세/총액 재계산
  · 부가세 직접 → 총액만 재계산
  · 총액 직접 → 영향 없음 (수동)
- 수주입력 버튼 분기: selected 없으면 신규(openCreate), 있으면 수정(openEdit). 라벨 자동 토글 ("수주입력" ↔ "수주수정"). 기존 별도 "수정" 버튼 제거.
- 다이얼로그 모드 분기 (is_direct_order):
  · 'Y' (수주통합등록/수정): 라인 13컬럼 + ORDER_* 5개 + Total 합계 행
  · 'N' (견적관리에서 온 견적단계 행): 라인 8컬럼 + ORDER_* 5개·Total 숨김 (견적요청수정 폼)
- openEdit에서 product / return_reason / master_part_no/name fallback 추가

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:52:47 +09:00
hjjeong 0a97f2ec38 S/N 관리·연속번호생성 Dialog 모두 onInteractOutside 차단 (자식 Dialog 닫힘 시 부모 도미노 차단 완성)
이전 커밋에서 메인 등록 Dialog에만 onInteractOutside 추가 — 자식(S/N)·손자(연속번호) Dialog가 닫힐 때 이벤트가 메인까지 도미노로 전파되며 여전히 메인이 닫혔음.

해결: nested Dialog 4개(견적/주문 각각 S/N + 연속번호) 모두에 onInteractOutside={(e) => e.preventDefault()} 추가.
사용자는 X / 취소 / 확인 / 생성 버튼으로만 명시적으로 각 Dialog 닫음.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:39:49 +09:00
hjjeong 447090faca 견적/주문 등록 다이얼로그: 자식 S/N·연속번호 Dialog 닫힐 때 부모 Dialog까지 닫히는 현상 차단
Radix Dialog 알려진 이슈 — nested Dialog 닫힐 때 PointerDown 이벤트가 부모로 전파되어 outside click으로 인식, 부모 Dialog도 함께 닫힘.

수정:
  <DialogContent onInteractOutside={(e) => e.preventDefault()}>
  → 외부 클릭으로 부모 닫힘 차단. 사용자는 X / 취소 / 저장 버튼으로만 닫음.
  ESC는 그대로 — Radix focus stack이 자식만 먼저 닫음.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:35:41 +09:00
hjjeong ae5ef8f7e5 주문서 수주통합등록 다이얼로그 wace G2 1:1 재작성
기존 RPS 폼이 wace estimateAndOrderRegistFormPopup과 크게 어긋남(헤더 항목 잘못 배치 + 라인 누락). 통째 재작성.

수주통합 기본정보 — wace 헤더 9개 정확 일치:
  영업번호(자동채번) / 주문유형* / 국내해외* / 고객사* / 유무상* / 접수일* / 견적환종 / 견적환율 / 발주번호 / 발주일*
  (이전 RPS의 요청납기/통화/수주상태/담당자(PM ID)/출하방법/고객사요청사항 헤더 배치 폐지 — wace 통합폼에 없음)

품목정보 — wace 라인 13컬럼 + Total 합계 행:
  No / 제품구분* / 품번* / 품명* / S/N / 요청납기 / 고객요청사항 / 반납사유 / 수주수량* / 수주단가 / 수주공급가액 / 수주부가세 / 수주총액 / 삭제
  (이전 누락: 제품구분 / S/N / 요청납기 / 고객요청사항 / 반납사유)

추가 컴포넌트:
- 품번/품명: PartSelect (part_mng 8,176건 검색 + 자동 매핑)
- 제품구분/반납사유: CommCodeSelect (0000001 / 0001810)
- S/N: 별도 다이얼로그(테이블 + 연속번호생성) — wace fn_openItemSnPopup / fn_openItemSequentialSnPopup 1:1
- 합계: useMemo로 라인 수량/공급가액/부가세/총액 실시간 집계

EMPTY_ITEM 라인 기본값에 product/serials/due_date/return_reason/customer_request 추가.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:24:25 +09:00
hjjeong 7c03907000 PR-B G2: 주문관리 수주입력 = 직접등록 통합폼 (is_direct_order='Y' + order_date + approval_required)
wace 패턴(estimateAndOrderRegistFormPopup + saveEstimateAndOrderInfo) 이식.
운영 데이터 90건 중 74건이 is_direct_order='Y' — 주문 신규 등록의 기본 흐름.

변경:
- 백엔드 OrderBody: order_date / approval_required / is_direct_order 신규 (contract_date 폐지, 운영 컬럼명 일치)
- create()/update() INSERT·UPDATE에 위 3개 컬럼 추가. is_direct_order 기본값 'Y'
- 프론트 OrderBody 타입 동기화. openCreate 시 order_date=today + is_direct_order='Y' 자동
- 폼 다이얼로그 "발주일" 입력을 order_date 바인딩 (잘못 contract_date 바인딩 정정)

자동 검증 (BEGIN/ROLLBACK):
- is_direct_order='Y' INSERT, order_date 저장, ORDER_* 라인 컬럼 정상
- 견적관리 그리드 노출 차단(IS_DIRECT_ORDER!='Y' 필터), 주문관리 그리드 노출 확인

docs/migration/sales/05-direct-order-verify.md

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:17:04 +09:00
hjjeong 86e3aef6f7 영업 4개 메뉴 그리드: wace JSP 주석 처리된 비활성 컬럼들 정정 (V1 보강 잘못 활성화 되돌림)
원인: wace JSP의 var columns 끝에 있는 /* 주석처리된 컬럼 */ 블록은 비활성 보존 영역(메모리 feedback_wace_jsp_columns)인데, V1 보강 커밋에서 추측으로 활성화함. 운영 화면에 노출되지 않는 컬럼이므로 원본대로 주석으로 되돌림.

비활성으로 복귀한 컬럼:
- 견적관리(estimateList_new.jsp 494~502): 제품구분 / 국내해외 / 반납사유
- 주문관리(orderMgmtList.jsp 429~434): 제품구분 / 국내해외 / 접수일
- 판매관리(salesMgmtList.jsp 503~519): 제품구분 / 국내해외 / 접수일 / 고객사요청사항 / 주문서첨부 / 출하방법 / 담당자 / 인도조건
- 매출관리(revenueMgmtList.jsp 615~632): 접수일 / 유무상 / 요청납기 / 고객사요청사항 / 수주상태 / 주문서첨부 / 출하방법 / 담당자 / 인도조건

코드는 주석 블록으로 남겨두어 필요시 활성화 가능. 백엔드 SQL은 그대로 두어 다른 메뉴에서 재사용 가능.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:09:09 +09:00
hjjeong 293339724c 영업 4개 메뉴 그리드 컬럼 너비 보강 (날짜·발주번호·프로젝트번호 잘림 해소)
YYYY-MM-DD 날짜 10자가 잘리던 컬럼 + 발주번호(10~13자 PO) + 프로젝트번호(한글 포함) 너비 상향.

- 견적관리: 영업번호 110→125, 접수일 100→115, 요청납기 110→160
- 주문관리: 영업번호 120→125
- 판매관리: 프로젝트번호 140→170, 발주일 100→115, 발주번호 110→140, 요청납기/출하일/접수일 100/110→115
- 매출관리: 프로젝트번호 140→170, 발주일/출하일 100→115, 발주번호 110→140, 접수일/요청납기 100/110→115

(개별 사용자 환경에서는 컬럼 드래그 리사이저 + localStorage로 추가 미세조정 가능)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 10:04:23 +09:00
hjjeong d23b305990 매출관리 그리드 V1 컬럼 9개 보강 + getRevenueList SQL JOIN 확장 + wace 1:1 검증
- getRevenueList SQL: contract_item / user_info / comm_code(CC_RES) / attach_file_info LATERAL 4개 JOIN 추가. receipt_date / payment_type / request_date / customer_request / order_status_name / manager_name / incoterms / cu01_cnt SELECT 보강
- RevenueListRow 타입: 9개 신규 필드 보강
- GRID_COLUMNS 9개 추가: 접수일/유무상/요청납기/고객사요청사항/수주상태/주문서첨부/출하방법/담당자/인도조건 (wace 35/35 일치)
- docs/migration/sales/04-revenue-verify.md, scripts/verify-revenue.sql

영업 4개 메뉴 (견적·주문·판매·매출) 모두 구조적 검증 1차 종결.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 09:42:21 +09:00
hjjeong a0f6e0fa26 판매관리 그리드 V1 컬럼 8개 보강 + cu01_cnt 실데이터 + wace 1:1 검증 문서·자동 검증 SQL
- getList SQL: attach_file_info LATERAL JOIN으로 cu01_cnt(주문서첨부) 실데이터 (contract_mgmt.objid 기반, doc_type IN FTC_ORDER/ORDER)
- SaleListRow 타입: product_type_name/nation_name/receipt_date/customer_request/manager_name/payment_type_name/cu01_cnt 보강
- GRID_COLUMNS 8개 추가: 제품구분/국내해외/접수일/고객사요청사항/주문서첨부/출하방법/담당자/인도조건 (wace 36/36 일치)
- docs/migration/sales/03-sale-verify.md: wace ↔ RPS 매핑 / 갭 처리
- scripts/verify-sale.sql: BEGIN/ROLLBACK 2개 시나리오 (그리드 V1 / 판매상태 wace 로직)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 09:38:57 +09:00
hjjeong 13b4efd2fe 주문관리 그리드 V1 컬럼 보강(제품구분·국내해외·접수일) + wace 1:1 검증 문서·자동 검증 SQL
- getList SQL: 라인 집계에 product_summary 추가, PRODUCT_NAME을 COALESCE(line, header)로 변경 (운영 contract_mgmt.product NULL 패턴 대응)
- GRID_COLUMNS 3개 추가: 제품구분/국내해외/접수일 (wace 27/27 일치)
- OrderRow 타입: product_name / area_name 보강
- searchForm.search_partName 키 추가(초기화 포함, UI 이미 PartSelect mode=partName 존재)
- docs/migration/sales/02-order-verify.md: wace ↔ RPS 항목 매핑 / 운영 데이터 / 갭 처리 결과
- scripts/verify-order.sql: BEGIN/ROLLBACK 4개 시나리오 (그리드 V1 / G1 / 수주취소 / 채번) 자동 검증

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 09:35:11 +09:00
hjjeong 12ea68616d 견적관리 그리드 V1 컬럼 보강(제품구분·국내해외·반납사유) + wace 1:1 검증 문서·자동 검증 SQL
- getList SQL: 라인 집계에 product_summary(=PRODUCT_NAME, contract_item.product distinct join) / return_reason_summary 추가. wace는 헤더 product 폐지·라인으로 이동(운영 90건 contract_mgmt.product NULL) → 라인 집계로 그리드 표시
- GRID_COLUMNS 3개 추가: 제품구분 / 국내해외 / 반납사유
- searchForm.search_partName 필드 추가(초기화 포함). 검색 폼 UI는 PartSelect mode=partName 이미 존재
- docs/migration/sales/01-estimate-verify.md: wace ↔ RPS 항목 매핑 / 운영 데이터 코드 체계 / 갭 우선순위
- scripts/verify-estimate.sql: BEGIN/ROLLBACK 5개 시나리오 (등록·수정·G1·수주취소·그리드) 자동 검증

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 09:29:43 +09:00
hjjeong 7cbf938345 Merge pull request 'hjjeong' (#4) from hjjeong into main
Reviewed-on: https://g.wace.me/chpark/vexplor_rps/pulls/4
2026-05-09 07:55:51 +00:00
hjjeong 66e2a63dfa 영업관리 G1 수주확정→프로젝트 자동생성 + 견적요청등록 wace 1:1 이식
- G1: salesOrderMgmtService.updateStatus 트랜잭션화 + project_mgmt 자동생성 (project_no 채번/Machine 분기/contract_item 라인별 INSERT)
- 수주확정 다이얼로그(상태 select 팝업) + 수주취소 다이얼로그(라인별 cancel_qty)·POST /sales/order-mgmt/:id/cancel-qty 신설
- 견적요청등록 폼: estimate_template 분리, 헤더 8(주문유형/국내해외/고객사/유무상/접수일/견적환종/견적환율/결재여부) + 라인 8(제품구분/품번/품명/S/N/견적수량/요청납기/반납사유/고객요청사항) wace 운영 화면과 1:1
- S/N 관리 다이얼로그(테이블+연속번호생성), PartSelect/CommCodeSelect/CustomerSelect 셀렉트박스 + ✕(선택해제), 수주확정된 행 라인 추가/삭제 차단
- DataGrid 체크박스 모드 (영업번호 No → 체크박스, 행 어디 클릭이나 단일 선택)
- 식별자 정합성: contract_mgmt.customer_objid를 customer_mng.customer_code 기반(C_xxxx)으로 통일, contract_no 채번 {YY}C-{NNNN} 운영 패턴 일치, contract_item.quantity ::integer 캐스트

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-09 16:48:25 +09:00
chpark 575098698c 배치 편집 conditional 매핑 평가 필드 UX 개선
- 평가 필드 미선택 시 select 에 빨간 테두리 + ring 강조 (한눈에 누락 식별)
- 라벨에 * 필수 마크 + placeholder 를 '조건을 평가할 API 필드 선택 (필수)' 로 변경
- 안내 텍스트 추가: 'status 컬럼에 enrlFg 의 J01→active 변환 시 평가 필드=enrlFg' 예시
- 저장된 apiField 가 fromApiFields 옵션에 없을 때 동적으로 (저장값) 라벨로 추가
  → 응답 미리보기 안 한 편집 모드에서도 기존 값 보존되어 그대로 저장 가능
- cn 유틸 import 추가 (조건부 클래스 적용 시 ReferenceError 방지)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 18:24:12 +09:00
chpark 4007042311 ECR · 고객 CS · 결재 시스템 + Amaranth 전자결재 RestAPI 연계 + wace_plm 데이터 import
[ECR(Engineering Change Request) 관리]
- ecr_mng / product_mgmt / part_mng 테이블 + seq_ecr_no 시퀀스
- 설변요청 코드(0000090) 자식 코드 시드 (설계오류/품질개선/원가절감/고객요청/법규대응/부품단종)
- API: 목록/상세/등록·수정(merge)/조치완료/삭제 + 옵션(작성자/제품/부품/공통코드)
- 화면: 필터바, 그리드, 등록·수정 모달, 상세 모달, 조치완료 모달

[고객 CS 관리]
- customer_cs_mng 테이블 (기존 customer_mng 거래처 마스터와 충돌 회피)
- 공통코드 5종 카테고리(0000200~0000204) 자동 시드: 관리유형/제품구분/담당자/조치유형/CS상태
- API: 목록/상세/등록·수정/삭제/대시보드(요약·상태별·관리유형별·제품구분별)
- 화면: 요약 카드 4종, 10종 필터바, 14컬럼 그리드, 등록·수정·상세 모달

[결재(APPROVAL) 시스템 — wace_plm ApprovalService 포팅]
- approval / route / inboxtask / approval_target / approval_kind / amaranth_approval 6개 테이블
- 라이프사이클: 상신(startApproval) → 결재함(listInbox) → 승인/반려(approveTask/rejectTask)
  → 다음 결재자 ready 자동 전달, 마지막이면 route+approval+target 일괄 complete
- target_type 별 도메인 status 동기화 훅 (ECR_MNG/CUSTOMER_MNG)
- API: /api/wace-approval/{inbox,start,inbox/:id/approve|reject,by-target,:id,:id/amaranth-link}

[Amaranth(Wehago) 전자결재 RestAPI 연계]
- 외부 커넥션 'Amaranth - 결재' 자동 시드 (auth_config: callerName/accessToken/hashKey/groupSeq/aesKey)
- amaranthApprovalClient: 자바 AmaranthApprovalApiClient 1:1 포팅
  HMAC-SHA256 wehago-sign / AES-128-CBC empSeq 암호화 / HTTPS / JSON 파싱
- 6개 endpoint: 인증토큰/결재함/문서목록/문서상세/SSO URL/문서상신
- 하드코딩 0건 — DB 외부 커넥션의 인증 정보를 매 호출 시 로드
- 통신 검증 완료 (dummy empSeq 로 응답 정상 수신)
- 프록시 라우트 /api/amaranth-approval/{box,docs,docs/:id,sso,submit,auth-token}

[wace_plm 데이터 import]
- WacePlmDataImportService: source PG 클라이언트 → 우리 DB ON CONFLICT DO NOTHING idempotent
- 환경변수 WACE_PLM_DB_* 만 읽음 (운영 비번 코드 0건, 미설정 시 명시적 에러)
- /api/wace-import/{all,ecr,cs,masters,approval} (SUPER_ADMIN 전용)

[Bugfix]
- 배치 편집 conditional 매핑 silent drop 방지 — 평가 필드/규칙 누락 시
  어느 컬럼이 어떤 이유로 빠졌는지 toast 로 명시 + 저장 차단
- 시드 topup 강화 — extra_auth_config(aesKey 등) 누락된 기존 레코드 자동 보강

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 17:01:56 +09:00
hjjeong 10e9996249 DataGrid 컬럼 너비 마우스 드래그 리사이저 + localStorage 영구 저장
- 헤더 우측 6px 영역 드래그 핸들 (col-resize 커서 + hover 강조)
- mousedown→document mousemove/mouseup으로 너비 계산 (최소 40px)
- columnWidths state로 inline width 적용 (Tailwind w-[Xpx]는 fallback)
- gridId prop이 있으면 localStorage에 영구 저장 → 새로고침 후 유지
- 컬럼 순서 드래그(@dnd-kit)와 충돌 안 하도록 핸들 영역 분리

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:53:08 +09:00
hjjeong 2d9f30ebab 영업관리 첨부파일 모달·주문서 뷰 + DataGrid frozen 컬럼
- 공통 AttachmentDialog 컴포넌트 신설 (목록/업로드/다운로드/삭제, doc_type 단일·배열 지원)
- 견적 add_est_cnt(클립) → AttachmentDialog (estimate02)
- 주문 cu01_cnt(클립) → AttachmentDialog (FTC_ORDER,ORDER), has_order_data(폴더) → OrderFormViewDialog
- OrderFormViewDialog 신설 — wace orderFormView 한국 표준 주문서 양식 + 인쇄
- 백엔드 fileController.getFileList docType 콤마 멀티값 지원, salesOrderMgmt.getOrderFormView API 추가
- DataGrid 확장: column.onClick / frozen prop / table-fixed / sticky-left + selected·hover 일관 처리
- 4개 메뉴 첫 컬럼 frozen 적용 (영업번호/프로젝트번호)
- 주문서관리 발주일·발주번호·요청납기 컬럼 너비 확장

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:48:13 +09:00
hjjeong 489fa50d11 영업관리 4개 메뉴 검색폼 wace 일치 + 공통 UX(초기화·date input) 정비
- 검색 폼 정합성: wace JSP `<!-- 주석처리된 검색필터 -->` 블록까지 잘못 이식했던 부분 정정
  - 견적: 11→7개 (제품구분/국내해외/유무상/요청납기 제거)
  - 주문: 13→9개 (제품구분/국내해외/유무상/견적환종 제거)
  - 매출: 10→11개 (출하지시상태 제거 + 제품구분·국내/해외 추가, JSP 순서로 재배치)
  - 판매: 변경 없음 (원본 그대로 일치)
- 매출 백엔드: SaleListFilter에 productType/nation 추가, getRevenueList에 partObjId/serialNo/orderDate/productType/nation 5개 필터 처리
- 공통 UX
  - 초기화 버튼을 4개 메뉴 동일하게 통일 (variant=ghost, 버튼 영역 끝)
  - <Input type="date">는 빈 값 placeholder 숨김 + 캘린더 아이콘 숨김 + 영역 클릭으로 picker 자동(showPicker)
- 신규 공통 컴포넌트: CommCodeSelect/CustomerSelect/CustomerSearchDialog/PartSelect/ItemSearchDialog + backend salesCommonRoutes
- 문서: 01/02/04 검색 폼 표를 활성/비활성 분리 형식으로 정정, README에 8. 공통 UX 규칙 섹션 신설

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 10:42:16 +09:00
chpark 4c3ea194a0 권한 그룹 코드 자동 생성 + 대시보드 API URL 환경변수 우선
- RoleFormModal: 권한 코드 입력 필드 제거. 생성 시 ROLE_<base36 timestamp>
  형태로 자동 부여 (시스템 내부 키, UI 비노출). 수정 모드에서도
  authCode 는 기존 값 유지하고 입력 받지 않음.
- dashboard.ts getApiBaseUrl: NEXT_PUBLIC_API_URL 환경변수가 있으면 우선 사용.
  fallback 포트를 8080 → 8090 (compose 외부 노출 포트)으로 정정해
  '데이터를 불러올 수 없습니다 / Failed to fetch' 해결.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 09:07:40 +09:00
chpark 442f4dc115 Merge backup/ui-compact-e9d6a701 (관리자 화면 컴팩트 리디자인 + Docker 프로젝트 분리) 2026-05-07 19:33:47 +09:00
chpark e9d6a701bb 관리자 화면 컴팩트 리디자인 + Docker 프로젝트 분리
- 테이블 타입 관리: h-screen → h-full(min-h-0) 로 탭 영역에 정확히 맞춤,
  사이드바·헤더·카드 폰트/패딩 톤다운, 헤더 입력칸 grid 레이아웃으로 빈 공간 메움
- ColumnGrid: 행 높이 56px → 36px, 한글라벨/영문명 분리 표시,
  PK/NN/IDX/UQ 한 줄 nowrap 고정폭, 그룹 헤더 sticky, 액션 버튼 hover 노출
- 메뉴 관리: min-h-screen → h-full(min-h-0) overflow-hidden, 헤더 flex-shrink-0,
  메인 컨텐츠 flex-1 로 탭 안에서 정확한 height
- MenuTable: max-h-[calc(100vh-350px)] 절대값 제거, flex-1 min-h-0 overflow-auto 로
  부모 컨테이너 따라 내부 스크롤
- docker-compose: name=vexplor_rps 추가 — Docker Desktop 에서
  pipeline 등 다른 프로젝트와 분리되어 한 그룹으로 깔끔하게 표시

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 19:30:22 +09:00
hjjeong 93186efe6a 영업관리 견적 placeholder 3종 실구현 + 폴더/클립 아이콘
- 추가견적: attach_file_info doc_type='estimate02' COUNT 집계 (wace 패턴)
- 메일발송: mail_log INSERT API + 다이얼로그 (POST /sales/estimate/mail)
- 결재상태: contract_mgmt.approval_required='N' → '결재불필요' 표시
  (vexplor_rps에 amaranth_approval 미도입 — 결재 모듈 통합은 차후)
- DataGrid renderType 'folder'/'clip' 신설 (lucide Folder/Paperclip)
- 견적현황·추가견적 컬럼이 wace 원본 그대로 파란/회색 아이콘 표시

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 17:53:48 +09:00
hjjeong 06ced6a863 공통코드 관리 화면 wace comm_code 단일 테이블로 전환
vexplor 로코드툴의 code_category/code_info 2-테이블 구조 대신 wace_plm
원본 comm_code(847건) 위에서 직접 동작하도록 백엔드 service 전면 재작성.
영업관리 등 이미 comm_code에 의존 중인 화면들과 데이터 소스 일치.

- backend service: comm_code 단일 테이블 기반(top-level=parent_code_id 빈값)
  으로 재작성. 다단계 계층은 재귀 CTE로 depth/parent_code_value 산출.
  단일 테넌시라 company_code/menu_objid 필터링은 시그니처만 유지하고 무시
- comm_code에 sort_order INT 컬럼 추가(드래그 정렬 유지) — DB 마이그레이션
- frontend schema: 영문명/설명을 optional로 완화(wace 컬럼 부재)
- 카테고리/코드 폼 모달에서 영문명·설명 입력 필드 제거
- 패널 레이아웃을 화면 높이에 고정 + 좌우 패널 자체 스크롤로 분리

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 16:58:02 +09:00
chpark 223cf55f5c 메신저 사용자 검색 undefined 가드
useCompanyUsers 응답 중 user_name 이 비어있는 레거시 row 가 있을 때
toLowerCase 호출에서 발생하던 Runtime TypeError 방지.

- NewRoomModal: userName/deptName ?? '' 으로 가드 후 includes
- MessageInput: 멘션 자동완성 필터에서 userName ?? '' 가드

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 16:51:28 +09:00
hjjeong 4175ae77c1 영업관리 wace 컬럼 정합성 강화 + project_mgmt 도입
- project_mgmt 테이블 신규(75컬럼/89건) — wace 운영 동일 schema 추출. 판매·매출관리 메인 테이블
- 판매·매출 SQL을 contract_item 기반 → project_mgmt 메인 + sales_registration LEFT JOIN으로 전면 재작성
  * 요청납기 COALESCE(CI.due_date, T.due_date, CM.due_date) 패턴
  * 환종/serial_no는 sales_registration 우선, contract_item_serial 집계 fallback
  * 판매상태 wace 로직 한글 라벨(미판매/완판/분할판매) 동적 계산
  * 매출관리는 shippingDateRequired EXISTS 필터로 출하 등록된 프로젝트만 표시
- 주문서: order_date 매핑 CONTRACT_DATE → ORDER_DATE 정정, 원화총액·고객사요청사항 SQL 추가
- 견적/주문/판매 page.tsx에서 wace 블록 주석 컬럼 제거(제품구분/국내·해외/접수일/반납사유 등 14개)
- 환종 raw 코드 → contract_currency_name 한글명 바인딩으로 정정

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 16:50:45 +09:00
hjjeong 73bd4f2ba7 권한 그룹 회사 필터 제거(COMPANY_16 단독) + 메신저 사용자명 옵셔널 체이닝
- rolesList/RoleFormModal/[id] 페이지에서 회사 선택 필터·라벨·SUPER_ADMIN 회사 컬럼 제거
- MessageInput/NewRoomModal에서 user.userName/deptName.toLowerCase 호출 시 옵셔널 체이닝 적용으로 null 사용자 방어

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 15:39:13 +09:00
hjjeong 1760045634 영업관리 4개 메뉴(견적/주문/판매/매출) 1차 이식 + 마스터 매핑
- wace_plm contract_mgmt/contract_item/contract_item_serial/contract_mgmt_option/estimate_template/estimate_template_item/mail_log/sales_registration/shipment_log 9개 테이블 DDL을 vexplor_rps에 적재, 운영 데이터 복사
- 거래처: Wehago/Amaranth ERP api16S11 INBOUND 동기화 결과(customer_code) 기준 LEFT JOIN으로 변경, 25/25 매칭
- 품목: wace part_mng 8,179건을 item_info(varchar id)에 wace objid 그대로 INSERT, contract_item 72/72 매칭
- 공통코드: wace comm_code 847건 복제 + backend SQL에 5종 LEFT JOIN
- DataGrid에 formatMoney(천단위콤마+소수점2자리) / formatNumber 자동 우측정렬 분리
- adminService.getUserMenuList company_code 분기 제거(RPS 단독), useMenu.buildMenuTree root 식별 보강

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 15:39:03 +09:00
hjjeong c123fd01ff 권한관리 화면 4분할 레이아웃 안정화 + 메뉴 권한 토글 race condition 가드 + 토큰 무효화 본인 제외
화면 (frontend/app/(main)/admin/userMng/userAuthList/page.tsx):
- 4분할 그리드를 inline flex 레이아웃으로 강제 (Tailwind v4 arbitrary value 파싱 이슈 우회)
- 권한있는/없는 직원 리스트 height 폭주 수정 (flex-1 + height 충돌 → 명시적 flex-basis)
- 직원 항목을 가로 배치(이름·부서)로 변경해 한 화면 표시 인원 증가
- 메뉴 트리 영역 자체 스크롤 + sticky thead 적용, 페이지 전체 스크롤 제거
- 빠른 연속 클릭 시 같은 메뉴-필드 토글이 백엔드 SELECT→UPDATE race로 충돌하던 문제를 프론트 inFlight 가드로 차단

API/인프라:
- 단건 메뉴 권한 토글 엔드포인트 신설: PATCH /roles/:id/menu-permissions/:menuId
- RoleService.upsertSingleMenuPermission 추가 (변경된 yn 필드만 머지하는 멱등 UPSERT)
- frontend/lib/api/role.ts: toggleMenuPermission · getWorkspace 함수 추가 (워크스페이스 통합 로드)

보안:
- 권한 변경 시 그룹 멤버 토큰 무효화 로직에서 작업자 본인을 제외 (자기 자신 로그아웃 방지)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 14:59:20 +09:00
chpark 97b333dd2e Amaranth(Wehago) ERP REST API 연계 + 배치 시스템 강화
부팅 시 자동 시드:
- 외부 REST API 연결 6종 (부서/사원/거래처/창고/계정과목/Wehago 사용자)
- 매칭 배치 6개 + Wehago HMAC-SHA256 서명 자동 부착 (erpApiClient/erpPresetSeedService/erpBatchSeedService)
- 동기화 대상 테이블/컬럼 보장 idempotent 마이그레이션 (erpTableMigration)

배치 기능 확장:
- 조건부 매핑 (mapping_type='conditional') — when/then/default 규칙으로 값 변환 (예: enrlFg=J01→active)
- 행 단위 제외 필터 (row_filter_config) — 특정 API 필드 값 가진 행 동기화 제외 (예: loginId=wace 통합 ERP 계정 제외)
- save_mode/conflict_key 기반 UPSERT, data_array_path 응답 배열 추출

UI 정비:
- 배치/플로우/메일/REST API 목록에 페이징 + FullHD 컴팩트 레이아웃
- 배치 편집 화면 한 화면 풀 활용 — TO 패널 가로 그리드, FROM 패널 등록 연결 한 줄 요약, 응답/JSON/파라미터 details 접힘
- ResponsiveDataView/AdminPageRenderer 쿼리 파라미터(?edit=N) 파싱

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 09:48:28 +09:00
chpark 36e232ba00 사이드바 메뉴 펼침/접힘 무한 루프 수정 + 사용자 메뉴 데이터/아이콘 정비
- AppLayout.tsx: 활성 탭 부모 자동 펼치기 useEffect의 의존성에서 expandedMenus를 제거.
  collapse 직후 effect가 재실행되며 강제 expand가 일어나 펼침/접힘이 토글되지 않던 문제 해결.
  이제 activeTab 변경 시에만 부모 메뉴 자동 펼침, 사용자 토글은 안정적으로 유지됨.
- 사용자 메뉴 데이터(DB) 재구성: waceplm 9개 화면 캡처와 1:1 매칭되는 46개 메뉴(루트 사용자 + 10 카테고리 + 35 리프) 재삽입,
  URL을 `.do` 레거시 → `/COMPANY_16/<카테고리>/<리프>` React 라우트로 통일.
- 메뉴 아이콘 매핑: 영업/프로젝트/개발/구매/구매요청/자재/생산/품질/CS/ECR 카테고리 + 35개 리프 각각에
  업무 성격에 맞는 lucide-react 아이콘(TrendingUp/FolderKanban/Wrench/ShoppingCart/Send/Boxes/Factory/ShieldCheck 등) 부여.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 14:34:36 +09:00
chpark 9a8196a395 RPS 브랜딩 · COMPANY_16 단독 운영 · Pipeline 디자인 채용
주요 변경:
- 회사 라우트 정리: COMPANY_7/8/9/10/29/30 6개 폴더 삭제, COMPANY_16(하이큐마그)만 유지
  - 모듈 수 17,470 → 16,121, /main 컴파일 시간 110s → 53s
- 브랜딩: VEXPLOR → RPS (로고/파비콘/타이틀/메타데이터/푸터 회사정보 전부 교체)
- 로그인 페이지 fito 스타일 리디자인 (다크 그라디언트 + 글래스 카드 + 격자 배경 + 하단 푸터)
- AppLayout/TabBar/ThemeToggle/ThemeProvider/Logo Pipeline 디자인 채용
  - 6색 컬러 테마 시스템 (blue/teal/green/purple/red/dark) + 좌→우 커튼 전환 애니메이션
  - 우상단 모드 전환 알약 버튼 (관리자만 노출)
  - 시안톤 탭 + Teal 활성 탭, 130px 컴팩트 너비
- 도커 포트 충돌 회피: 백엔드 8080→8090, 프론트 9771→9781, 컨테이너명 rps_backend/rps-front
- DB: vexplor_rps 신규 생성 후 vexplor_dev 데이터 이관, DATABASE_URL 변경
- useAuth: SUPER_ADMIN userType도 isAdmin으로 인정

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 10:36:21 +09:00
kjs 5dfae5e6b6 Refactor analytics report data retrieval and enhance equipment report logic
- Updated the `getQualityReportData` function to improve item name retrieval logic by using `NULLIF` for better handling of empty values.
- Refactored the `getEquipmentReportData` function to include company and date filters for equipment statistics, ensuring accurate data aggregation.
- Enhanced the SQL queries for both quality and equipment reports to utilize lateral joins and improve performance.
- Improved loading states in frontend components for inspection records and inspection results across multiple companies.

This refactor enhances data accuracy and user experience in the analytics module.
2026-04-28 20:20:10 +09:00
kjs 310f644508 Implement item inspection information feature with server-side pagination
- Added a new controller for item inspection information to handle grouped data retrieval with pagination.
- Created routes for accessing item inspection data, specifically for grouped item codes.
- Updated frontend components to support server-side pagination, including total count display and page navigation.
- Enhanced the item inspection info page to utilize the new API for fetching data, ensuring a smooth user experience.

This implementation improves the management of item inspection data and enhances usability in the quality module.
2026-04-28 18:42:25 +09:00
kjs 0b7c967f56 Refactor analytics report data retrieval and improve logistics info page loading logic
- Updated the analytics report controller to correctly join work_order_process and work_order_process_result for accurate production data retrieval.
- Enhanced the logistics info page to load all tabs on mount for immediate count accuracy, while ensuring only the active tab is reloaded on subsequent changes to prevent race conditions.

This refactor improves data accuracy and user experience in the logistics module.
2026-04-28 18:15:22 +09:00
kjs bf8d99ccf5 Implement KPI daily production feature
- Added a new KPI controller to handle daily production data retrieval.
- Created routes for accessing KPI data, specifically for daily production.
- Developed frontend components for displaying daily production metrics, including charts and summary cards.
- Implemented data fetching logic with date range filtering for production data.
- Ensured proper loading states and error handling in the UI.

This feature is part of TASK:ERP-022.
2026-04-28 16:14:27 +09:00
kjs 4afb0f5ca4 Implement server-side pagination for order summaries, plans, and shipping orders
- Added pagination parameters (page and size) to the getOrderSummary and getPlans functions in the productionController.
- Updated the getList function in shippingOrderController and shippingPlanController to support server-side pagination.
- Modified frontend components to handle pagination state and display total counts for orders and plans.
- Ensured compatibility with existing functionality by maintaining behavior when pagination is not used.
2026-04-28 13:59:34 +09:00
DDD1542 ee8f274feb 매미킴 2026-04-27 16:15:42 +09:00
DDD1542 34a44e0d9c Merge branch 'mhkim-node' of https://g.wace.me/jskim/vexplor_dev into gbpark-node 2026-04-27 14:46:26 +09:00
kmh e18a62f56f refactor(pop): trim main page widgets, drop layout auto-clone
- Remove KpiCarousel/RecentActivity from pop main pages (7 companies)
- Empty banner default; rename settings key home -> main
- Strip API fetch/cache from usePopSettings, return hardcoded defaults
- Drop screen_layouts_pop auto-clone/fallback for regular users
- Add SUPER_ADMIN direct-entry branch in AppLayout pop handler

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 14:45:00 +09:00
kjs 346a1314a2 Merge branch 'mhkim-node' of https://g.wace.me/jskim/vexplor_dev into jskim-node 2026-04-26 18:33:52 +09:00
kmh dcbcdb2f52 refactor(pop): isolate new shell, add super-admin entry, drop /pop fallback
- per-company PopShell copies under (main)/COMPANY_*/pop/_components/common/
  (no longer imports @/components/pop/hardcoded/PopShell)
- new components/pop/shell/CompanySwitchModal for new POP entry
- AppLayout: SUPER_ADMIN POP-mode toggle + company-select modal flow
- usePopSettings: handle /COMPANY_X/pop/<tail> URLs (extractScreenKey)
- authController + AppLayout: drop legacy /pop fallback;
  use /\${companyCode}/pop/main when childMenus>1 lacks [POP_LANDING]

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 15:07:44 +09:00
kjs 3d339f4846 Merge branch 'mhkim-node' of https://g.wace.me/jskim/vexplor_dev into jskim-node 2026-04-24 17:59:56 +09:00
kjs f922841d8d Merge branch 'mhkim-node' of https://g.wace.me/jskim/vexplor_dev into jskim-node 2026-04-24 17:59:00 +09:00
kjs 7e3a503adc feat: Add sales order bulk upload functionality
- Introduced a new controller for handling bulk uploads of sales orders via Excel, allowing users to efficiently manage large volumes of sales data.
- Implemented validation to ensure required fields are present and provided appropriate error messages for missing data.
- Enhanced the service layer to support item creation and master data management during the upload process.
- Updated routes to include a new endpoint for the bulk upload feature, ensuring secure access through token authentication.

These changes aim to streamline the sales order management process and improve user experience when handling bulk data uploads.
2026-04-24 17:58:11 +09:00
kmh 5ba8901a33 feat(pop): replicate COMPANY_7 pop to COMPANY_8/9/10/16/29/30
Copy the POP terminal screens from COMPANY_7/pop to the other six
company folders (POP.md excluded). URLs are already companyCode-aware
via usePopCompanyPath, so the replicated code works per-company with
no further edits.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 16:25:55 +09:00
kmh 28bdaedac6 refactor(pop): extract company path via usePopCompanyPath hook
Replace hardcoded /COMPANY_7/ URL prefixes across POP pages and
components with usePopCompanyPath() so navigation derives the company
code from the authenticated user.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 15:29:57 +09:00
kmh d8209f85c2 feat(pop): unify theme with COLOR_MAP and introduce accepted_results multi-accept flow 2026-04-24 15:00:47 +09:00
kmh de660679ca feat(frontend/logistics): render remark via category label map 2026-04-24 15:00:42 +09:00
kjs 37ca354af9 feat: Implement cutting plan management and work instruction modal
- Introduced a new cutting plan management page for COMPANY_9, allowing users to manage cutting plans effectively.
- Added a Work Instruction Apply Modal to facilitate the application of work instructions linked to cutting plans.
- Enhanced data handling by incorporating additional fields such as condition_unit, condition_base_value, condition_tolerance, condition_auto_collect, and condition_plc_data in relevant controllers and database interactions.
- Updated UI components to support new features, including displaying batch numbers and item sizes in the work instruction page.

These changes aim to improve the efficiency and usability of cutting plan and work instruction management processes.
2026-04-24 11:12:32 +09:00