From 2ab38c7dbd443c2d78a52b85a5f327936bdc77be Mon Sep 17 00:00:00 2001 From: king Date: Mon, 22 Jun 2026 18:14:45 +0900 Subject: [PATCH] =?UTF-8?q?feat(malaysia):=20=EC=9D=B4=EB=8F=99=20?= =?UTF-8?q?=EC=9D=B4=EB=A0=A5=EC=97=90=20=EB=82=B1=EA=B0=9C/=EC=BD=A4?= =?UTF-8?q?=EB=B3=B4=20=EB=B6=84=EB=A6=AC=20=ED=91=9C=EC=8B=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - set_movement(콤보 출고 원장)을 이동이력에 병합, 구분 컬럼(낱개/콤보) 추가 - db.list_set_movements (동일 필터: 창고/종류/날짜) - 콤보 줄은 set_code 를 Item 으로 표시 → 콤보 몇 개 나갔는지 확인 가능 Co-Authored-By: Claude Opus 4.8 --- app/modules/malaysia/db.py | 34 +++++++++++++++++++ app/modules/malaysia/router.py | 26 ++++++++++---- .../templates/malaysia/movements.html | 11 ++++-- 3 files changed, 63 insertions(+), 8 deletions(-) diff --git a/app/modules/malaysia/db.py b/app/modules/malaysia/db.py index 522d830..02474ab 100644 --- a/app/modules/malaysia/db.py +++ b/app/modules/malaysia/db.py @@ -327,6 +327,40 @@ class MalaysiaStockStore: ).fetchall() return [self._serialize(r) for r in rows] + def list_set_movements( + self, + *, + warehouse_code: str | None = None, + movement_type: str | None = None, + date_from: str | None = None, + date_to: str | None = None, + limit: int = 500, + ) -> list[dict[str, Any]]: + """콤보(세트) 출고 원장(set_movement) 목록. 이동이력 콤보 줄 표시용.""" + clauses: list[str] = [] + params: list[Any] = [] + if warehouse_code: + clauses.append("warehouse_code = %s") + params.append(warehouse_code) + if movement_type in store.MOVEMENT_TYPES: + clauses.append("movement_type = %s") + params.append(movement_type) + if date_from: + clauses.append("movement_date >= %s") + params.append(date_from) + if date_to: + clauses.append("movement_date <= %s") + params.append(date_to) + where = ("WHERE " + " AND ".join(clauses)) if clauses else "" + params.append(int(limit)) + with self._pool.connection() as conn: + rows = conn.execute( + f"SELECT * FROM set_movement {where} " + "ORDER BY movement_date DESC, id DESC LIMIT %s", + params, + ).fetchall() + return [self._serialize(r) for r in rows] + def daily_movement_totals( self, *, warehouse_code: str, movement_date: str, movement_type: str ) -> dict[str, int]: diff --git a/app/modules/malaysia/router.py b/app/modules/malaysia/router.py index fc4abed..cf58e01 100644 --- a/app/modules/malaysia/router.py +++ b/app/modules/malaysia/router.py @@ -268,12 +268,26 @@ async def movements_page(request: Request) -> HTMLResponse: wh = _selected_wh(request, st) mtype = (request.query_params.get("type") or "").strip().upper() fdate = (request.query_params.get("date") or "").strip() - movements = st.list_movements( - warehouse_code=wh, - movement_type=mtype if mtype in store.MOVEMENT_TYPES else None, - date_from=fdate or None, - date_to=fdate or None, - limit=300, + mt = mtype if mtype in store.MOVEMENT_TYPES else None + singles = st.list_movements( + warehouse_code=wh, movement_type=mt, + date_from=fdate or None, date_to=fdate or None, limit=300, + ) + for m in singles: + m["kind"] = "individual" + # 콤보(세트) 출고 원장도 함께 보여준다(낱개/콤보 분리 표시). + combos = st.list_set_movements( + warehouse_code=wh, movement_type=mt, + date_from=fdate or None, date_to=fdate or None, limit=300, + ) + for m in combos: + m["kind"] = "set" + m["item_code"] = m.get("set_code", "") + # 날짜(그다음 id) 내림차순 병합. + movements = sorted( + singles + combos, + key=lambda m: (str(m.get("movement_date") or ""), int(m.get("id") or 0)), + reverse=True, ) for m in movements: m["date_label"] = _date_label(m.get("movement_date")) diff --git a/app/modules/malaysia/templates/malaysia/movements.html b/app/modules/malaysia/templates/malaysia/movements.html index 4c73bea..21f107d 100644 --- a/app/modules/malaysia/templates/malaysia/movements.html +++ b/app/modules/malaysia/templates/malaysia/movements.html @@ -144,11 +144,18 @@
- + {% for m in movements %} + @@ -157,7 +164,7 @@ {% endfor %} {% if not movements %} - + {% endif %}
DateTypeItemQtyMemoBy
Date구분TypeItemQtyMemoBy
{{ m.date_label }} + {% if m.kind == 'set' %} + 콤보 + {% else %} + 낱개 + {% endif %} + {{ m.movement_type }} {{ m.item_code }} {{ m.qty }}
이동 이력이 없습니다.
이동 이력이 없습니다.