--- phase: 02-bug-fixes plan: 02 subsystem: database, cron tags: [allegro, status-sync, cursor, migration] requires: - phase: 02-bug-fixes provides: Plan 02-01 (dead code fix in AllegroShipmentService) provides: - Kolumna orders.last_status_checked_at z indeksem (source, source_updated_at) - Kursor kursorowy w findOrdersNeedingStatusSync() - Zapis timestampu po sukcesie importu (markOrderStatusChecked) affects: cron-status-sync, allegro-order-import tech-stack: added: [] patterns: [cursor-based-sync, timestamp-marker] key-files: created: - database/migrations/20260312_000047_add_last_status_checked_at_to_orders.sql modified: - src/Modules/Settings/AllegroStatusSyncService.php key-decisions: - "Indeks kompozytowy (source, source_updated_at) zamiast single-column (last_status_checked_at) — code review wykazał że single-column jest bezużyteczny dla zapytania" - "markOrderStatusChecked() ciche Throwable — nie przerywać pętli sync z powodu błędu logu" patterns-established: - "Cursor pattern: last_status_checked_at NULL OR source_updated_at > last_status_checked_at" duration: ~30min started: 2026-03-13T00:00:00Z completed: 2026-03-13T00:00:00Z --- # Phase 02 Plan 02: Kursor last_status_checked_at w AllegroStatusSyncService **Dodano kursor czasowy do sync statusów Allegro — zamówienia nie są re-importowane gdy status nie zmienił się.** ## Performance | Metric | Value | |--------|-------| | Duration | ~30min | | Started | 2026-03-13 | | Completed | 2026-03-13 | | Tasks | 2/2 completed | | Files modified | 2 | ## Acceptance Criteria Results | Criterion | Status | Notes | |-----------|--------|-------| | AC-1: Zamówienia z aktualnym timestampem pomijane | Pass | `source_updated_at > last_status_checked_at` | | AC-2: Zamówienia bez sprawdzenia uwzględniane | Pass | `last_status_checked_at IS NULL` | | AC-3: Timestamp zapisywany po sukcesie | Pass | `markOrderStatusChecked()` w try, nie w catch | | AC-4: Migracja bez destrukcji danych | Pass | `NULL DEFAULT NULL` — istniejące wiersze = NULL | ## Accomplishments - Migracja SQL dodaje kolumnę `orders.last_status_checked_at DATETIME NULL` - `findOrdersNeedingStatusSync()` filtruje tylko zamówienia gdzie status mógł się zmienić - `markOrderStatusChecked()` aktualizuje timestamp po każdym sukcesie importu - Code review poprawił indeks: kompozytowy `(source, source_updated_at)` zamiast bezużytecznego single-column ## Files Created/Modified | File | Change | Purpose | |------|--------|---------| | `database/migrations/20260312_000047_add_last_status_checked_at_to_orders.sql` | Created | Migracja: nowa kolumna + indeks kompozytowy | | `src/Modules/Settings/AllegroStatusSyncService.php` | Modified | Kursor + markOrderStatusChecked() | ## Decisions Made | Decision | Rationale | Impact | |----------|-----------|--------| | Indeks kompozytowy `(source, source_updated_at)` | Code review: single-column na `last_status_checked_at` nieużywany przez zapytanie z `source = ?` | Lepsza wydajność zapytania kursorowego | | `markOrderStatusChecked()` swallows Throwable | Błąd zapisu timestampu nie może przerywać pętli synchronizacji | Degradacja graceful — zamówienie zostanie ponowione | ## Deviations from Plan ### Auto-fixed Issues **1. Indeks SQL — zmiana z single-column na kompozytowy** - **Found during:** Code review po implementacji - **Issue:** Plan zakładał `ADD INDEX orders_status_check_idx (last_status_checked_at)` — bezużyteczny dla zapytania z wiodącym filtrem `source = ?` - **Fix:** Zamieniony na `ADD INDEX orders_source_updated_idx (source, source_updated_at)` - **Files:** `database/migrations/20260312_000047_add_last_status_checked_at_to_orders.sql` - **Verification:** Logika zapytania potwierdza, że MySQL użyje indeksu z wiodącą kolumną `source` ### Deferred Items - Duplikacja kodu `AllegroOrderSyncStateRepository` / `ShopproOrderSyncStateRepository` (brak abstrakcji) — poza zakresem planu 02-03, do rozważenia w osobnym planie ## Issues Encountered None. ## Skill Audit | Skill | Status | Notes | |-------|--------|-------| | /code-review | ✓ | Wywołany — wykazał błąd indeksu, naprawiony | | sonar-scanner | ✓ | Uruchomiony — brak nowych issues w zmienionych plikach | ## Next Phase Readiness **Ready:** - Kursor `last_status_checked_at` gotowy po uruchomieniu migracji na bazie - Migracja idempotentna (nullable column, nie psuje istniejących danych) **Concerns:** - Migracja musi być uruchomiona ręcznie lub przez migrator przed pierwszym cron run - AllegroStatusSyncService nadal ma problem wydajności — każde zamówienie = pełny re-import z API (oddzielny concern w CONCERNS.md) **Blockers:** None --- *Phase: 02-bug-fixes, Plan: 02* *Completed: 2026-03-13*