feat(cupang): 출고방식 파렛트, 상태/문서번호 폼 제거, 폼·상세 레이아웃 개편

- 출고방식 선택지에 "파렛트" 추가
- 신규/수정 폼에서 상태·문서번호 입력 제거 (status는 작성중 기본 + 취소처리로만 변경)
- document_no DB 컬럼 제거: init.sql 반영 + 기존 DB용 002 드롭 마이그레이션(승인 후 실행)
- 폼: 공통 헤더(좌) / 품목 라인(우) 2열 배치
- 상세: 엑셀·상태변경 버튼 삭제, ◀◀ 달력(검정) 좌측, 수정 우측 정렬, 문서번호 표시 제거

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
2026-05-30 05:07:21 +09:00
parent 4113a034f4
commit d9ea7550b0
8 changed files with 48 additions and 42 deletions
+3 -6
View File
@@ -323,14 +323,13 @@ class CupangDBStore:
row = conn.execute(
"""
INSERT INTO cupang_shipments
(document_no, created_by, document_date, ship_date,
(created_by, document_date, ship_date,
center_arrival_date, center_id, center_name_snapshot,
ship_method, outbound_summary, worker, status, memo)
VALUES (%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s)
VALUES (%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,%s)
RETURNING *
""",
(
h["document_no"] or None,
created_by.lower().strip(),
h["document_date"],
h["ship_date"],
@@ -360,7 +359,7 @@ class CupangDBStore:
row = conn.execute(
"""
UPDATE cupang_shipments
SET document_no = %s, document_date = %s, ship_date = %s,
SET document_date = %s, ship_date = %s,
center_arrival_date = %s, center_id = %s,
center_name_snapshot = %s, ship_method = %s,
outbound_summary = %s, worker = %s, memo = %s
@@ -368,7 +367,6 @@ class CupangDBStore:
RETURNING *
""",
(
h["document_no"] or None,
h["document_date"],
h["ship_date"],
h["center_arrival_date"],
@@ -526,7 +524,6 @@ class CupangDBStore:
center_id = None
return {
"document_no": str(header.get("document_no") or "").strip(),
"document_date": document_date,
"ship_date": ship_date,
"center_arrival_date": center_arrival_date,
-6
View File
@@ -248,7 +248,6 @@ async def new_form(request: Request) -> HTMLResponse:
async def create(
request: Request,
lines_json: str = Form("[]"),
document_no: str = Form(""),
document_date: str = Form(...),
ship_date: str = Form(...),
center_arrival_date: str = Form(...),
@@ -257,7 +256,6 @@ async def create(
ship_method: str = Form("택배"),
outbound_summary: str = Form(""),
worker: str = Form(""),
status: str = Form("작성중"),
memo: str = Form(""),
user: dict[str, Any] = Depends(_require_user),
) -> RedirectResponse:
@@ -265,7 +263,6 @@ async def create(
if store is None:
raise HTTPException(status_code=503, detail="cupang_db 미설정")
header = {
"document_no": document_no,
"document_date": document_date,
"ship_date": ship_date,
"center_arrival_date": center_arrival_date,
@@ -274,7 +271,6 @@ async def create(
"ship_method": ship_method,
"outbound_summary": outbound_summary,
"worker": worker,
"status": status,
"memo": memo,
}
try:
@@ -351,7 +347,6 @@ async def update(
request: Request,
shipment_id: int,
lines_json: str = Form("[]"),
document_no: str = Form(""),
document_date: str = Form(...),
ship_date: str = Form(...),
center_arrival_date: str = Form(...),
@@ -367,7 +362,6 @@ async def update(
if store is None:
raise HTTPException(status_code=503, detail="cupang_db 미설정")
header = {
"document_no": document_no,
"document_date": document_date,
"ship_date": ship_date,
"center_arrival_date": center_arrival_date,
+1 -1
View File
@@ -21,7 +21,7 @@ STATUSES: tuple[str, ...] = (
)
# 출고방식 기본 후보 (자유 입력 허용, 아래는 select 기본값)
SHIP_METHODS: tuple[str, ...] = ("택배", "직접배송", "화물", "기타")
SHIP_METHODS: tuple[str, ...] = ("택배", "직접배송", "화물", "파렛트", "기타")
# 엑셀/시트 컬럼 순서 — 기존 구글시트와 동일하게 유지
SHEET_COLUMNS: tuple[str, ...] = (
@@ -6,18 +6,7 @@
<section class="cpg">
<div class="erp-page-actions cpg-actions">
<a class="erp-btn erp-btn-primary" href="/cupang/{{ shipment.id }}/edit">수정</a>
<a class="erp-btn erp-btn-outline" href="/cupang/{{ shipment.id }}/export">엑셀</a>
<a class="erp-btn erp-btn-outline" href="/cupang/?date={{ shipment.ship_date }}">달력으로</a>
<form method="post" action="/cupang/{{ shipment.id }}/status" class="cpg-inline-form">
<select class="erp-select" name="status">
{% for s in statuses %}
<option value="{{ s }}" {% if shipment.status == s %}selected{% endif %}>{{ s }}</option>
{% endfor %}
</select>
<button type="submit" class="erp-btn erp-btn-outline">상태 변경</button>
</form>
<a class="erp-btn erp-btn-primary" href="/cupang/?date={{ shipment.ship_date }}">◀◀ 달력</a>
<form method="post" action="/cupang/{{ shipment.id }}/delete" class="cpg-inline-form"
onsubmit="return confirm('이 출고 묶음을 취소 처리합니다(상태=취소). 계속할까요?');">
@@ -28,6 +17,8 @@
onsubmit="return confirm('이 출고를 완전 삭제합니다(복구 불가, 품목 포함). 계속할까요?');">
<button type="submit" class="erp-btn erp-btn-danger">삭제</button>
</form>
<a class="erp-btn erp-btn-primary cpg-push-right" href="/cupang/{{ shipment.id }}/edit">수정</a>
</div>
<!-- 헤더 -->
@@ -48,7 +39,6 @@
<div><dt>입고센터</dt><dd>{{ shipment.center_name_snapshot or '—' }}</dd></div>
<div><dt>출고방식</dt><dd>{{ shipment.ship_method }}</dd></div>
<div><dt>작업자</dt><dd>{{ shipment.worker or '—' }}</dd></div>
<div><dt>문서번호</dt><dd>{{ shipment.document_no or '—' }}</dd></div>
<div class="cpg-full"><dt>출고/박스 요약</dt><dd>{{ shipment.outbound_summary or '—' }}</dd></div>
<div class="cpg-full"><dt>메모</dt><dd>{{ shipment.memo or '—' }}</dd></div>
</dl>
+8 -15
View File
@@ -9,8 +9,10 @@
<form id="cpg-form" method="post" action="{{ action }}">
<input type="hidden" name="lines_json" id="cpg-lines-json" value="[]" />
<!-- ── 공통 헤더 ── -->
<div class="erp-card cpg-form-card">
<div class="cpg-form-2col">
<!-- ── 공통 헤더 (왼쪽) ── -->
<div class="erp-card cpg-form-card cpg-form-head">
<div class="cpg-card-head"><h2>공통 헤더</h2></div>
<div class="cpg-header-grid">
<label class="erp-field"><span>작성일 *</span>
@@ -45,17 +47,6 @@
<label class="erp-field"><span>작업자</span>
<input class="erp-input" type="text" name="worker"
value="{{ shipment.worker if shipment else '' }}" /></label>
{% if mode == 'new' %}
<label class="erp-field"><span>상태</span>
<select class="erp-select" name="status">
{% for s in statuses %}<option value="{{ s }}">{{ s }}</option>{% endfor %}
</select></label>
{% endif %}
<label class="erp-field"><span>문서번호(선택)</span>
<input class="erp-input" type="text" name="document_no"
value="{{ shipment.document_no or '' if shipment else '' }}" /></label>
</div>
<label class="erp-field cpg-full"><span>출고/박스 요약 (수동 보정 메모)</span>
@@ -66,8 +57,8 @@
<textarea class="erp-input" name="memo" rows="2">{{ shipment.memo if shipment else '' }}</textarea></label>
</div>
<!-- ── 품목 라인 ── -->
<div class="erp-card cpg-form-card">
<!-- ── 품목 라인 (오른쪽) ── -->
<div class="erp-card cpg-form-card cpg-form-lines">
<div class="cpg-card-head">
<h2>품목 라인</h2>
<span class="erp-muted">
@@ -90,6 +81,8 @@
<button type="button" class="erp-btn erp-btn-outline" id="cpg-add-line">+ 라인 추가</button>
</div>
</div><!-- /cpg-form-2col -->
<div class="erp-page-actions">
<button type="submit" class="erp-btn erp-btn-primary">저장</button>
{% if mode == 'edit' %}