- Created checklist for task 11: Package and Credit Ledger - Created checklist for task 12: Treatment Course - Created checklist for task 13: Cancellation Policy, No-Show, and Waitlist - Created checklist for task 14: Domain Events and Utilization Reports
7.2 KiB
7.2 KiB
چکلیست — تسک ۱۴ (رویدادهای دامنه و گزارش بهرهوری)
وضعیت کلی: ⏳ شروع نشده · آخرین بازبینی: —
قواعد: _shared/definition-of-done.md · red-lines.md · ui-conventions.md
۰. خط سرخ
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۰.۱ | --group=slot-mode-frozen سبز |
⏳ | |
| ۰.۲ | AppointmentEvent موجود دستنخورده |
⏳ | تاریخچهٔ وضعیت ≠ رویداد دامنه |
| ۰.۳ | پیامکهای موجود (Sms domain) نشکستند |
⏳ | |
| ۰.۴ | گزارش با داده حدسی ساخته نشد | ⏳ | ⭐ بند ۱.۹ |
۱. بکاند — رویدادها
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۱.۱ | DomainEvent پایه + DomainEventPublisher + DomainEventLog |
⏳ | |
| ۱.۲ | payload فقط uuid و اسکالر — هیچ entity | ⏳ | ⭐ |
| ۱.۳ | هر رویداد entityType/entityId دارد |
⏳ | وگرنه پیامک محیط اشتباه |
| ۱.۴ | الگوی outbox: record() داخل تراکنش کاری، فقط persist |
⏳ | ⭐ |
| ۱.۵ | PublishDomainEventHandler + scheduler هر ۱۰ ثانیه |
⏳ | |
| ۱.۶ | attempts < 5؛ ردیف شکستخورده حذف نمیشود |
⏳ | |
| ۱.۷ | همهٔ dispatch های تسکهای ۰۷ تا ۱۳ به record() تغییر کردند |
⏳ | ⭐ |
| ۱.۸ | چهارده رویداد بند ۱۶ مستند ثبت شدند | ⏳ | |
| ۱.۹ | idempotency در مصرفکننده، با domain_events.uuid |
⏳ | at-least-once |
| ۱.۱۰ | worker با loop-wrap برای Coolify | ⏳ | کانتینر خارج نشود |
| ۱.۱۱ | app:events:prune --older-than=180d |
⏳ | |
| ۱.۱۲ | GET /domain-events فقط ROLE_ADMIN |
⏳ |
۲. بکاند — گزارشها
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۲.۱ | ResourceUtilizationReporter با چهار عدد |
⏳ | |
| ۲.۲ | available_minutes × capacity منبع |
⏳ | ⭐ اتاق سهتخته سه برابر |
| ۲.۳ | passive در occupied هست، در active نه |
⏳ | |
| ۲.۴ | setup/cleanup در occupied هست |
⏳ | |
| ۲.۵ | released شمرده نمیشود (status='booked' فقط) |
⏳ | |
| ۲.۶ | available = 0 → utilization = null، نه صفر |
⏳ | ⭐ معنای متفاوت |
| ۲.۷ | مرز بازه: start_at >= from AND start_at < to |
⏳ | نه end_at <= to |
| ۲.۸ | کوئری تجمعی با GROUP BY، بدون پیمایش |
⏳ | |
| ۲.۹ | پیش از پیادهسازی plan-accuracy: وجود patient_sessions.started_at/ended_at تأیید شد |
⏳ | ⭐ اگر نبود → تسک جدا، نه داده حدسی |
| ۲.۱۰ | PlanAccuracyReporter با آستانههای شدت |
⏳ | |
| ۲.۱۱ | انحراف منفی بزرگ هم high است |
⏳ | نصف ظرفیت هدر میرود |
| ۲.۱۲ | حداقل نمونه ۱۰، وگرنه insufficient_data |
⏳ | |
| ۲.۱۳ | بازه > ۹۰ روز → ۴۲۲ | ⏳ | |
| ۲.۱۴ | سه endpoint | ⏳ |
۳. دیتابیس
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۳.۱ | domain_events (BIGINT id) با سه ایندکس |
⏳ | |
| ۳.۲ | idx_de_pending (published_at, occurred_at) |
⏳ | کوئری worker |
| ۳.۳ | هیچ جدول دیگری تغییر نکرد | ⏳ | |
| ۳.۴ | TenantSchemaCoverageTest سبز |
⏳ |
۴. UI
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۴.۱ | ResourceUtilizationPage — جدول + نمودار Recharts |
⏳ | کتابخانهٔ موجود |
| ۴.۲ | PlanAccuracyPage — جدول انحراف با شدت |
⏳ | |
| ۴.۳ | ردیفهای active_ratio < 0.3 نشان هشدار دارند |
⏳ | |
| ۴.۴ | tooltip توضیح active_ratio در خودِ UI |
⏳ | ⭐ نه فقط در مستندات |
| ۴.۵ | utilization = null → — با tooltip «تقویم تعریف نشده» + لینک تنظیم |
⏳ | |
| ۴.۶ | لینک «ویرایش بخشهای این سرویس» از PlanAccuracyPage |
⏳ | ⭐ گزارشی که راه اصلاح ندهد خوانده نمیشود |
| ۴.۷ | بازهٔ زمانی با PersianDatePicker |
⏳ | |
| ۴.۸ | وضعیت (بازه، فیلتر) در URL با useUrlState |
⏳ | |
| ۴.۹ | DataTable با skeleton و empty state |
⏳ | |
| ۴.۱۰ | رنگ نمودار از توکنهای --stat-*، نه پالت پیشفرض Recharts |
⏳ | ⭐ |
| ۴.۱۱ | هیچ رنگ/شعاع hard-code | ⏳ | |
| ۴.۱۲ | دارکمود — نمودار هم در دارک خوانا است | ⏳ | ⭐ محور و legend |
| ۴.۱۳ | حالت فشرده | ⏳ | |
| ۴.۱۴ | RTL و موبایل — جدول و نمودار اسکرول افقی داخلی | ⏳ | |
| ۴.۱۵ | همهٔ رشتهها فارسی · اعداد با formatNumber |
⏳ | |
| ۴.۱۶ | backTo روی صفحات گزارش |
⏳ |
۵. تست
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۵.۱ | OutboxTest — record داخل تراکنش، rollback، انتشار، شکست، سقف تلاش |
⏳ | ⭐ |
| ۵.۲ | EventPayloadTest — reflection روی همهٔ زیرکلاسها: فقط اسکالر |
⏳ | |
| ۵.۳ | ResourceUtilizationTest — شش سنجهٔ سند |
⏳ | ⭐ شامل capacity و null |
| ۵.۴ | PlanAccuracyTest — انحراف دوطرفه، نمونهٔ کم |
⏳ | |
| ۵.۵ | ReportAuthTest — منشی ۴۰۳، بازه ۴۲۲ |
⏳ | |
| ۵.۶ | ReportQueryCountTest — تعداد کوئری مستقل از تعداد منبع |
⏳ |
۶. مستندات
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۶.۱ | docs/api/reports.md — معنی هر عدد + جدول active_ratio |
⏳ | |
| ۶.۲ | docs/architecture/domain-events.md — قرارداد، فهرست، outbox، idempotency |
⏳ | |
| ۶.۳ | جدول تفاوت AppointmentEvent با DomainEventLog |
⏳ | ⭐ وگرنه یکی حذف میشود |
۷. بازبینی پایانی
| # | مورد | وضعیت | یادداشت |
|---|---|---|---|
| ۷.۱ | هیچ 🔄 و ⏳ بیدلیل نمانده | ⏳ | |
| ۷.۲ | bin/phpunit کامل سبز |
⏳ | |
| ۷.۳ | --group=slot-mode-frozen سبز |
⏳ | |
| ۷.۴ | phpstan بدون خطای جدید |
⏳ | |
| ۷.۵ | npx tsc --noEmit و yarn test سبز |
⏳ | |
| ۷.۶ | تستهای tenant سبز | ⏳ | |
| ۷.۷ | docs/api/* بهروز |
⏳ | |
| ۷.۸ | چکلیست UI کامل | ⏳ | |
| ۷.۹ | پیامکهای موجود سرتاسر تست شدند (outbox نشکستشان) | ⏳ | ⭐ |
| ۷.۱۰ | دو کلاینت دیگر بررسی شدند | ⏳ | |
| ۷.۱۱ | commit، سپس graphify update . |
⏳ | |
| ۷.۱۲ | موارد بهتعویق با دلیل و تسک مقصد | ⏳ | plan-accuracy اگر داده نبود |