feat: operator Sacks/Boxes/DO tiles, drop Net from history
ci / smoke (push) Canceled after 0s

This commit is contained in:
andrew committed 2026-09-25 08:52:29 +07:00
1 parent 0efcfa45b8
commit 1e4dc4201c
7 files changed
+172 -729

No files matched your search

+137
View File
@@ -0,0 +1,137 @@
# Implementation Plan — Operator Tiles + History Cleanup (DO Expected Labels)
> Status: **implemented** (UI-only; manual device checks pending).
> Scope: **UI labels/columns only** — no API/DB/predict semantics change.
> Ports (locked): **5721 = office** · **5000 = operator** (DO manual uploads, legacy manual, live counts).
> Operator does **not** need history; history/analytics stay **office-only** (`/history`, `/analytics` already gated in `counter_dashboard.py`).
---
## 1. Why
Current operator tiles in `do_manual` show **Net / Target** next to **Karung Masuk / Box Masuk**. When unloading is 0 (normal load-out), net == gross → redundant and confusing.
History has a **Net** column that duplicates sacks/boxes when net ≈ count, and **Expected** has no unit hint (sack vs box).
**Goal:** operator compares **counted** vs **DO paper qty** in four clear tiles. History drops Net; Expected is labeled as DO sacks/boxes.
---
## 2. Locked decisions
| # | Topic | Decision |
|---|---|---|
| 1 | Port split | 5721 office (mode/model switches, history, analytics, plate require) · 5000 operator (start/stop, DO photo upload, live counts). Unchanged. |
| 2 | Operator history | Operator does not consume history/count analytics; no history link/panel on `operator.html`. History page stays office-only. |
| 3 | Operator tiles | Four tiles only (see §3). **No “Net …” tiles** on operator UI. |
| 4 | DO expected naming | UI name = **DO Sacks** / **DO Boxes** (paper expected). Server fields stay `expected_sack` / `expected_box`. |
| 5 | History columns | Cleaner set (§4). **Remove Net column.** Expected labeled as DO sacks/boxes. |
| 6 | Backend NET | **Keep** `net_sack` / `net_box` in API, `current_batch.json`, DB, discard rule (`both nets 0`), exports if still needed for audit. **UI stop showing net on operator.** |
---
## 3. Operator tiles (`templates/operator.html`)
Replace current info grid rows with:
| Tile label | Value | Source (`GET /api/current-batch`) |
|---|---|---|
| **Sacks** | counted sacks | `count` (same as today’s “Karung Masuk”) |
| **Boxes** | counted boxes | `box_count` (same as “Box Masuk”) |
| **DO Sacks** | expected sacks | `expected_sack` (0 if no batch/no DO) |
| **DO Boxes** | expected boxes | `expected_box` |
Render rules:
- **All four tiles always visible** on the operator card (not only in `do_manual`).
- Non-`do_manual`: DO Sacks / DO Boxes show `0` or `--` (no staged expectation); still show label so layout is stable.
- `do_manual` + active batch: DO tiles = values from batch state (start sum of staged DOs).
- Remove rows/IDs: `opNetSackItem`, `opNetBoxItem`, and JS that writes `net_sack` / `net_box` into those tiles.
- Keep: Batch Berjalan, Waktu Mulai, Plat / No. DO (batch active), mode badge, DO panel.
DO card form labels (same vocabulary):
- `Ekspektasi karung` → **`DO Sacks`** (or `DO Sacks (karung)` if Indonesian preferred — pick one at implement; default English matches tiles).
- `Ekspektasi box` → **`DO Boxes`**.
Group preview chips unchanged (already “N karung · M box”).
Optional polish (same file, if trivial): under Sacks show `of DO Sacks` only in `do_manual` — **not** a second Net row.
---
## 4. History (`templates/history.html`) — office only
Current header:
`Batch # | Plate | No. DO | Sacks | Boxes | Expected | Net | Start | End | Duration`
**New header (no Net, clearer Expected):**
| Column | Content |
|---|---|
| Batch # | `batch_number` |
| Plate | `plate` or `—` |
| No. DO | `do_numbers` joined or `—` |
| Sacks | `count` (gross loaded; stored as `count`) |
| Boxes | `box_loading` |
| DO Sacks / Boxes | `expected_sack / expected_box` e.g. `100 / 12` |
| Start | time |
| End | time |
| Duration | minutes |
- Remove cell that prints `net_sack / net_box`.
- API: keep returning nets if already present; **UI ignores them** (or stop emitting in `day-detail` later — not required).
- colspan updates (loading, empty, error rows).
- Export day XLSX: drop Net columns if present; rename Expected headers to `DO Sacks`, `DO Boxes` (match UI).
No changes to operator gate: `GET /history` still office-only.
---
## 5. Non-goals
- No change to `net_counts` / discard-both-nets / `finalize_batch`.
- No change to ports, office-only POSTs, OCR engine toggle.
- No history page for operator.
- No API rename of `expected_*` (JSON keys stable).
---
## 6. Files
| File | Change |
|---|---|
| `templates/operator.html` | Four tiles Sacks/Boxes/DO Sacks/DO Boxes; remove Net tiles + JS |
| `templates/history.html` | Drop Net column; Expected → `DO Sacks / DO Boxes` |
| `counter_dashboard.py` | Optional: export headers only (if export shows Net/Expected) |
| `docs/do-expected-tiles-plan.md` | This plan |
| Old plan | Delete `docs/do-batch-implementation-plan.md` (superseded by shipped feature + this UI plan) |
---
## 7. Test / verify
```bash
python -m pytest tests/ -q
python -m compileall predict.py counter_dashboard.py src tests
```
Manual (office vs operator):
1. `:5000/operator` — tiles labeled Sacks, Boxes, DO Sacks, DO Boxes; no “Net …” labels.
2. `:5000/operator` in `do_manual` — start with DO → DO Sacks/Boxes = sum of DO fields; Sacks/Boxes track camera.
3. `:5721/history` — columns as §4; no Net; Expected shows `n / m`.
4. Operator browser → `/history` → still operator page (office gate).
5. Mode/model POST from `:5000` still 403 (unchanged).
---
## 8. Acceptance
1. Operator live card shows exactly: Sacks, Boxes, DO Sacks, DO Boxes (+ batch meta).
2. No operator-visible string “Net Karung”, “Net Box”, “Net / Target”.
3. History table has no Net column; Expected header communicates DO sacks/boxes.
4. History remains office-only.
5. Discard rule and DB `net_*` columns unchanged.
6. pytest + compileall green.