Trường Số QA/03 Classes and scheduling
Trường Số · QA test suite · Phase 1 · 10/09/2026
03 · Classes and scheduling
Test cases for PRD 03. Every case names the fixture data it needs (see the dashboard fixtures table), numbered steps, and one observable expected result. Trace points to the user story or rule in the PRD.
Key facts, origin and limits
Drafted by an AI assistant in a single session on 10/09/2026 as part of the Trường Số QA suite, under the request quoted verbatim on the dashboard. A proposal for team review, not a sign-off.
Sources
- The Trường Số PRD set (Draft v1, 10/09/2026): user stories, screen tables, business rules and permission matrices, plus the Cloud theme reference.
Limits
- Phase 1 (authoring) only. Cases are executed in Phase 2 against the local build; results are recorded in
testcases.jsonandruns/run-1/, and every result field is stillnot_run. - Cases inherit any open question or inconsistency in the PRDs they trace to.
1Summary
P0
17
P1
20
P2
18
P3
0
| Type | functional | ui-ux | edge | negative | regression | flow | a11y | perf | security | i18n |
|---|---|---|---|---|---|---|---|---|---|---|
| Count | 33 | 4 | 7 | 5 | 0 | 0 | 1 | 1 | 3 | 1 |
2Test cases
| ID | Title | Type | Priority | Phase | Preconditions | Steps | Expected result | PRD trace | Data needed | Run 1 |
|---|---|---|---|---|---|---|---|---|---|---|
| TS-CLS-001 | Create a course with extension fields | functional | P0 | P1 | As U-ACAD-A on /settings/courses. |
| Course saved (PUT/POST to the existing course endpoint with extension fields); appears in the class form; selecting it fills level, duration 90, capacity 12, lessons 48. | CLS-01 | Fixtures below | Not run |
| TS-CLS-002 | Course validation | negative | P2 | P1 | Course form. |
| Each rejected inline; currency locked to VND. | CLS-01, 05 §11 currency VND | Fixtures below | Not run |
| TS-CLS-003 | Class form step 1 fields and auto values | functional | P0 | P1 | As U-ACAD-A on /classes/new. |
| Tên lớp auto-suggests "Movers 2 · T3/T5 18:00"; Mã lớp auto "MOV-<YYMM>-02" editable; per-weekday time-to fills 19:30 from duration 90; holidays list preloaded from tenant holidays. | CLS-02, 03 §5 form | Fixtures below | Not run |
| TS-CLS-004 | Class form validation | negative | P1 | P1 | Class form. |
| Errors: "Chọn ít nhất một ngày"; "Giờ kết thúc phải sau giờ bắt đầu"; "1–60"; "Tối đa 5"; "Tên lớp đã tồn tại"; "Chọn phòng" (unless the virtual room is chosen). | 03 §5 validation | Fixtures below | Not run |
| TS-CLS-005 | Step 2 preview lists generated sessions and conflicts | functional | P0 | P1 | Step 1 completed with 48 sessions. |
| Preview shows 48 rows with seq, date, time, room, teacher; holidays skipped and the end date extended accordingly; button label exactly "Tạo lớp và 48 buổi"; dry_run=true request seen in the network log. | CLS-02, 03 §8 dry_run | Fixtures below | Not run |
| TS-CLS-006 | Create class generates sessions and appears in the list | functional | P0 | P1 | Preview shown. |
| Redirect to /classes/:id; tab Buổi học has 48 rows numbered 1..48; /classes tab Sắp khai giảng lists it with status Sắp mở; a ClassSchedule is created only when a FLYER program was chosen. | CLS-02 | Fixtures below | Not run |
| TS-CLS-007 | Pattern with two sessions on the same weekday | edge | P2 | P1 | Class form. |
| Both rows accepted; preview shows two sessions per Saturday. | 03 §11 | Fixtures below | Not run |
| TS-CLS-008 | Class spanning Tết skips holidays and extends end date | edge | P1 | P1 | Tenant holidays include a 7-day Tết block within the class range. |
| No sessions on holiday dates; end date extends; preview footer shows "Kết thúc dự kiến: <date>". | 03 §11 Tết | Fixtures below | Not run |
| TS-CLS-009 | Session generation performance | perf | P2 | P1 | Class with 200 sessions. |
| Preview and creation each complete in ≤ 2 s. | 12 §2 timetable generation | Fixtures below | Not run |
| TS-CLS-010 | Room conflict shown inline with override for permitted roles | functional | P0 | P1 | C1 uses P.201 T3/T5 18:00–19:30. |
| Preview rows carry a red chip "Trùng phòng: Movers 2A 18:00–19:30"; U-ACAD-A has no "Vẫn lưu" (no classes.override_conflict) and cannot submit; U-BM-A sees "Vẫn lưu" and can create; API returns 409 CONFLICT with conflicts[] until override_conflict=true. | CLS-03 | Fixtures below | Not run |
| TS-CLS-011 | Teacher conflict is checked across branches | functional | P0 | P1 | T1 teaches C3 at branch B T2/T4 17:00–18:30. |
| Conflict chip "Trùng giáo viên: Movers 1C (Thủ Đức)"; 409 CONFLICT. | CLS-03, 03 §6 teacher conflict any branch | Fixtures below | Not run |
| TS-CLS-012 | Buffer between sessions tenant setting | functional | P2 | P1 | Set buffer 15 min in settings. |
| Conflict reported; with buffer 0 no conflict. | 03 §6 buffer | Fixtures below | Not run |
| TS-CLS-013 | Cancelled sessions do not conflict | edge | P2 | P1 | A cancelled C1 session on date D. |
| No conflict. | 03 §6 both not cancelled | Fixtures below | Not run |
| TS-CLS-014 | Edit one session marks it adjusted | functional | P0 | P1 | C1 planned session next week. |
| Only that row changes; chip "Đã điều chỉnh"; other sessions untouched; guardians of enrolled students receive a schedule_change message if the notification policy is enabled (status Chờ duyệt template → fallback push/email). | CLS-04 | Fixtures below | Not run |
| TS-CLS-015 | Apply to following regenerates future planned sessions only | functional | P0 | P1 | C1 with 20 held sessions. |
| All future planned sessions move to 18:30; the 20 held sessions unchanged; numbering preserved by date order; audit entry. | CLS-04, 03 §6 regeneration | Fixtures below | Not run |
| TS-CLS-016 | Session edit conflict on save | negative | P1 | P1 | Another class occupies P.202 at the target time. |
| 409 CONFLICT inline list; Vẫn lưu only for override roles. | CLS-03 | Fixtures below | Not run |
| TS-CLS-017 | Concurrent session edit returns STALE | edge | P1 | P1 | Two admins open the same session drawer. |
| Admin 2 receives 409 STALE and a toast "Buổi học đã được thay đổi, tải lại"; no silent overwrite. | 03 §11 optimistic concurrency | Fixtures below | Not run |
| TS-CLS-018 | Cancel a session with make-up appended | functional | P0 | P1 | C1 planned session 3 days ahead. |
| Status Đã huỷ; a new session appended after the last one with chip Học bù (is_makeup) at the same weekday/time; no package sessions consumed; guardians receive session_cancelled; total non-cancelled count stays 48. | CLS-05 | Fixtures below | Not run |
| TS-CLS-019 | Late cancellation within 24 h marks cancelled_late | functional | P1 | P1 | Session starting in 10 hours. |
| Status cancelled_late (chip "Huỷ muộn"); visible for PRD 06 pay rules; no make-up added. | CLS-05, 03 §6 threshold | Fixtures below | Not run |
| TS-CLS-020 | Cancelling a session with a saved sheet is blocked | negative | P1 | P1 | SES-PAST (sheet saved). |
| Blocked with "Xoá phiếu điểm danh trước" (admin) and the delete action requires attendance.delete_sheet. | 04 §5 rule 8 | Fixtures below | Not run |
| TS-CLS-021 | Assign a substitute | functional | P0 | P1 | SES-TODAY. |
| Session row shows T1 (main) and T2 (dạy thay); T2 sees the session in /teach/today and can open the sheet; T1 still sees it with a substitute marker. | CLS-06 | Fixtures below | Not run |
| TS-CLS-022 | Teacher can only request a substitute | security | P1 | P1 | As U-TEACH on SES-TODAY. |
| UI offers "Yêu cầu dạy thay" (creates a request/notification) but no direct assignment; PATCH returns 403. | 03 §9 sessions.manage teacher request only | Fixtures below | Not run |
| TS-CLS-023 | Add student to class up to capacity then waiting list | functional | P0 | P1 | C1 11/12; S3 Waiting; another Waiting student S10. |
| After S3: 12/12, class chip Đầy, list tab Đầy includes C1. S10: dialog 409 CLASS_FULL offers waiting list; S10 appears in the Danh sách chờ section with position 1. | CLS-07 | Fixtures below | Not run |
| TS-CLS-024 | Roster table columns and level-match hint | functional | P1 | P1 | C1 tab Học viên. |
| Columns: name, guardian phone, start date, status, sessions attended/total, balance, flags (Cần lưu ý); actions Chuyển lớp, Kết thúc, Gửi tin; the add dialog searches branch students and shows a level match chip (Movers → "Phù hợp"). | 03 §5 Học viên tab | Fixtures below | Not run |
| TS-CLS-025 | Transfer class ends and starts on the same day | functional | P0 | P1 | S1 in C1; C4 has seats. |
| C1 enrollment ends today; C4 enrollment starts today; S1 on today's C1 roster (end ≥ date) and on C4 rosters from today; Lớp & lịch sử shows both rows. | CLS-07 transfer, 04 §10 transferred out on the date | Fixtures below | Not run |
| TS-CLS-026 | Ending an enrollment early asks for reason | functional | P1 | P1 | S6 in C1. |
| Reason dialog required; S6 with no other enrollment becomes Đã nghỉ per lifecycle; enrollment status ended with end_reason. | CLS-07, 02 §3 | Fixtures below | Not run |
| TS-CLS-027 | Capacity counts trials and make-ups per session | edge | P1 | P1 | C1 12/12 with a make-up booking on session X. |
| Roster shows 12 enrolled + 1 Học bù; trial seats counted separately ("Học thử 1/2"); attendance sheet lists all 13. | 03 §6 capacity | Fixtures below | Not run |
| TS-CLS-028 | Waiting list promotion when a seat frees | functional | P2 | P1 | C1 full with S10 waiting. |
| Admin gets a prompt/notification "Có chỗ trống: Movers 2A · Danh sách chờ: Trần S10"; S10 is not auto-enrolled. | 03 §5 waiting list section | Fixtures below | Not run |
| TS-CLS-029 | Book a make-up into another class of the same level | functional | P0 | P1 | S1 has an excused absence on SES-PAST; tenant allow make-up; class C2 same level with a free seat next week. |
| makeup_booking created; C2 session roster shows S1 with chip Học bù; attending does not consume a package session when policy says so; S1 absences table shows "Đã đặt học bù". | CLS-08 | Fixtures below | Not run |
| TS-CLS-030 | Make-up as a one-off session | functional | P1 | P1 | Same as above. |
| A one-off session (is_makeup) is created with conflict check; booking created. | CLS-08, 03 §8 POST sessions one-off | Fixtures below | Not run |
| TS-CLS-031 | Make-up blocked when policy disallows | negative | P2 | P1 | Tenant allow_makeup false or class allow_makeup false. |
| Button hidden; API 409 or 403 with message. | CLS-08 Given policy | Fixtures below | Not run |
| TS-CLS-032 | Timetable week grid by room | functional | P0 | P1 | As U-ACAD-A, /timetable?view=room&week=<this week>. |
| Columns P.201, P.202, Trực tuyến; rows 07:00–22:00 in 30-min steps; C1 block on Tue/Thu 18:00–19:30 with class name, T1, "11/12"; block colour by level; clicking opens the session drawer. | CLS-09 | Fixtures below | Not run |
| TS-CLS-033 | Timetable views by teacher and by class, date navigation | functional | P1 | P1 | Timetable. |
| Columns change to teachers (T1, T2...) then classes; URL week param updates (2026-W38 etc.); filters branch and level apply. | CLS-09 | Fixtures below | Not run |
| TS-CLS-034 | Drag a block to move with conflict check on drop | functional | P1 | P1 | Desktop timetable. |
| First drop asks for confirmation and updates the session (marked adjusted); second drop shows the conflict and reverts unless overridden. | 03 §5 timetable drag | Fixtures below | Not run |
| TS-CLS-035 | Print produces A4 landscape per room | ui-ux | P2 | P1 | Timetable by room. |
| One A4 landscape page per room with header (branch, week), grid legible; no sidebar or top bar printed. | CLS-09 print | Fixtures below | Not run |
| TS-CLS-036 | iCal export for teacher view is a signed link | security | P2 | P1 | Timetable by teacher. |
| Valid URL returns text/calendar with the sessions; tampered URL returns 401/403; the link can be revoked from the staff profile. | 03 §8 timetable.ics signed, test seed 03 | Fixtures below | Not run |
| TS-CLS-037 | Timetable day view on mobile | ui-ux | P2 | P1 | 390 px. |
| A day view (not the week grid) with a date stepper; blocks tappable; no horizontal scroll. | 03 §5 day view mobile | Fixtures below | Not run |
| TS-CLS-038 | Teacher timetable scope | security | P1 | P1 | As U-TEACH. |
| Only T1's sessions (C1 and C3) appear; view switcher limited to own view; other teachers not listed. | 03 §9 timetable.view own | Fixtures below | Not run |
| TS-CLS-039 | Close a class | functional | P0 | P1 | C1 as U-ACAD-A; S1 has only the C1 enrollment. |
| Class status Đã kết thúc; enrollments ended; S1 status Hoàn thành; /classes tab Đã kết thúc lists C1; planned future sessions cancelled or removed; no attendance sheets deleted. | CLS-10 | Fixtures below | Not run |
| TS-CLS-040 | Class auto-completes after the last session is held | functional | P2 | P1 | A class whose last session is marked today. |
| Class status becomes completed automatically (or on the nightly job); students with no other enrollment become Hoàn thành. | CLS-10 Given last session held | Fixtures below | Not run |
| TS-CLS-041 | Class list tabs, columns and status chips | functional | P0 | P1 | As U-OWNER, branch A. |
| Tabs Đang học · Sắp khai giảng · Đầy · Đã kết thúc · Tất cả; columns Mã lớp, Tên lớp (link + level chip), Lịch ("T3, T5 · 18:00–19:30"), Phòng, Giáo viên (avatar + name), Sĩ số ("11/12" with bar; C2 "12/12" red with "Chờ: 1"), Tiến độ ("20/48"), Khai giảng · Kết thúc, Trạng thái chips Sắp mở (blue) / Đang học (green) / Đầy (yellow) / Đã kết thúc (grey), Thao tác Xem lịch · Thêm học viên · Điểm danh hôm nay. | 03 §5 class list | Fixtures below | Not run |
| TS-CLS-042 | Class list filters | functional | P1 | P1 | /classes. |
| Only C1 remains (C2 has no seats); clearing restores. | 03 §5 filters | Fixtures below | Not run |
| TS-CLS-043 | Class list empty state | ui-ux | P1 | P1 | Tenant EMPTY. |
| Exactly "Chưa có lớp. Tạo khoá học trước, rồi mở lớp từ khoá học." with buttons + Tạo lớp and a link to courses. | 03 §5 empty | Fixtures below | Not run |
| TS-CLS-044 | Class detail header and right rail per Cloud lop-hoc frame | ui-ux | P1 | P1 | C1. |
| Breadcrumb; name; subtitle "T3 & T5, 18:00 · 11 học viên · Movers"; buttons Sửa · Giao bài · kebab (Nhân bản lớp, Kết thúc lớp); tabs Tổng quan · Học viên · Buổi học · Điểm danh · Bài tập · Học phí · Cài đặt; right rail Thông tin lớp with code + copy icon, teacher, room, capacity, course, program, fill rate bar, next session. | 03 §5 class detail | Fixtures below | Not run |
| TS-CLS-045 | Buổi học tab toolbar and per-row actions | functional | P1 | P1 | C1. |
| Toolbar Tạo buổi, Tạo lại lịch, Nghỉ lễ; columns No., date, time, room, teacher, substitute, status, attendance marked, note; row actions edit, cancel, substitute; held rows are not editable for date/time. | 03 §5 Buổi học | Fixtures below | Not run |
| TS-CLS-046 | Regenerate never touches held or cancelled sessions | functional | P0 | P1 | C1 with 20 held, 1 cancelled. |
| Held and cancelled rows identical before/after (ids and timestamps); planned rows regenerated; numbering recalculated among non-cancelled by date. | 03 §6 rules 1–2 | Fixtures below | Not run |
| TS-CLS-047 | Nhân bản lớp clones settings without students | functional | P2 | P1 | C1. |
| Class form opens prefilled with course, pattern, room, teacher, capacity; name suffix changed; no enrollments copied. | 03 §5 kebab | Fixtures below | Not run |
| TS-CLS-048 | Rooms settings: unique per branch, deactivate blocked with future sessions | functional | P1 | P1 | As U-ACAD-A on /settings/rooms. |
| Duplicate rejected "Tên phòng đã tồn tại"; deactivating P.201 blocked with "Còn N buổi học sắp tới, chuyển phòng trước"; P.203 created then deactivated successfully. | 03 §5 rooms, 03 §11 room deactivated | Fixtures below | Not run |
| TS-CLS-049 | Virtual room "Trực tuyến" allowed for online classes | functional | P2 | P1 | Class form. |
| Class saves; no room conflicts computed for the virtual room (or conflicts only for teacher). | 03 §12 open question proposed | Fixtures below | Not run |
| TS-CLS-050 | Levels catalog with score bands drives placement suggestion | functional | P1 | P1 | As U-OWNER /settings/levels. |
| Seeded: Pre-A1, A1, A2, B1, B2, C1 and Starters, Movers, Flyers, KET, PET with bands; after edit, a placement result of 72 suggests Movers. | 03 §6 level mapping | Fixtures below | Not run |
| TS-CLS-051 | Teacher removed from branch with future sessions | edge | P2 | P1 | T2 assigned to future sessions; remove T2 from branch A. |
| A list of affected sessions is shown for reassignment; sessions keep T2 until changed. | 03 §11 | Fixtures below | Not run |
| TS-CLS-052 | Holiday list management | functional | P2 | P1 | /settings/tenant holidays. |
| Holiday preloaded in Ngày nghỉ; new classes skip it; existing planned sessions are not auto-moved (admin uses Nghỉ lễ tool). | 03 §8 holidays | Fixtures below | Not run |
| TS-CLS-053 | Timezone at month boundary | edge | P2 | P1 | Session on the 30th at 23:00 local. |
| Displayed on the 30th; API returns timestamptz with +07:00; not shifted to the next day. | 03 §11 time zone, 06 §11 month boundary | Fixtures below | Not run |
| TS-CLS-054 | Class pages in en locale | i18n | P2 | P1 | en locale. |
| Tabs and chips translated (Open, Full, Ended, Upcoming); schedule text "Tue, Thu · 18:00–19:30". | 12 §8 | Fixtures below | Not run |
| TS-CLS-055 | Class form keyboard navigation and focus | a11y | P2 | P1 | Class form. |
| Chips toggle with Space; all fields reachable; error text linked via aria-describedby. | 12 §9 | Fixtures below | Not run |
Trường Số (truongso.net) · FLYER internal