diff --git a/docs/audit/2026-09-08-audit-report.html b/docs/audit/2026-09-08-audit-report.html
index d6b614b6820..569fb2587fe 100644
--- a/docs/audit/2026-09-08-audit-report.html
+++ b/docs/audit/2026-09-08-audit-report.html
@@ -101,6 +101,7 @@
Trạng thái xử lý - cập nhật đến Round 4 (2026-09-16)
| ĐÃ FIX (Round 4 - verify lại 2026-09-16) | MD-03, MD-05/06, LO-02, LO-03, MD-29 | MD-03: PBAC checkPermission giờ query membership thật, throw FORBIDDEN (aa68fd3acc). MD-05/06: partial expression index trên metadata dosOrgId/dosTeamId + WebhookScheduledTriggers drain take:100 + await + deleteMany sau dispatch (efb232e52f). LO-02: 3 barrels chết đã xoá (a058d89d53). LO-03: restore membership ADMIN/OWNER check (aa68fd3acc). MD-29: fork env vars vào turbo globalEnv (ccf9b85785) |
| ĐÃ FIX (Round 4 - 2026-09-16) | HI-09, CR-08 (hoàn tất), LO-13 (một phần) | HI-09: workflow mới fork-ci.yml (type-check + lint + unit test) chạy trên PR + push dev/main của DOS/Crove-Cal; deploy-docker.yml thêm job ci-gate (type-check) mà build-and-push phải chờ. CR-08: Dockerfile/docker-compose bỏ default secret từ Round trước; Round 4 thay 4 giá trị secret thật trong apps/api/v2/.env.example bằng placeholder. LO-13: JWT example trong README-PLATFORM.md thay bằng placeholder |
| ĐÃ FIX (Round 5 - 2026-09-16, PR #74) | HI-12 phần runner | Runner stage chạy USER node (app tree copy với --chown=node:node, không tạo layer copy-up) sau bước apt chạy root; .dockerignore chặn .env*/*.pem/*.key/*.p12/*.pfx/.husky - bảo vệ cả image web lẫn api/v2 (cùng context root). Verify: docker build --check sạch (4 warning là ARG build-time placeholder đã xử lý ở CR-08), image build + publish sau gate thành công trên dev (run 35127273831) |
+ | ĐÃ FIX (Round 6 - 2026-09-17, PR #76) | MD-30, LO-04, LO-05 | LO-04/05: 3 vị trí dùng CALENDSO_ENCRYPTION_KEY thiếu một cách âm thầm (signJwt + login getServerSideProps encode thành secret 0-byte mà jose vẫn ký/verify được; verifyCodeUnAuthenticated seed degrade thành hàm của email nạn nhân) - giờ throw theo pattern next.config.ts; start.sh prod đã refuse boot khi thiếu key từ trước nên chỉ local setup sai mới thấy lỗi. MD-30: xoá Stripe secrets.png (590KB, account ID Stripe lộ, không có chỗ nào reference); lưu ý: vẫn nên rotate test-mode keys trên Stripe dashboard vì account ID còn trong git history |
| CHỜ QUYẾT ĐỊNH | HI-13, HI-14, HI-16, HI-10 | HI-13: 61 migrations cần biết DB prod dùng schema nào (lưu ý: upstream đã đóng source 2026-04 nên áp lực sync giảm). HI-14: wire workflows dispatcher là quyết định feature - tham khảo Cal.com Workflows 2.0 (v6.9) trong report feature-gap cùng ngày. HI-16: branding hardcode - giờ upstream đóng source nên việc giữ branding riêng có chủ đích là phương án hợp lý, cần chốt. HI-10: bật crons cần cấu hình secrets riêng (CRON_SECRET v.v.) trước. Khi deploy: rotate secret Supabase + env mới (CRON_SECRET, OIDC_*, BREVO/CROVE/DOS_SYNC_WEBHOOK_SECRET, DATABASE_SSL_REJECT_UNAUTHORIZED=false nếu pooler cần) + prisma migrate deploy |
| CÒN LẠI (TAIL) | Docker phần dở + perf/cosmetic | HI-12 phần còn lại (pin actions theo SHA - trùng MD-28; turbo prune để bỏ dev deps khỏi image), LO-13 phần dở (prisma/.env symlink, pin trigger.dev), MD-16…22 (frontend perf), MD-27/28 (CI supply-chain hygiene), MD-30 (Stripe png), MD-31/32 (latent), LO-01/04/05/06/07 (một phần)/08/09/11/14 |
@@ -437,11 +438,14 @@ Danh sách phát hiện
"MD-01":"fixed","MD-02":"fixed","MD-03":"fixed","MD-04":"fixed","MD-05":"fixed","MD-06":"fixed","MD-07":"fixed","MD-08":"fixed","MD-09":"fixed",
"MD-10":"fixed","MD-11":"fixed","MD-12":"fixed","MD-13":"fixed","MD-14":"fixed","MD-15":"fixed",
"MD-16":"open","MD-17":"open","MD-18":"open","MD-19":"open","MD-20":"open","MD-21":"open","MD-22":"open",
- "MD-23":"fixed","MD-24":"fixed","MD-25":"fixed","MD-26":"fixed","MD-27":"open","MD-28":"open","MD-29":"fixed","MD-30":"open","MD-31":"open","MD-32":"open",
- "LO-01":"open","LO-02":"fixed","LO-03":"fixed","LO-04":"open","LO-05":"open","LO-06":"open","LO-07":"partial","LO-08":"open","LO-09":"open","LO-10":"open","LO-11":"open","LO-12":"fixed","LO-13":"partial","LO-14":"open"
+ "MD-23":"fixed","MD-24":"fixed","MD-25":"fixed","MD-26":"fixed","MD-27":"open","MD-28":"open","MD-29":"fixed","MD-30":"fixed","MD-31":"open","MD-32":"open",
+ "LO-01":"open","LO-02":"fixed","LO-03":"fixed","LO-04":"fixed","LO-05":"fixed","LO-06":"open","LO-07":"partial","LO-08":"open","LO-09":"open","LO-10":"open","LO-11":"open","LO-12":"fixed","LO-13":"partial","LO-14":"open"
};
const ST_LABEL = {fixed:["ĐÃ FIX","st-yes"], partial:["FIX 1 PHẦN","st-part"], decision:["CHỜ QUYẾT ĐỊNH","st-dec"], open:["CÒN MỞ","st-no"]};
const ST_NOTE = {
+ "MD-30":"Round 6 (PR #76): file đã xoá, không còn reference. Test-mode keys trong ảnh vẫn nên rotate trên Stripe dashboard (account ID còn trong git history).",
+ "LO-04":"Round 6 (PR #76): signJwt + login getServerSideProps throw khi thiếu CALENDSO_ENCRYPTION_KEY (pattern next.config.ts).",
+ "LO-05":"Round 6 (PR #76): bỏ fallback chuỗi rỗng, throw khi thiếu key; thuật toán md5 giữ nguyên để không vô hiệu code đã phát.",
"CR-08":"Round 2 bỏ ARG defaults + comment studio; Round 4 (2026-09-16) thay 4 giá trị thật trong apps/api/v2/.env.example bằng placeholder.",
"HI-09":"Round 4 (2026-09-16): fork-ci.yml (type-check + lint + unit) chạy trên PR/push dev/main; deploy-docker.yml thêm ci-gate. Cron xem HI-10.",
"HI-10":"Cần cấu hình secrets riêng cho fork (CRON_SECRET…) rồi mới bật được - không bật khi thiếu secret.",