---
url: https://docs.nemo12.com/intake/src-0400-0424.md
description: >-
  Sổ tiếp nhận nguồn yêu cầu SRC-0400 tới SRC-0424: mỗi dòng một nguồn, ngày
  nhận, tài liệu canonical đã ghi và trạng thái.
---

# Sổ nguồn SRC-0400 tới SRC-0424

Một mảnh của [sổ tiếp nhận](../intake.md). Chỉ CHÈN dòng bằng `node scripts/src-new.mjs`, không ghi đè cả file.

| ID | Ngày nhận | Nguồn | Canonical hóa vào | Trạng thái |
| --- | --- | --- | --- | --- |
| SRC-400 | 2026-08-19 | Tự kiểm sau khi nạp 39 lab (chủ dự án: "trình tự làm thì bạn quyết") | Mở thử một lab mới bằng test giao diện thì lộ lỗi nội dung của chính đợt trước: **20/39 lab đánh nhãn nút là "Lựa chọn 1", "Bước 2", "Phản ứng 3"** — learner bấm mù, đúng lỗi từng làm hỏng `ib-shopping-and-change` ở SRC-390. Nguyên nhân: nội dung thật bị đẩy hết vào `show` (phần chỉ lộ ra SAU khi bấm), còn `label` thì đánh số. Viết lại nhãn cho cả 20 lab: nhãn nói ra LỰA CHỌN hoặc BƯỚC bằng lời learner đọc được, `show` giữ phần hé lộ, `note` giữ câu rút ra. Thêm test e2e lấy **nguyên văn một lab thật từ D1** làm fixture — 39 lab này vào production dưới dạng dữ liệu chứ không qua bundle, nên trước bản này khuôn lệch một chữ là learner thấy màn trắng mà không test nào đỏ; test giữ luôn luật "không có nhãn đánh số" | ✅ |
| SRC-401 | 2026-08-19 | Chỉ đạo: "làm nốt cho môn Tiếng Việt, và môn tiếng Anh" (sau khi rà soát SRC-394 mở rộng ra cả 11 môn) | Rà soát cho thấy hai môn này trống hệt môn Toán trước SRC-396: **0 cạnh prerequisite, 96/96 node Tiếng Anh và 213/213 node Ngữ văn thiếu ba câu "vì sao", thiếu cả can_do** — tức hé cửa, bậc "đang hổng" của hàng chờ, câu "đang chặn N bài sau" và cả hai popover đều câm. Soạn tay theo quan hệ ngữ nghĩa (không sinh theo thứ tự bày, lý do đã ghi ở SRC-396): **Tiếng Anh 81 unit → 128 cạnh**, **Ngữ văn cây V1-V5 126 unit → 145 cạnh**, cả hai môn nay 0 node thiếu why/can_do. Điểm riêng của Tiếng Anh: 12 unit nằm trong HAI module (bài mở đầu dùng chung của hai nhánh) nên mỗi unit có hai khoá `unit_prereqs`, cạnh phải nhân ra cho cả hai. **Phát hiện cần chủ dự án quyết:** Ngữ văn đang có HAI cây song song — V1-V5 (kiểu B21, lớp 1-9) và DH/LV/TV (kiểu cũ, lớp 6-9), đúng tình trạng môn Toán trước SRC-299 nhưng cây cũ CHƯA được tạm ẩn, nên learner đang thấy cùng một nội dung bày hai lần theo hai cách sắp xếp. Chỉ soạn cho cây V1-V5 mà learner thật sự đi | ✅ |
| SRC-402 | 2026-08-19 | Tiếp chỉ đạo "làm nốt cho môn Tiếng Việt" | **320 câu soạn tay cho 32 Unit Ngữ văn chưa có câu nào** — không còn Unit ngõ cụt trong cây V1-V5. Đây không phải kho mỏng mà là ngõ cụt thật: learner bấm vào một trong 32 Unit ấy thì API trả "Bài này chưa có câu hỏi để luyện", tức là một phần tư đường học của môn Văn dẫn tới màn báo lỗi. Phần lớn 32 Unit này dạy đọc phản biện và siêu nhận thức (biết mình đang không hiểu, ai viết và họ được lợi gì, chỗ nào bài viết bỏ trống), nên câu hỏi ra theo tình huống chứ không theo định nghĩa. Vẫn soạn tay theo bài học SRC-046, mỗi câu kèm `misconception` mô tả hiểu lầm dẫn tới đáp án sai | ✅ |
| SRC-403 | 2026-08-19 | Tiếp chỉ đạo "làm nốt cho môn Tiếng Việt" | **216 câu soạn tay cho 53 Unit Ngữ văn còn ở mức 6 câu** — cây V1-V5 nay 0/126 Unit dưới 10 câu, ngang với môn Toán sau SRC-398. Sáu câu không chặn đường học (SRC-377 cho chạy với số câu sẵn có) nhưng bài đo mỏng thì qua hay trượt đều ít nói lên điều gì, mà chính con số ấy lại đi thẳng vào Learner Model và Readiness. Câu mới rải vào node ít câu nhất của Unit, vị trí đáp án đúng xoay theo chỉ số câu | ✅ |
| SRC-404 | 2026-08-19 | Chỉ đạo trên bảng learner của admin: "Đổi tên cột Name thành Learner, còn thêm cột Parents, cần điền tên bố mẹ vào, và bên dưới tên bố mẹ là email của bố mẹ" | Bảng trước đây chỉ có tên trẻ con, nên mọi việc vận hành thật (gọi điện, gửi báo cáo, hỏi vì sao em nghỉ hai tuần) đều phải mở D1 lên tra tay. Cột **Parents** lấy hợp của HAI nguồn, thiếu một nguồn là mất người: `family_members` role owner · guardian (người mở tài khoản gia đình lúc đăng ký) và `guardians(learner_id)` (người lớn nhận lời mời cho đúng một em — bố mẹ ly thân, ông bà đỡ một cháu, có thể không nằm trong family). `supporter` cố ý KHÔNG tính là phụ huynh: đó là người hỗ trợ xem được dữ liệu chứ không phải người chịu trách nhiệm, gộp vào thì cột này thôi trả lời được câu "gọi cho ai"; chính learner cũng bị loại vì em cũng là một dòng `family_members`. Email hiện nguyên văn ngay dưới tên và bấm được ra mail — cột này tồn tại để LIÊN LẠC, cắt gọn bằng "…" thì lại phải tra chỗ khác. Một câu SQL cho cả trang (`json_group_array`) chứ không phải 1 + 100 lượt đi D1 | ✅ |
| SRC-405 | 2026-08-19 | Chủ dự án gửi ảnh màn "Chưa mở lúc này — Có lỗi xảy ra, vui lòng thử lại" khi vào một bài đo: "Sao lại lỗi nhỉ?" | **Lỗi do chính SRC-396 gây ra, đã live khoảng 4 tiếng.** SRC-396 thêm bước ghi `status='started'` lúc mở bài, nhưng bảng `learner_experience_state` (migration 0028) có `CHECK (status IN ('completed','failed'))`. Câu INSERT vi phạm ràng buộc và ném lỗi, mà nó nằm THẲNG trong đường khởi động bài (sau khi phiên đã tạo), nên mọi lần vào học từ Đường học có kèm `unit_key` + `exp_key` đều trả 500. Sửa hai lớp: migration 0056 dựng lại bảng với `CHECK (status IN ('started','completed','failed'))` (SQLite không sửa CHECK tại chỗ) — riêng migration này đã gỡ lỗi ngay trên production, không cần deploy; và bọc phép ghi ấy trong try/catch, vì nó là ghi sổ PHỤ còn việc chính của endpoint là mở bài, đúng lối đã dùng cho retention ở SRC-065. Kiểm chứng end-to-end trên production bằng phiên tạm: HTTP 201, trả 6 câu, và dòng `started` được ghi. **Bài học:** đặt một phép ghi phụ vào đường đi chính mà không có lưới đỡ; và migration cũ có CHECK liệt kê giá trị thì thêm giá trị mới phải sửa schema, không chỉ sửa code. Test mới đọc thẳng file migration để giữ luật này | ✅ |
| SRC-406 | 2026-08-20 | Chỉ đạo sau sự cố SRC-405: "rà soát toàn bộ các lỗi tiềm năng, audit. Rồi fix hết chúng đi" | Rà bảy mặt trận, mỗi mặt bằng bằng chứng chứ không bằng suy đoán. **Sửa được ba lỗi thật:** (1) câu `vn2-dau-hoi-va-dau-nga-1` có HAI lựa chọn giống hệt nhau nên learner không phân biệt được hai ô, bấm ô nào cũng có thể bị ghi là sai; (2) câu `b21f-make-a-table-...-t03` gần trùng khít câu `-04` cùng node (đáp án đúng chỉ khác một chữ), hai câu ấy có thể rơi vào cùng một lượt luyện; (3) lab `evolution` (Sinh học, đang live) không có `viz`, không có `observe`, không có node để mượn widget — learner mở ra mất trọn chặng đoán trước và quan sát, đúng hạng lỗi của lab `functions` ở SRC-396. **Kiểm mà KHÔNG thấy lỗi** (ghi lại để lần sau khỏi rà lại): 58 endpoint GET không endpoint nào 5xx; trọn vòng đời buổi học chạy thật trên production bằng learner tạm (mở bài, trả lời, hoàn thành, đo cả unit, học vượt) rồi xoá sạch; 42 route riêng tư gọi không kèm phiên đều bị chặn đúng; learner A gọi 14 endpoint của learner B đều bị chặn; 0 lệch giữa giá trị chữ trong code và CHECK của schema; 0 tham chiếu mồ côi ở learner_skill_state/evidence/retention/skill_edges; 0 số liệu ngoài khoảng; 8 trang chính không có lỗi console. **Ghi nhận, chưa xử lý:** 324 item trỏ 21 node lớp 8-9 đã bị gỡ khỏi cây — mọi node còn lại đều đã đủ câu, nên đám này chỉ là học liệu treo; KHÔNG xoá vì xoá học liệu là việc không hoàn lại được. Đóng gói phép kiểm thành `scripts/audit-data.mjs` chạy lại được, và thêm 8 e2e bắt lỗi console | ✅ |
| SRC-407 | 2026-08-20 | Chỉ đạo: "làm nốt môn tiếng Anh và Tiếng Việt đi" (lab còn thiếu) | 64 lab cho toàn bộ Unit Tiếng Anh chưa có lab, theo khuôn picker của SRC-388/390. Soạn xong thì chỉ đạo tiếp ở SRC-408 cho thấy chúng đang gắn vào cây CŨ, nên chúng được chuyển sang cây Pearl cùng với câu hỏi ở SRC-408 | ✅ |
| SRC-408 | 2026-08-20 | Chỉ đạo kèm hai ảnh (Dashboard môn Anh và trang Pearl Curriculum): "có vẻ như lệch hết cả rồi. Đúng ra là cần tạo hệ thống Package, Modules, Units theo Pearl.nemo12.com chứ nhỉ" | **Đúng, và đây là lệch gốc.** D1 giữ cây Tiếng Anh CŨ chia theo KỸ NĂNG NHÀ TRƯỜNG (4 Package: Từ vựng · Ngữ pháp · Đọc hiểu · Viết, 81 Unit), trong khi Pearl đã chốt cây chia theo NĂNG LỰC kiểu Building 21 (5 Package: Listen & Decode · Build Language · Read & Interpret · Speak & Write · Use English in the World, 19 module, 64 Unit). Toán (B1-B5) và Ngữ văn (V1-V5) đều đã theo cây mới; chỉ Tiếng Anh còn sót. Dựng lại cây bằng cách **đọc thẳng file Pearl** (`apps/pearl/content/curriculum/tieng-anh/`) chứ không soạn tay lại: câu "I will be able to", ba bậc Đang hình thành/Đạt/Vững, bằng chứng đạt và hiểu lầm thường gặp đều lấy nguyên từ tài liệu, nên hai nơi không thể lệch — tài liệu là nguồn, DB là bản sao thi hành. Một Unit đúng MỘT node (chốt ở SRC-396). Chuyển **970 câu hỏi và 92 lab** sang cây mới theo bảng ánh xạ soạn tay 81→28 Unit; cây cũ còn 0 câu và được tạm ẩn như DS/HH/SH của Toán. Lab vướng UNIQUE index PHẦN (một lab live mỗi Unit) nên mỗi Unit mới giữ một lab chính, 63 lab còn lại bỏ trống cột `unit` để vẫn nằm trong Thư viện Lab thay vì bị xoá. Cố ý KHÔNG gán câu hỏi vào Package 1 Listen & Decode: cây cũ không có một câu nghe nào, gán bừa câu ngữ pháp vào đó là nói dối về việc learner đã đo cái gì. **Còn lại: 36/64 Unit chưa có câu hỏi nào** (trọn Package Nghe, cùng các Unit về tự sửa lỗi, nói, lịch sự, dùng tiếng Anh thật) và prerequisite graph môn Anh phải soạn lại cho cây mới | ✅ |
| SRC-409 | 2026-08-20 | Chỉ đạo: "làm nốt toàn bộ content của cả Lý Hoá Sinh, đều lấy nguồn từ pearl.nemo12.com" | Kiểm ra **cả ba môn đang chạy đều lệch Pearl**, không riêng Tiếng Anh: Toán khớp 95/112 unit, Ngữ văn khớp 81/97 — nguyên nhân là Pearl phủ lớp 1-12 còn cây trong D1 dựng cho lớp 1-9. Nên thay vì sửa từng môn, viết **một script đọc được cả bảy môn** (`sync-tree-from-pearl.mjs`): Pearl dùng chung một khuôn nên một bản đọc là đủ, và không đẻ ra bản chép tay thứ hai để lệch. Hai định dạng liệt kê module của Pearl (tiêu đề ở Toán/Văn/Anh, bảng ở Lý/Hoá/Sinh) đều đọc được. Luật cốt lõi: unit đã có trong D1 khớp theo TÊN thì **giữ nguyên id**, chỉ cập nhật vị trí và phần chữ — đổi id là mất toàn bộ câu hỏi, lab và bằng chứng learner đã gắn vào node. Kết quả: Toán +15 unit (giữ 97), Văn +16 (giữ 82), **Lý 64 · Hoá 62 · Sinh 64 unit dựng mới hoàn toàn**, tất cả kèm sẵn ba bậc can_do và ba câu "vì sao" lấy nguyên từ Pearl. Package cũ theo chủ đề của Lý/Hoá/Sinh **giữ nguyên, không ẩn**: Pearl nói rõ cây năng lực không thay thế cây chủ đề, hai cây là hai trục và phải kiểm coverage riêng. Kèm `remap-unit-prereqs.mjs` vì khoá cạnh chứa tên Module, đồng bộ mà đổi tên module là graph chết lặng lẽ; chạy xong 225 cạnh Toán và 145 cạnh Văn vẫn nguyên | ✅ |
| SRC-410 | 2026-08-20 | Chỉ đạo kèm ảnh Dashboard: "sao bấm vào học tiếp, rồi nó cứ xuất hiện đúng cái lesson mà vừa học xong thế nhỉ?" | **Hai lỗi trong một màn hình.** (1) Nút HỌC TIẾP mở lại đúng ô vừa hoàn thành: chỗ chọn ô dùng `.find` lấy ô ĐẦU TIÊN khớp bài, mà ô đầu tiên thường chính là ô vừa xong, nên nút ấy nói dối về việc nó sẽ làm gì và learner kẹt trong vòng lặp. Tách phép chọn thành hàm thuần `pickResumeSlot` (ô chưa xong của đúng bài → ô chưa xong bất kỳ trong Unit → ô đầu làm lưới đỡ khi đã xong hết) và test thẳng nó; e2e không bắt được vì fixture không dựng đủ ô, còn test hàm thuần thì gỡ bản vá là đỏ ngay. (2) **Bốn Package cũ của Tiếng Anh vẫn hiện cạnh năm Package mới** dù SRC-408 đã đưa chúng vào danh sách tạm ẩn: deploy-learn của commit ấy bị **lint chặn** vì hai biến thừa trong script tôi vừa viết, nên bản mới chưa bao giờ lên production. Bài học: local tôi chạy `eslint apps workers` còn CI chạy `eslint .` — thư mục `scripts/` nằm ngoài vùng tôi kiểm, và một lỗi lint ở đó chặn cả deploy mà tôi tưởng đã xong. Từ nay chạy `npm run lint` như CI. Kèm cập nhật test giữ hai bản danh sách ẩn (server và app learn) không lệch nhau | ✅ |
| SRC-411 | 2026-08-20 | Chỉ đạo "làm nốt đi" sau khi đồng bộ cây từ Pearl | **670 câu hỏi soạn tay cho 67 Unit ngõ cụt của ba môn learner đang học** — Toán, Ngữ văn và Tiếng Anh nay đều 0 Unit không có câu nào. Toán 150 câu cho 15 Unit lớp 10-12 mới thêm khi đồng bộ Pearl (logarit, lượng giác, giới hạn, đạo hàm, tích phân, quy nạp, mệnh đề, tập hợp, tổ hợp, xác suất, tối ưu, giới hạn của mô hình). Ngữ văn 160 câu cho 16 Unit mới (điều tác giả cố ý không viết, hai cách đọc cùng hợp lệ, tự đặt câu hỏi nghiên cứu…). Tiếng Anh **360 câu cho 36 Unit**, trong đó trọn Package 1 Listen & Decode — mảng cây cũ không có lấy một câu, nên đây là lần đầu môn Anh có nội dung cho kỹ năng nghe và phát âm. Vẫn soạn tay theo bài học SRC-046, mỗi câu kèm `misconception` mô tả hiểu lầm dẫn tới đáp án sai | ✅ |
| SRC-412 | 2026-08-20 | Chỉ đạo "làm nốt toàn bộ content của cả Lý Hóa Sinh, đều lấy nguồn từ pearl.nemo12.com" | **630 câu hỏi soạn tay cho toàn bộ 63 Unit rỗng của môn Vật lý** (P1 Observe & Measure tới P5 Apply in the World). Khác các đợt trước ở chỗ nguồn nội dung không phải do tôi tự nghĩ: Pearl đã viết sẵn mục *Hiểu lầm thường gặp* cho từng Unit, nên `misconception` của mỗi câu là hiểu lầm có thật trong tài liệu curriculum — ví dụ "vật dừng vì lực trong nó cạn dần", "mắt nhìn bằng cách phóng ra thứ gì đó tới vật", "đường sức từ là những sợi dây có thật", "hiệu điện thế là thứ chảy trong dây". Vật lý nay còn 0 Unit không có câu nào | ✅ |
| SRC-413 | 2026-08-20 | Ảnh chụp Dashboard + "bấm vào icon chữ i nhỏ, cần sửa lại để user biết về nội dung của I will be able to (học xong module này, unit này thì tôi làm được cái gì). Bỏ link Đóng lại" | Popover dấu "i" ở cả ba tầng Package · Module · Unit nay mở đầu bằng **câu "I will be able to…" lấy thẳng từ Pearl**, con số đo đạc lùi xuống một dòng phụ, và nút "Đóng" bỏ hẳn (bấm lại dấu "i" hoặc bấm ra ngoài là đóng — đúng luật popover SRC-310). Migration 0057 thêm ba cột `strands.i_will`, `skill_nodes.i_will`, `skill_nodes.module_i_will`; `scripts/sync-iwill-from-pearl.mjs` đổ từ `apps/pearl/content/curriculum/` xuống, nên tài liệu vẫn là nguồn duy nhất | ✅ |
| SRC-414 | 2026-08-20 | Tiếp "làm nốt toàn bộ content của cả Lý Hóa Sinh" | **600 câu hỏi soạn tay cho toàn bộ 60 Unit rỗng của môn Hoá học** (H1 Observe tới H5 Apply), cùng cách làm với Vật lý ở SRC-412: mỗi `misconception` lấy thẳng từ mục *Hiểu lầm thường gặp* của Pearl — "nước bay hơi thì biến mất", "cân bằng nghĩa là phản ứng đã dừng", "phá liên kết thì giải phóng năng lượng", "chất nào ít gam hơn thì hết trước", "tên hoá học dài khó đọc thì nguy hiểm". Hoá học nay còn 0 Unit không có câu nào | ✅ |
| SRC-415 | 2026-08-17 | Chỉ đạo: **Dolphin có khu rà soát từng Interactive Lab / Learning Experience / Assessment Experience và từng step**; mentor bấm 1-2 nhãn rồi confirm, hệ ghi nhận; experience nghiêm trọng thì **tự ẩn** tới khi sửa xong. Mỗi experience cần **metadata**, chỉ hiện trong Dolphin | migration **0049** (experience_reviews + review_status/hidden\_\* + metadata sư phạm objective/depth/bloom/pedagogy/prerequisites/misconception) đã apply remote; API + UI Dolphin + backfill metadata: đợt sau | 🔵 |
| SRC-416 | 2026-08-20 | Chỉ đạo: "audit toàn bộ hệ thống tài liệu, hệ thống admin này, tạo ra các audit report, sau đó fix dần" | Hai audit chuyên đề, cố ý KHÔNG đặt thang điểm mới vì Audit Standard cấm trục chấm thứ hai: [Audit #005 — hệ tài liệu](../quality/audits/2026-08-20-002.md) và [Audit #006 — hệ admin](../quality/audits/2026-08-20-003.md). Phát hiện nặng nhất bên tài liệu: **232/415 SRC (56%) chưa canonical hoá** và khoảng cách đang rộng ra chứ không hẹp lại; cộng 25/93 doc có `last_reviewed` cũ hơn ngày sửa thật, một doc mồ côi lại đúng là doc của chỉ báo 🔴 backup/restore. Bên admin: **5 endpoint chạy production mà không màn hình nào gọi tới** (audit log, dead letters, retention policies, run metrics) nên bốn chỉ báo AS đang PASS bằng lý do 'endpoint tồn tại' thật ra người vận hành không với tới được; Overview quay spinner vĩnh viễn khi API lỗi; 5 màn hình nuốt lỗi thành 'không có dữ liệu'; cấp được quyền admin nhưng không thu lại được; 0 xác nhận cho mọi hành động ghi. Kèm 13 việc T1..T7 và M1..M6 | ✅ |
| SRC-417 | 2026-08-20 | Báo lỗi: "learner chọn một unit rất khó để học vượt, rồi không vượt qua được, thì hệ thống lại vẫn bắt học đi học lại chỗ đó. Và mãi mãi ko vượt qua được" | Dữ liệu production xác nhận: `exp_key='skip'` có 8 lượt `failed` so với 5 `completed`, và bậc 0 của `pickToday` ghim unit đang dở **vô điều kiện** nên vòng lặp là chắc chắn, không phải rủi ro. Thêm `isStalled()` (4 lượt thử, hoặc 7 ngày, hoặc 2 lần trượt test-out) để đẩy unit bí ra khỏi hàng đợi; thêm hai chiến lược người dùng đặt tên: nền móng (unit dễ nhất đang chặn nhiều unit khác) và 5 unit vừa làm gần đây. Kèm bản tiếng Anh cho cả khu "Việc hôm nay" | ✅ |
| SRC-418 | 2026-08-20 | Yêu cầu: "learner có thể đánh dấu ưu tiên tối đa 3 module hoặc 3 unit, đưa lên khu vực phía trên... hãy gợi ý cho tôi trước, tôi chọn, rồi mới làm" | Bốn đề xuất được chốt nguyên vẹn: ưu tiên **mềm** (ghim chỉ phá hoà trong cùng bậc, không vượt bậc — để ghim không dựng lại đúng vòng lặp SRC-417 vừa gỡ); cái ghim đầu tiên quyết định loại; tự bỏ ghim khi đã vững; 3 cái mỗi môn | ✅ |
| SRC-419 | 2026-08-20 | Câu hỏi: "làm sao để biết như thế nào là xong? Tôi lo là học sinh cứ học mãi, ko có cận trên và ko có đích nên nó sẽ vô tận" | Đo bằng **số Unit**, không bằng phút: một phiên trên production ghi 82 câu trong 1.241 phút (tab bỏ quên) so với 77 câu trong 19 phút, nên phút không đo được gì. Cường độ chọn trong hồ sơ: nhẹ 1-3, vừa 4-7, cao 8-20 unit/ngày; tuần là 5 ngày có học trong 7; "cách đích bao xa" cố ý chỉ hiện ở trang Plan để đích dài hạn không đè lên việc hôm nay | ✅ |
| SRC-420 | 2026-08-20 | Việc nối tiếp SRC-396: graph prerequisite cho Tiếng Anh và Hoá học | 71 + 91 cạnh có lý do. Cổng mới chặn **cạnh đi ngược lớp** ngay lúc nạp — bắt được 19 cạnh đang chạy trên production, trong đó 16 nằm trong graph Toán do chính đợt SRC-396 sinh ra | ✅ |
| SRC-421 | 2026-08-20 | Việc nối tiếp SRC-399: 17 lab cho Unit Toán lớp 10-12 | Thêm cổng canh **nhãn nút**: 20/39 lab đợt đầu có nhãn kiểu "Lựa chọn 1", "Bước 2" nên learner bấm mù. Cổng cũng bắt hai nút trùng nhãn và câu kiểm không có đáp án đúng | ✅ |
| SRC-422 | 2026-08-20 | Việc nối tiếp: 36 lab cho Unit Tiếng Anh còn thiếu | Dùng lại khuôn picker SRC-388/390 đã tổng quát hoá thành `node scripts/seed-b21-labs.mjs [file] [môn] [PKG]` | ✅ |
| SRC-423 | 2026-08-20 | Yêu cầu: "soạn graph Ngữ văn" và "với riêng learner dac2205@gmail.com, thêm cụm card giải thích logic của việc tính ra việc hôm nay" | 156 cạnh Ngữ văn soạn lại thành file nguồn (bản cũ nạp từ đợt máy sinh, file soạn đã mất). Vệt giải thích được sinh **bên trong `queue.ts`, cùng lúc với quyết định** — không mô tả lại ở tầng hiển thị, vì một mô tả viết riêng sẽ trôi khỏi luật ngay lần sửa đầu rồi nói dối thay vì giải thích | ✅ |
| SRC-424 | 2026-08-20 | Báo lỗi: "chỉnh ngôn ngữ chỗ sắp quên và 2 units ở khu đó" | Nốt phần tiếng Anh còn sót của khu ôn tập | ✅ |
