Commit Graph

2 Commits

Author SHA1 Message Date
Дмитрий 1e0c0ab90a fix(billing): Plan 4 Task 2 code-review fixes (2 Important + 1 Minor)
- PricingTierResolver::resolveForCount — InvalidArgumentException на
  $leadOrdinal < 1 (closes I-1: defensive contract validation).
- PricingTierRepository::activeAt — explicit @var Collection<int,
  PricingTier> annotation для type narrowing (closes I-2; firstOrFail
  отвергнут — Stan ругается на Eloquent\Model return-type).
- PricingTierResolverTest — +1 unit test (8/8 PASS): throws на 0/-1.
- PricingTierRepositoryTest — +1 integration test (5/5 PASS): excludes
  inactive tiers (closes M-2 coverage gap).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 09:17:13 +03:00
Дмитрий e07d025efd feat(billing): Plan 4 Task 2 — PricingTierResolver + Repository (pure resolver + DB-обёртка)
- PricingTierResolver: pure-function, ищет tier для N-го лида (1-based).
  100→tier1, 101→tier2, 6000→tier6 (cumul.sum 1-6), 6001+→tier7 (NULL=unlimited).
  RuntimeException на пустой коллекции.
- PricingTierRepository::activeAt(Carbon): DB-обёртка, MAX(effective_from) <= $at
  per tier_no (учёт «новая сетка перекрывает старую»), is_active=true.
- 7 unit-тестов (in-memory, без БД) + 4 integration-теста (DatabaseTransactions
  с baseline-cleanup для seed-7-tiers из PricingTierSeeder Task 1).
- phpstan-baseline.neon: +3 entry (Pest TestCall::\$resolver/\$tiers/\$repo) —
  следуем project-convention (см. SupplierResolverTest идентичные baseline-entries).

Spec: docs/superpowers/specs/2026-05-11-plan4-billing-csv-admin-design.md §3.1
Plan: docs/superpowers/plans/2026-05-11-plan4-billing-csv-admin.md Task 2

Tests: 633 passed / 3 skipped / 0 failed (+11 new); pint clean; stan 0 errors above baseline.
2026-05-11 09:05:22 +03:00