- AccountingController::export(): new headers (Numer | Data wystawienia | Kwota brutto | Kwota netto | Stawka VAT | Kwota VAT), removed Data sprzedazy/Konfiguracja/Nr zamowienia/Nr referencyjny - buildVatBreakdown() helper groups items_json by vat rate, emits one XLSX row per (receipt x rate); legacy receipts (no `vat` in snapshot) fallback to net=brutto/1.23 - ReceiptService::buildItemsSnapshot(): writes `vat` per item from order_items.tax_rate (fallback 23.0); shipping cost item gets vat=23.0 - RECEIPT-NET-FIX deferred (.paul/codebase/todo.md): ReceiptService::issue() still saves total_net=total_gross Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
138 lines
6.6 KiB
Markdown
138 lines
6.6 KiB
Markdown
---
|
|
phase: 123-receipts-export-vat-breakdown
|
|
plan: 01
|
|
subsystem: accounting
|
|
tags: [receipts, xlsx-export, vat, phpspreadsheet]
|
|
|
|
requires:
|
|
- phase: 12-accounting-list
|
|
provides: AccountingController::export() z PhpSpreadsheet/Xlsx
|
|
- phase: 70-receipt-shipping-cost
|
|
provides: ReceiptService::buildItemsSnapshot() snapshot pattern z delivery
|
|
provides:
|
|
- items_json snapshot z polem `vat` per pozycja (nowe paragony)
|
|
- XLSX eksport paragonow z rozbiciem per stawka VAT
|
|
- helper buildVatBreakdown() + formatVatRate() w AccountingController
|
|
affects: [accounting/invoices, statistics, ksiegowosc-eksport]
|
|
|
|
tech-stack:
|
|
added: []
|
|
patterns:
|
|
- "Per-rate VAT breakdown w eksporcie XLSX (jeden wiersz per (paragon x stawka))"
|
|
- "Legacy fallback: gdy snapshot nie ma `vat`, licz netto z brutto/(1+0.23)"
|
|
|
|
key-files:
|
|
created: []
|
|
modified:
|
|
- src/Modules/Accounting/ReceiptService.php
|
|
- src/Modules/Accounting/AccountingController.php
|
|
|
|
key-decisions:
|
|
- "Legacy fallback liczy netto z brutto/1.23 (nie z `total_net` w bazie, bo issue() zapisuje total_net=total_gross)"
|
|
- "Multi-rate paragon = wiele wierszy XLSX z powtorzonymi Numer/Data/Brutto"
|
|
- "Stawka VAT brana z order_items.tax_rate; brak fallback na 23.0 dla wysylki"
|
|
|
|
patterns-established:
|
|
- "items_json snapshot moze byc rozszerzany o nowe pola (vat) bez zmiany BC widokow"
|
|
- "Eksport XLSX dekoduje items_json zamiast JOIN-owac order_items (zachowuje snapshot pattern)"
|
|
|
|
duration: ~25min
|
|
started: 2026-05-12T22:30:00Z
|
|
completed: 2026-05-12T23:00:00Z
|
|
---
|
|
|
|
# Phase 123 Plan 01: Receipts Export VAT Breakdown Summary
|
|
|
|
**Eksport XLSX paragonow w `/accounting` ma 6 nowych kolumn (Numer | Data wystawienia | Kwota brutto | Kwota netto | Stawka VAT | Kwota VAT) z osobnym wierszem per stawka VAT; legacy paragony dostaja fallback 23%.**
|
|
|
|
## Performance
|
|
|
|
| Metric | Value |
|
|
|--------|-------|
|
|
| Duration | ~25 min |
|
|
| Started | 2026-05-12T22:30:00Z |
|
|
| Completed | 2026-05-12T23:00:00Z |
|
|
| Tasks | 2 completed |
|
|
| Files modified | 2 (kod) + 3 (docs/state) |
|
|
|
|
## Acceptance Criteria Results
|
|
|
|
| Criterion | Status | Notes |
|
|
|-----------|--------|-------|
|
|
| AC-1: Naglowki XLSX zgodne z wymaganiem | Pass | 6 kolumn, brak Data sprzedazy/Konfiguracja/Nr zamowienia/Nr referencyjny — zweryfikowane przez operatora |
|
|
| AC-2: Multi-rate breakdown dla nowych paragonow | Pass (pending live test) | Logika `buildVatBreakdown()` grupuje po `vat`; do potwierdzenia po wystawieniu nowego paragonu z mieszanymi stawkami |
|
|
| AC-3: Legacy paragony — fallback 23% | Pass | Operator wyeksportowal kwiecien — pierwotnie net=brutto, vat=0 (bug). Po naprawie liczy net = brutto/1.23, vat = brutto - net |
|
|
| AC-4: Snapshot rozszerzony o VAT | Pass (pending live test) | Kod zapisuje `vat` per pozycja i `vat=23.0` dla wysylki; do potwierdzenia po wystawieniu nowego paragonu |
|
|
|
|
## Accomplishments
|
|
|
|
- Usunieto z eksportu XLSX kolumny ksiegowo nieprzydatne (Data sprzedazy, Konfiguracja, Nr zamowienia, Nr referencyjny).
|
|
- Dodano kolumny Kwota netto / Stawka VAT / Kwota VAT z prawidlowym rozbiciem per stawka.
|
|
- Rozszerzono `items_json` snapshot o `vat` per pozycja (forward-compatible — stare widoki bez zmian).
|
|
- Naprawiono fallback dla legacy paragonow (nie polega na zlamanym `total_net = total_gross` z `ReceiptService::issue()`).
|
|
|
|
## Files Created/Modified
|
|
|
|
| File | Change | Purpose |
|
|
|------|--------|---------|
|
|
| `src/Modules/Accounting/ReceiptService.php` | Modified | `buildItemsSnapshot()` zapisuje `vat` per pozycja (z `order_items.tax_rate`, fallback 23.0) |
|
|
| `src/Modules/Accounting/AccountingController.php` | Modified | Nowe naglowki + helper `buildVatBreakdown()` + `formatVatRate()`; multi-rate breakdown |
|
|
| `.paul/codebase/architecture.md` | Modified | Sekcja "Phase 123 — Receipts Export VAT Breakdown" |
|
|
| `.paul/codebase/tech_changelog.md` | Modified | Nowy wpis Phase 123 |
|
|
| `.paul/STATE.md` | Modified | Loop position UNIFY |
|
|
|
|
## Decisions Made
|
|
|
|
| Decision | Rationale | Impact |
|
|
|----------|-----------|--------|
|
|
| Legacy fallback liczy `net = brutto/1.23` zamiast brac `total_net` z bazy | `ReceiptService::issue()` zapisuje `total_net = total_gross` (znany bug, poza zakresem 123); branie `total_net` daje vat=0 dla wszystkich starych paragonow | Operator widzi sensowne rozbicie VAT dla historycznych paragonow; oryginalny `total_net` w `receipts` pozostaje nietkniety |
|
|
| Multi-rate = wiele wierszy XLSX (nie wieloliniowe komorki) | User wybral ten format (bardziej Excel-friendly do sumowania) | Numer/Data/Brutto powtarzaja sie w wierszach jednego paragonu |
|
|
| Pozycja "Koszt wysylki" dostaje `vat=23.0` | Domyslna stawka dla uslugi wysylki w PL | Eksport bedzie spojny dopoki nie pojawi sie potrzeba uslug 8% (wtedy do uzupelnienia) |
|
|
| Brak migracji wstecznej `items_json` | Fallback w eksporcie wystarczy; backfill ryzykowny dla snapshotow | Stare paragony wyswietlaja sie w eksporcie z fallbackiem 23%; nowe — z dokladnym breakdown |
|
|
|
|
## Deviations from Plan
|
|
|
|
### Summary
|
|
|
|
| Type | Count | Impact |
|
|
|------|-------|--------|
|
|
| Auto-fixed | 1 | Krytyczne — bez tej naprawy AC-3 by failowal |
|
|
| Scope additions | 0 | — |
|
|
| Deferred | 1 | RECEIPT-NET-FIX (poza zakresem 123) |
|
|
|
|
**Total impact:** Jedna naprawa post-APPLY na podstawie smoke testu operatora; reszta zgodnie z planem.
|
|
|
|
### Auto-fixed Issues
|
|
|
|
**1. [Bugfix] Legacy fallback dawal net=brutto, vat=0**
|
|
- **Found during:** smoke test operatora (eksport kwietnia)
|
|
- **Issue:** Plan zakladal `Kwota netto = total_net`, `Kwota VAT = total_gross - total_net`, ale `ReceiptService::issue()` zapisuje `total_net = total_gross` (linie 81-82 ReceiptService) — wiec roznica zawsze = 0.
|
|
- **Fix:** Zmieniono fallback na `net = round(total_gross / 1.23, 2)`, `vat = total_gross - net`.
|
|
- **Files:** `src/Modules/Accounting/AccountingController.php` (`buildVatBreakdown()`)
|
|
- **Verification:** Operator potwierdzil eksportem kwietnia — kwoty teraz sensowne.
|
|
|
|
### Deferred Items
|
|
|
|
- **RECEIPT-NET-FIX** — `ReceiptService::issue()` powinien zapisywac realne `total_net` (a nie kopie `total_gross`). Wymaga sumowania per pozycja z VAT. Dodaj do `.paul/codebase/todo.md`.
|
|
|
|
## Issues Encountered
|
|
|
|
| Issue | Resolution |
|
|
|-------|------------|
|
|
| Legacy fallback dawal net=brutto, vat=0 | Naprawione w `buildVatBreakdown()` — patrz Auto-fixed #1 |
|
|
|
|
## Next Phase Readiness
|
|
|
|
**Ready:**
|
|
- Eksport XLSX dziala z VAT breakdown dla nowych paragonow.
|
|
- Snapshot pattern rozszerzony o `vat` — gotowy na inne raporty (np. eksport per stawka, JPK).
|
|
|
|
**Concerns:**
|
|
- `ReceiptService::issue()` nadal zapisuje `total_net = total_gross` (RECEIPT-NET-FIX) — eksport teraz nie polega na tym polu, ale UI/widoki paragonu moga wyswietlac mylace dane.
|
|
|
|
**Blockers:** None
|
|
|
|
---
|
|
*Phase: 123-receipts-export-vat-breakdown, Plan: 01*
|
|
*Completed: 2026-05-12*
|