- Given the executive dashboard with period This month and All branches
- When it loads
- Then every tile shows within 1.5 s p95, deltas versus last month, and clicking a tile opens the filtered list with the same period applied.
PRD 09 · Reports and dashboards
An executive dashboard across admissions, students, classes, attendance and finance with drill-downs, a library of standard reports per module, scheduled digests, and exports. Extends the existing sales dashboard and drill-down page.
Key facts, origin and limits
Drafted by an AI assistant in a single session on 10/09/2026, from the original request quoted verbatim on the hub page; the Proposed design section was added on 16/09/2026. A proposal for team discussion, not a decision of the product team.
Sources
- Public competitor research (PSE ONE, pse4.one), the
center-crm-frontendcodebase and the staging/v3OpenAPI specification (182 paths), as of 10/09/2026. - The existing / extend / new tags on this page come from a comparison with the staging
/v3specification at that date.
Limits
- Verification pending in-app survey, because automated login to the reference product was not authorised in the drafting session:
- Competitor's report list ("thống kê danh sách nhân sự / lớp / học sinh / buổi học còn lại / doanh số tư vấn / thu chi / công nợ / kho") and their column sets.
- Whether they have a dashboard with charts or only tabular reports.
- Export formats offered.
Proposed design
The overall layout is a four-row executive dashboard in the Cloud theme, role home pages that reuse the same tiles and tables, and every figure is a link to the list that produced it.







1Purpose
The owner's question is "how is the center doing this month" and the branch manager's is "what do I fix today". The existing dashboard answers the sales part (funnel, won/lost, top sales, today's tasks). This PRD adds the operational and financial picture with the same drill-down discipline: every number links to the list that produced it. Reports are lists with filters and totals, exportable; no report builder in P1.
In scope
- Executive dashboard (owner, branch manager) with period and branch filters.
- Role home pages: admissions (existing sale cards), academic admin, accountant, teacher.
- Standard reports per module (list below), each with filters, totals, drill-down, xlsx export.
- Weekly email digest to owner and branch managers.
Out of scope
- Custom report builder, BI connectors (P3).
- Forecasting.
2What exists today
| Widget | Endpoint | Keep |
|---|---|---|
| Việc tôi cần làm hôm nay: overdue tasks, due today, pending calls, closing soon, cold customers | GET /v3/crm/dashboard/sale-summary?period | yes, admissions home |
| Manager card: pipeline value, open deals, won count and amount, lost, conversion rate, avg deal | /manager-summary | yes, admissions section of executive dashboard |
| Won/lost trend, funnel, top sales (ECharts) | /won-lost-trend, /funnel, /top-sales | yes |
| Drill-down page with category map (overdue_tasks, due_today, pending_calls, closing_soon, cold_customers, pipeline_open, won_period, lost_period) | customers and interactions list endpoints | yes; pattern extended |
| Tuition stats (total, paid, unpaid, overdue counts) | /school-finance/tuitions/stats | yes |
| Teacher rollup (students, tests, completion, growth) | /v3/teacher/viewer/rollup-teachers | yes |
| Today plan widget | /me/today-plan | yes; gains attendance and finance items |
| Demo mode with fake data when tenant has zero customers | client | keep for empty tenants |
3Executive dashboard
Route /dashboard for owner and branch_manager; filters: branch (all or one), period (this week, this month, last month, this quarter, custom), compare to previous period toggle. Layout: four rows of tiles and charts; each tile shows value, delta versus previous period, and a link. Widgets load independently.
| Row | Widget | Definition | Drill-down |
|---|---|---|---|
| Money | Doanh thu lập hoá đơn | Σ invoice totals created in period (excluding void) | /finance/tuition?created |
| Thực thu | Σ valid payments in period | /finance/cashbook?type=in | |
| Công nợ quá hạn | Σ remaining on invoices past due at period end; aging mini-bars | /finance/debt | |
| Chi phí | Σ approved expenses in period | /finance/cashbook?type=out | |
| Students | Học viên đang học | count status active at period end; delta | /students?status=active |
| Nhập học mới | first enrollment start in period | /students?enrolled_from | |
| Nghỉ học | withdrawn in period; churn rate = withdrawn / active at start | /students?status=withdrawn | |
| Sắp hết buổi / hết hạn | balance ≤ 3 or expiring within 14 days | /students?low_balance | |
| Classes | Tỷ lệ lấp đầy | Σ active enrollments / Σ capacity of active classes | /classes?tab=active |
| Chuyên cần | attendance rate in period; late share | /attendance?tab=report | |
| Buổi chưa điểm danh | sessions ended > 2 h without sheet | /attendance?tab=unmarked | |
| Admissions | Khách mới | leads created in period by source (stacked bar) | /crm/customers?created |
| Chuyển đổi | conversions / leads created; trial to enrolled rate | /crm/customers?status=won | |
| Pipeline value and funnel | existing manager summary and funnel | existing drill-down | |
| Charts | Thu theo ngày | daily collected (bar) vs billed (line), period | |
| Học viên theo tháng | active, new, withdrawn per month, 12 months | ||
| Table | Theo chi nhánh | rows per branch: students, new, withdrawn, fill rate, attendance, billed, collected, overdue | row switches branch filter |
Chart rules (house dataviz): brand purple for the primary series, grey for comparison, status colours only for status meaning; no 3D, no pie for more than 5 slices; axis labels 11.5 px; tooltips list value and delta.
4Role home pages
| Role | Home content |
|---|---|
| Admissions | Existing sale cards and today plan; plus Học thử tuần này, Gọi lại quá hạn. |
| Academic admin | Today's sessions with unmarked count, waiting students by level, classes near capacity, classes ending in 14 days, parent requests open, substitute needed (sessions with teacher on leave). |
| Accountant | Today's payments, unmatched transfers, invoices pending approval, overdue by bucket, cash close status per branch, e-invoice failures. |
| Teacher | Today's sessions, unmarked sessions, my week, students needing attention (absences, low balance), FLYER assignments due (existing data). |
5Report library
| Module | Report | Rows | Key columns | Filters |
|---|---|---|---|---|
| Admissions | Nguồn khách và chuyển đổi | source × period | leads, trials, placements, converted, rate, revenue from converted | branch, period, channel |
| Admissions | Hiệu suất tư vấn | consultant | calls, talk time, trials booked, conversions, won amount | period |
| Students | Danh sách học viên | student | all profile columns, status, class, balance, debt | status, class, level, branch |
| Students | Nghỉ học và lý do | withdrawal | student, date, reason, months studied, refund | period, branch |
| Students | Sắp hết hạn | student | balance, expiry, class, payer, last reminder | threshold |
| Classes | Lấp đầy lớp | class | capacity, enrolled, waiting, fill %, sessions left, end date | branch, level |
| Classes | Sử dụng phòng | room × weekday | hours booked / available | branch, week |
| Attendance | Chuyên cần theo lớp / học viên / giáo viên | per group | marked, present, late, absent, excused, rate, unmarked | period, branch |
| Finance | Doanh thu và thực thu | day or month | billed, collected by method, refunds, net | branch, period |
| Finance | Công nợ theo tuổi nợ | student | buckets, oldest due, promise date | branch |
| Finance | Doanh thu theo khoá / gói | course, fee plan | invoices, amount, discount total, avg price | period |
| Finance | Doanh thu hoãn lại | student | unused sessions × unit price, expiry | branch |
| Finance | Sổ quỹ | entry | cash book | account, period |
| Staff | Giờ dạy giáo viên | teacher × month | sessions, hours, substitutes, pay | branch, month |
| Inventory | Tồn kho và nhập xuất | item | on hand, in, out, value | branch, period |
| Communication | Tin đã gửi | type × channel | sent, delivered, failed, cost | period |
Every report page: title, filter bar (Cloud dropdown-buttons), totals row, table with sticky header, pagination 100, buttons Xuất Excel and Lưu bộ lọc (per user, stored in view-configs). Exports run as jobs above 5,000 rows.
6User stories and acceptance criteria
- Given the Thực thu tile
- When compared to the cash book total for the same filters
- Then they are equal; the test plan includes this reconciliation for every money tile.
- Given owner and branch managers with digest enabled
- When Monday 07:30
- Then an email with last week's key numbers per branch and links is sent; the same content is available at /reports/digest.
- Given a report with 20,000 rows
- When I export
- Then a job runs, a notification delivers a signed link within 60 s, and the export is audited as a personal-data export where applicable.
7Data and API
Dashboards read from maintained daily aggregates (agg_daily_school: date, school_id, billed, collected, refunds, expenses, active_students, new_enrollments, withdrawals, sessions_held, present, late, absent, excused, unmarked, leads_new, conversions) refreshed on write and recomputed nightly. Real-time tiles (unmarked sessions, unmatched transfers, pending approvals) query live tables.
| Method | Path | Request / response | Status |
|---|---|---|---|
| GET | /v3/crm/dashboard/* | unchanged | existing |
| GET | /v3/school/dashboard/executive | school_id?, from, to, compare=true → {tiles: {key: {value, prev, delta_pct, link}}, series: {...}, by_school: [...]} | new |
| GET | /v3/school/dashboard/home?role= | role home widgets | new |
| GET | /v3/school/reports/{key} | filters per report; page, limit; format=xlsx → rows + totals or job id | new |
| GET | /v3/school/reports/jobs/{id} | status, download url | new |
| GET/PUT | /v3/crm/view-configs/{view} | saved filters per report view key | existing |
| GET/PUT | /v3/school/digest-settings | {enabled, recipients, weekday, hour} | new |
8Permissions
| Code | owner | branch_manager | accountant | academic_admin | admissions | teacher |
|---|---|---|---|---|---|---|
reports.executive | all | branch | finance section | no | no | no |
reports.admissions | yes | branch | no | no | own | no |
reports.academic | yes | branch | no | branch | no | own classes |
reports.finance | yes | branch | branch | no | no | no |
reports.export | yes | yes | finance | academic | no | no |
9Analytics events
| Event | Properties |
|---|---|
| dashboard_viewed | role, period, branch_scope, load_ms |
| tile_drilldown | tile_key |
| report_viewed | key, filters_count |
| report_exported | key, rows, job |
| digest_sent / digest_opened |
10Edge cases and open questions
- Period boundary in tenant timezone; a payment at 23:50 on the last day belongs to the month.
- Voided payments after the aggregate day closed: aggregate recomputed for that day on void.
- Branch with zero data shows zeros, not blanks; new tenants see the demo mode only on the admissions section (existing behaviour) and an onboarding checklist on the rest.
- Open: do owners want revenue recognised by service delivery (sessions held) as a second view? Proposed P2 as "Doanh thu ghi nhận".
Trường Số (truongso.net) · FLYER internal