1.8.6
⚙️ Patch 1.8.6 — Tiered Nettospanne EK & full-watchlist analyze¶
🚀 Summary¶
- Tiered target EK — Amazon Nettospanne margin by avg VK (30d): 13% when VK < 25 EUR, 10% at or above (replaces single configurable margin %).
- Analyze (by EAN) — one API call processes all non-archived watchlist rows in internal 500-row DB batches; always recomputes and writes EK/margin (no skip-write / reanalyze pagination).
- Watchlist UI — removed manual Margin % inputs (analyze toolbar + cron); info text explains tier rules; Target EK column shows per-row
% Nettospannefrom analyze. - Broader analyze scope — no longer limited to
source=keepaorASIN:stub exclusion; ~all table rows are eligible (rows without Keepa fetch data areskipped_analyze).
✨ Improvements¶
Tiered Nettospanne (pricing.py)¶
| Avg VK (30d) brutto | Target margin |
|---|---|
| < 25 EUR | 13% |
| ≥ 25 EUR | 10% |
margin_percent_for_sell_price_eur()— tier selection from avg30 sell price.analyze_from_stored_row()/analyze_product()— always use tiered margin (no per-run override).margin_percentstored on each watchlist row; Target EK and tiered margin driveare_targets_met/ wholesale targets.
Example: VK 19.14 EUR, fees 2.87 EUR → 13% → target EK ~10.72 EUR (was ~11.30 EUR at flat 10%).
Analyze pipeline — simplified¶
Before: frontend looped offset / limit / reanalyze=true; backend could skip DB writes when EK unchanged (ek_skipped_write).
After:
POST /keepa/analyze-productsbody:{ target_quantity?, asins? }only.- Server loads all eligible rows (
archived_at IS NULL), batches ofKEEPA_ANALYZE_BATCH_SIZE(500). - Every row with valid Keepa metrics is written (tier refresh, catalog targets,
in_qogita_catalog). - Response:
requested,stored,batches,ek_changed,margin_changed,skipped_analyze, pipeline counts.
Logs:
Keepa analyze start: margin=tiered(<25→13%,≥25→10%) eligible=1450 with_keepa_fetch=239 batch_size=500
Keepa analyze complete: … batches=3 margin_changed=… ek_changed=…
eligible— all non-archived watchlist rows.with_keepa_fetch— subset that completed Fetch Products (havekeepa_product_fetched_at); only those can get tiered EK until fetched.
CRUD — analyze eligibility¶
_analyze_eligible_query()— non-archived rows only (nosource=keepa, noASIN:GTIN filter).count_items_with_keepa_fetch()— diagnostic count for logging.
Frontend¶
- Removed Margin % (Nettospanne) from analyze toolbar and scheduled jobs.
- Margin tier info above table and under Scheduled jobs.
- Single
analyzeProducts()call (no client-side batch loop). - Success toast includes
margin_changedwhen tier updates apply.
🐛 Bug Fixes¶
Reanalyze skipped tier migration¶
- Flat 10% rows were not updated after tier rules shipped because
ek_skipped_writetreated them as unchanged. - Analyze now always persists on each run; tier mismatches show up as
margin_changed/ek_changedin logs.
✨ Tests¶
test_keepa_pricing.py— tier thresholds,analyze_from_stored_rowat 19.14 EUR → 13% / EK 10.72.- Updated analyze API models (
KeepaAnalyzeProductsRequest/Response).
cd backend/service_omni
pytest app/tests/test_keepa_pricing.py::TestTieredMargin -v
📁 Files changed¶
Backend (service_omni)
app/services/keepa/pricing.py— tiered margin constants + helpersapp/services/keepa/scanner.py— simplifiedanalyze_products()app/services/keepa/constants.py—KEEPA_ANALYZE_BATCH_SIZEapp/crud/qogita.py—_analyze_eligible_query(),count_items_with_keepa_fetch()app/models/keepa.py— analyze request/response shapeapp/api/v1/endpoints/keepa.pyapp/tests/test_keepa_pricing.py,test_keepa_workflow_integration.py,test_keepa_scanner_mocked.py
Frontend
src/pages/Statistics/Tabs/QogitaWatchlistTab.jsxsrc/pages/Statistics/Tabs/qogitaWatchlistPrefs.js—KEEPA_NETTOPANNE_MARGIN_SUMMARY,formatTargetEkMarginCaption()
🔧 Deploy¶
Restart service-omni. Rebuild frontend. No database migration.
After deploy:
- Run 2. Fetch Products for any rows still missing Keepa metrics (
with_keepa_fetch<eligible). - Run 3. Analyze (by EAN) once — expect
margin_changed> 0 for VK < 25 EUR rows still on old 10%.
Usage notes¶
Why analyze total ≠ table row count
| Count | Meaning |
|---|---|
| Table total (~1453) | All rows including archived / stubs |
eligible |
Non-archived rows analyze iterates |
with_keepa_fetch |
Rows with Keepa product data (can compute EK) |
skipped_analyze |
Eligible but missing avg30 / fees (run Fetch Products first) |
Cron margin
- Qogita / Keepa crons no longer send
margin_percent; tier rules apply automatically on analyze paths.
SQL — rows still on 10% below 25 EUR VK
SELECT gtin, name, avg30_new_price_cents / 100.0 AS vk_eur,
margin_percent, calculated_ek_price
FROM qogita_watchlist_items
WHERE archived_at IS NULL
AND avg30_new_price_cents IS NOT NULL
AND avg30_new_price_cents >= 0
AND (avg30_new_price_cents / 100.0) < 25
AND margin_percent = 10
ORDER BY gtin;
Run Analyze (by EAN) after deploy to refresh these rows.