Bỏ qua

E-004 — Onboard tổ chức

Nguồn: PRD prd-openapi-platform-2026-09-04 §5 (F2, F9) · spine architecture-openapi-platform-2026-09-04 (AD-3, AD-20) · story chi tiết + AC ở _bmad-output/planning-artifacts/epics.md (mục Epic E-004). PO duyệt cấu trúc epic + ô parity: 05/09/2026 — duyệt cả danh sách epic và bảng story. · bổ sung 11/09/2026 tối (PO chốt từng mục — UU-TIEN-GD1 §G): tách 2.42.4 đăng ký tài khoản · 2.9 nộp hồ sơ (P4); thêm 1.9 · 1.10 người dùng TPP phía quản trị, chỉ xem (P2); thêm 2.10 (nợ có thi công OAPI-131). Thứ tự 17–20, không dời hàng nào. · bổ sung 12/09/2026 (PO chốt cả 8 mục — spine AD-30 lưu tệp đính kèm): thêm 1.11 kho + bảng đính kèm đơn nộp (admin-be) · 2.11 điểm cuối nhận/trả tệp (portal-be). Thứ tự 21–22, không dời hàng nào. · bổ sung 13/09/2026 (PO chốt OAPI-230-cô-lập-byte-kho-chung cách 1 — thu hồi SELECT trần của portal_app trên kho byte, thay bằng hàm lọc): thêm 1.12 hàm lọc (admin-be) · 2.12 đổi câu đọc + hợp đồng (portal-be) · 1.13 REVOKE (admin-be) — ba nhịp vì chiều thu hồi đảo AD-14; 1.22.11 đã archive nên khép bằng story mới. Thứ tự 23–25, không dời hàng nào. · bổ sung 12/09/2026 (PO chốt): vai của người dùng trong tổ chức TPP — CHƯA LÀM, nợ có tên OAPI-205 (openapi-platform#23); 1.9/1.10 thôi trỏ «E-005» (không có story vai TPP ở đó). Không thêm hàng.

Hai cửa vào — bên thứ ba tự đăng ký, hoặc nhân sự ngân hàng nhập hộ. Cả hai đều qua thẩm định và phê duyệt, vì khoản 10 Điều 11 đặt nghĩa vụ thẩm định lên ngân hàng.

Vì sao làm — BRD tầng epic

Mục tiêu. Bên thứ ba vào hệ thống qua hai cửa — tự đăng ký hoặc nhân sự ngân hàng nhập hộ — và ngân hàng thẩm định rồi duyệt. Đây là phần thi hành nghĩa vụ thẩm định ở khoản 10 Điều 11.

Nhóm yêu cầu trong PRD — F2, F9

F2 — Hồ sơ TPP và tiếp nhận onboard

Hai cửa vào, một định nghĩa hồ sơ. PO chốt 04/09/2026: hồ sơ TPP vào hệ thống theo hai đường — TPP tự đăng ký trên portal-fe (nhóm F9), hoặc nhân sự ngân hàng nhập từ admin-fe. Cả hai đều phải qua phê duyệt. Bộ trường, quy tắc hợp lệ và trạng thái ở nhóm F2 là một định nghĩa dùng chung; hai cửa vào không được đẻ ra hai bộ quy tắc, vì lúc đó cửa lỏng hơn sẽ thành đường vòng của cửa chặt hơn.

  • FR-008 Tạo hồ sơ TPP với mã số thuế làm định danh (TPP-ID).
  • FR-009 Mã số thuế là duy nhất toàn hệ thống; hệ thống chặn tạo trùng.
  • FR-010 Thẩm định mã số thuế còn hoạt động. [ASSUMPTION C7] Chưa rõ có API tra cứu dùng được không. Giả định nhập tay, đính kèm bằng chứng, checker xác nhận; nếu có API thì thêm bước tự động chứ không bỏ bước người xác nhận.
  • FR-011 Loại pháp nhân TPP là trường bắt buộc, giá trị đóng: Ngân hàng · Tổ chức trung gian thanh toán · Tổ chức khác. Đổi giá trị này là thay đổi ràng buộc (xem FR-026).
  • FR-012 Hồ sơ mang đủ 8 khối nội dung tối thiểu của Điều 8. Thiếu khối nào thì không cho chuyển sang trạng thái chờ duyệt. [ASSUMPTION] 8 khối này ánh xạ thành bao nhiêu trường thật phụ thuộc mẫu hợp đồng bank đang dùng — chưa có mẫu đó.
  • FR-013 Trường cấp độ an toàn hệ thống thông tin của TPP, kèm tài liệu chứng minh.
  • FR-014 Đính kèm tài liệu vào hồ sơ. [ASSUMPTION C4] Chưa rõ hợp đồng ký giấy hay ký điện tử, và admin lưu bản scan hay chỉ metadata. Giả định lưu file đính kèm.
  • FR-015 Trạng thái hồ sơ: NhápChờ duyệt → (Chờ bổ sung | Đã duyệt | Từ chối).
  • FR-016 Trả hồ sơ về Chờ bổ sung kèm lý do bắt buộc (Điều 10.1).
  • FR-017 Danh sách TPP có tìm kiếm và lọc theo trạng thái, loại pháp nhân, scope đang có.
  • FR-018 Nhập dữ liệu TPP đang đấu nối sẵn. [ASSUMPTION C3] Chưa rõ có TPP nào đang đấu nối trực tiếp không. Nếu có, đây không phải hệ thống trắng mà là hệ thống có dữ liệu di trú, và Điều 15.1 buộc bank đã phải lập danh mục đó rồi.

F9 — Cổng TPP tự đăng ký (portal-fe + portal-be)

  • FR-054 Bên thứ ba tự tạo tài khoản người dùng trên portal-fe và tự nộp hồ sơ đăng ký.
  • FR-055 Tách bạch hai loại danh tính của TPP — đây là chỗ dễ trộn nhất khi mở cổng tự phục vụ:
  • Tài khoản người dùng của TPP: người thật đăng nhập portal-fe để nộp và theo dõi hồ sơ. Tồn tại trước khi TPP được duyệt, vì không có nó thì không ai nộp được gì.
  • Credential ứng dụng: client_idclient_secret dùng gọi Open API. Chỉ cấp sau khi hồ sơ được duyệt — Phụ lục 01 §1 nói TPP đăng ký credential sau khi đã thiết lập kênh an toàn với ngân hàng.

Trộn hai thứ này lại thì hoặc phải cấp credential cho một TPP chưa thẩm định, hoặc không cho ai nộp hồ sơ được. Cả hai đều sai. - FR-056 Hồ sơ TPP tự nộp dùng đúng bộ trường và đúng quy tắc hợp lệ của nhóm F2, gồm cả 8 khối Điều 8 (FR-012) và loại pháp nhân (FR-011). - FR-057 ⛔ Hồ sơ TPP tự nộp không đi thẳng tới checker. Phải có một nhân sự ngân hàng tiếp nhận và thẩm định, đóng vai maker, trước khi hồ sơ tới checker.

Lý do là pháp lý chứ không phải quy trình: Điều 11.10 đặt nghĩa vụ thẩm định lên ngân hàng. Nếu để TPP đóng vai maker thì "hai người" là TPP cộng checker — mà TPP không phải người của ngân hàng, nên ngân hàng chưa thẩm định gì cả. Hồ sơ tự nộp là đầu vào, không phải nửa đầu của cặp maker/checker. - FR-058 TPP theo dõi được trạng thái hồ sơ và bổ sung khi bị trả về Chờ bổ sung (FR-016). Lý do trả về hiển thị cho TPP; ghi chú nội bộ của ngân hàng thì không. - FR-059 Chống lạm dụng đường đăng ký công khai: giới hạn tần suất tạo tài khoản và nộp hồ sơ theo nguồn, xác minh email trước khi cho nộp, chặn dò mã số thuế bằng cách không tiết lộ mã số thuế đó đã tồn tại trong hệ thống hay chưa.

Đây là đường ghi từ Internet vào kho hồ sơ pháp lý — thứ mà giai đoạn chỉ-có-admin không có. - FR-060 TPP xem được client_id đã cấp và yêu cầu xoay client_secret (FR-029). Yêu cầu xoay vẫn qua phê duyệt phía ngân hàng; client_secret mới hiển thị đúng một lần (FR-028).

Bảng story → change

Story Service Thứ tự bắt buộc Ghi chú Chặn bởi
E-004/1.1 Schema Tổ chức và hồ sơ admin-be 1 cap/tpp-onboarding · mã số thuế là khoá tự nhiên, loại pháp nhân là enum bắt buộc · ⚠️ PO chốt 11/09 (tại làn admin-be, memlog change tpp-organization-schema @ d810c85): V12 BỎ trang_thaingay_duyet khỏi app.tpp — không SHALL, không design, không test; V11 đã ghi «cột trạng thái là nguồn sự thật thứ hai». Vòng đời/trạng thái hồ sơ là việc của 1.3. ⇒ Câu «trạng thái, ngày duyệt» ở epics.md:485nguyên liệu đã hết hiệu lực (⛔G1: không sửa ngược), hàng này là nơi ghi. Cùng lượt PO chốt: 8 khối Điều 8 đi bằng noi_dung jsonb (hoãn lần hai, có nợ) · tpp_profile chỉ-thêm · portal_app không SELECT trần (lệch AD-20 lần 2, vết ở OAPI-121) · đính kèm chỉ metadata M:E-001/1.1 · M:E-001/1.2
E-004/1.2 Thẩm định mã số thuế admin-be 2 cap/tpp-onboarding · nhập tay + checker xác nhận M:E-004/1.1 · M:E-001/3.1
E-004/1.3 Vòng đời hồ sơ admin-be 3 cap/tpp-onboarding · qua khung phê duyệt E-001/3.1 M:E-004/1.1 · M:E-001/3.1
E-004/2.1 Tài khoản người dùng của bên thứ ba portal-be 4 cap/tpp-self-registration · tách hẳn khỏi người dùng nội bộ M:E-001/0.2 · M:E-001/1.2
E-004/1.6 Khai bảng SUBMISSION và ma trận quyền portal_app admin-be 5 cap/schema-migration · ⛔ vật mang của E-004/2.2 · AD-14: bảng portal-be GHI vẫn do admin-be KHAI M:E-001/1.1
E-004/1.7 Khai bảng phiên cho người dùng bên thứ ba admin-be 6 cap/schema-migration · ⛔ vật mang của E-004/2.8 · AD-14 · ⚠️ phạm vi chốt bằng số đo của portal-be trước khi mở change M:E-001/1.1 · TK:E-004/2.8
E-004/2.8 Xác thực và phiên cho người dùng bên thứ ba portal-be 7 cap/tpp-self-registration · AD-19 phiên có trạng thái · khoá tạm 3 lần / 15 phút (cấu hình, ⛔ không hằng số) · quên mật khẩu câu trung lập · đổi mật khẩu trong phiên · ⛔ tách hẳn đường xác thực nội bộ (AD-20) · chặn tới khi 1.7 xong M:E-004/1.7 · M:E-004/2.1 · Đ:E-001/4.1
E-004/2.2 Đơn nộp hồ sơ portal-be 8 cap/tpp-self-registration · SUBMISSION tự chứa, không khoá ngoại tới TPP · ✅ 1.6 đã xong (admin-be 2d0909b, V5__khai_bang_submission.sql) · nay chặn bởi 2.8: nộp hồ sơ là hành động của người đã đăng nhập M:E-004/1.6 · M:E-004/2.8
E-004/2.3 Chống lạm dụng đường đăng ký công khai portal-be 9 cap/abuse-protection · căn cứ FR-059, KHÔNG phải Điều 11.9 M:E-004/2.1
E-004/1.4 Màn hồ sơ tổ chức admin-fe 10 cap/admin-console-ui · ⛔ màn riêng không modal · ô lý do nhắc hiển thị ra ngoài · PO chốt 13/09/2026: M:1.3Đ:1.3 — FE đi trước API vòng đời hồ sơ theo tiền lệ E-001/5.12 (Đ:2.4) và E-001/5.9 (P7, Đ:E-004/2.8): dựng trên gói (OrgList · OrgDetailScreen · OrgCreateModal) + máy chủ giả lập theo nếp port, màn tự khai chỗ chưa nối (§F); ⛔ không coi là xong khi 1.3 chưa archive và chưa nối thật · hợp đồng API 1.3 chưa có (OAPI-224 mới mở) ⇒ làn admin-fe nhắn admin-be xin openapi.yaml sớm (AD-28) Đ:E-004/1.3 · M:E-001/5.5
E-004/2.4 Màn đăng ký tài khoản portal-fe 11 cap/tpp-portal-ui · PO tách 11/09 tối (P4): CHỈ còn đăng ký tài khoản (3 bước theo gói «Đăng ký tài khoản»), nộp hồ sơ sang 2.9 · ô đồng ý hai văn bản dẫn sang 2.6 · ⛔ §F UU-TIEN-GD1: đăng ký tạm tự động kích hoạt, bước xác minh email để //TODO đúng chỗ + màn tự khai, nợ có điều kiện trả (cổng gửi thư) — đường BE là change mới có tênportal-be, ⛔ không vá 2.1 đã archive · ✅ hết chặn: 2.15.6 đều archive M:E-004/2.1 · M:E-001/5.6 · Đ:E-004/2.6
E-004/2.5 Tiếp nhận đơn nộp admin-be 12 cap/tpp-onboarding · ⛔ đơn KHÔNG đi thẳng tới checker M:E-004/2.2 · M:E-004/1.3
E-004/1.5 Nhập dữ liệu tổ chức đang đấu nối admin-be 13 cap/tpp-onboarding · ⚠️ BỊ CHẶN: chưa rõ có tổ chức nào M:E-004/1.1 · ⛔NGOÀI:chưa rõ có tổ chức nào
E-004/2.6 Khung hai văn bản pháp lý portal-fe 14 cap/tpp-portal-ui · điều khoản 9 mục + chính sách dữ liệu 8 mục · bảng bốn cột chuyển thẻ dưới 768px M:E-001/5.4
E-004/1.8 Khai bảng phiên bản văn bản pháp lý và vết đồng ý admin-be 15 cap/schema-migration · ⛔ vật mang của E-004/2.7 · AD-14 · ⛔ không ghi đè tại chỗ: bảng phải giữ được NHIỀU phiên bản và vết ai đồng ý bản nào M:E-001/1.1 · TK:E-004/2.7
E-004/2.7 Nội dung pháp lý có phiên bản và vết đồng ý portal-be 16 cap/tpp-self-registration · ⛔ không ghi đè tại chỗ · ghi ai đồng ý PHIÊN BẢN NÀO, lúc nào M:E-004/1.8
E-004/2.9 Màn nộp hồ sơ portal-fe 17 cap/tpp-portal-ui · tách từ 2.4 11/09 tối (P4) · 8 khối theo Điều 8 · lưu nháp tự động · là hành động của người đã đăng nhập (2.8) · tuyến «Hồ sơ đăng ký» hiện là màn tự khai chưa dựng M:E-004/2.2 · M:E-004/2.8 · M:E-004/2.4
E-004/1.10 API xem người dùng bên thứ ba theo tổ chức admin-be 18 cap/tpp-onboarding · mở 11/09 tối (PO chốt P2: A3 = CHỈ XEM) · liệt kê + chi tiết app.tpp_user gom theo tổ chức (admin_app đã có SELECT từ V3) · ⛔ 2.1 (portal-be) đã archive, không đụng · ⛔ KHÔNG gán vai, KHÔNG khoá/mở trong story này — gán vai chờ nguồn vai TPP — nợ có tên OAPI-205 (openapi-platform#23; ~~E-005~~ ⛔ đo 12/09 E-005 không có story vai TPP, trỏ vào đó là trỏ chỗ trống), khoá/mở là thao tác ràng buộc (K2 + duyệt 3.1) ⇒ nợ có tên, mở story sau khi hai nguồn đó có M:E-004/1.1 · M:E-001/2.3
E-004/1.9 Màn xem người dùng bên thứ ba (phía quản trị) admin-fe 19 cap/admin-console-ui · mở 11/09 tối (PO chốt P2: A3 = CHỈ XEM) · gói AccountList({scope:"tpp"}) (cột Tổ chức + Vai trò trong tổ chức, ⛔ không nút Tạo mới) + khối «Người dùng thuộc tổ chức» trong OrgDetailScreen · cột Vai trò trong tổ chức ⛔ chưa có nguồn (nợ vai TPP OAPI-205, openapi-platform#23) ⇒ lượt đầu bỏ, ghi nợ cùng nếp OAPI-142 · ⛔ không nút gán vai / khoá / mở (xem 1.10) M:E-004/1.10 · M:E-001/5.5 · M:E-001/5.10
E-004/2.10 Giới hạn tốc độ ngoài đường đăng nhập và độ dài tối thiểu khi đổi mật khẩu portal-be 20 cap/abuse-protection · mở 11/09 tối (PO chốt — luật nợ sau archive, E-001 §Bổ sung 11/09) · nhà của issue có sẵn OAPI-131 (portal-be#28), nợ phát hiện sau khi 2.8 archive · đổi trailer **Story:** trên body issue #28 từ E-004/2.8 thành E-004/2.10 (mối nối thật; link.yaml cũ không chứa #28 — số đo làn portal-be 11/09) M:E-004/2.8
E-004/1.11 Khai bảng đính kèm của đơn nộpkho nội dung tệp admin-be 21 cap/schema-migration · mở 12/09 (PO chốt 8 mục — AD-30) · ⛔ vật mang của E-004/2.11 · AD-14 · app.submission_attachment (metadata, nối submission, khuôn V12 tpp_attachment: ten_file · loai_mime · kich_thuoc_byte · bam · duong_dan = khoá kho db:<uuid>) + app.tep_noi_dung (bytea, xoá được — AD-30 mục 1) · GRANT portal_app INSERT/SELECT theo hàng (nếp V5), ⛔ không UPDATE/DELETE · ⛔ hình dạng do 2.11 chốt trong design.md trước, 1.11 không tự đoán — ba nhịp như cặp 1.7/2.8 · trả nợ OAPI-149 (admin-be#53) M:E-004/1.6 · TK:E-004/2.11
E-004/2.11 Điểm cuối nhận tệp đính kèm cho đơn nộp và trả tệp cho chính người nộp portal-be 22 cap/tpp-self-registration · mở 12/09 (PO chốt 8 mục — AD-30) · multipart, PDF/JPG theo magic bytes, ≤ 10 MB là cấu hình (gói design màn nộp hồ sơ khối 2: 3 tài liệu, 2 bắt buộc) · bam = sha256: tính khi nhận · trả tệp Content-Disposition: attachment + nosniff, ⛔ không inline (AD-30 mục 3) · T_iso: chỉ tệp của đơn thuộc tổ chức mình, 404 vô hình · ⛔ không quét mã độc trong story này — nợ có cổng của AD-30 · nhịp 1: chốt hình dạng bảng gửi admin-be (ghi vào issue của 1.11) trước khi viết mã nối · trả nợ OAPI-151 (portal-be#31); mở đường cho OAPI-176 (portal-fe#26) M:E-004/1.11 · M:E-004/2.2
E-004/1.12 Hàm lọc đọc byte kho tệp cho portal_app admin-be 23 cap/schema-migration · mở 13/09 (PO chốt OAPI-230-cô-lập-byte-kho-chung cách 1) · nhịp ①/③ thu hồi SELECT trần trên app.tep_noi_dung · hàm trả noi_dung chỉ khi khoá kho thuộc đính kèm của đơn người gọi (join submission_attachment_of_user, nếp V18) · ⛔ SECURITY INVOKER không đủ sau thu hồi ⇒ DEFINER hẹp + SET search_path + REVOKE FROM PUBLIC + GRANT EXECUTE portal_app · ⛔ chưa thu hồi gì ở đây (chiều THÊM — admin-be trước)
E-004/2.12 Đọc byte qua hàm lọc, bỏ SELECT trần khỏi hợp đồng portal-be 24 cap/tpp-self-registration · mở 13/09 (PO chốt OAPI-230 cách 1) · nhịp ②/③ · AttachmentJdbcRepository.FIND_CONTENT (SELECT noi_dung FROM app.tep_noi_dung) → gọi hàm của 1.12 · DatabaseContract: bỏ SELECT khỏi tập bắt buộc của app.tep_noi_dung (giữ INSERT theo cột), khai EXECUTE hàm — cổng hai chiều, THỪA cũng đỏ · T_iso giữ nguyên: 404 vô hình M:E-004/1.12
E-004/1.13 Thu hồi SELECT trần của portal_app trên app.tep_noi_dung admin-be 25 cap/schema-migration · mở 13/09 (PO chốt OAPI-230 cách 1) · nhịp ③/③ · V2x REVOKE SELECT ON app.tep_noi_dung FROM portal_app + ma trận quyền + lưới · đo has_table_privilege('portal_app','app.tep_noi_dung','SELECT') = false · ⛔ TR: bản portal-be của 2.12 phải chạy trên mọi môi trường TRƯỚC khi migration này chạy — chiều THU HỒI đảo AD-14, án lệ V7/OAPI-83-dat-updated-at-không-revoke-execute M:E-004/2.12 · TR:E-004/2.12
Câu Chốt
--- --- ---
1 NFR-003 không có số — bao lâu không hoạt động thì hết phiên 15 phút (áp cả E-001/2.3)
2 FR-007 ghi vào đâu E-001/4.1 — story đã có, ⛔ không mở story mới; xem E-001
3 đổi mật khẩu và đăng xuất, gói design chưa vẽ màn làm back-end trước

Bổ sung 07/09/2026 (PO duyệt) — hai văn bản pháp lý. 2.62.7 sinh từ hệ thống thiết kế, trước đó không epic nào mang chúng. Chúng nằm trên đường đi bắt buộc: ô đồng ý ở màn đăng ký tài khoản dẫn sang, nên 2.4 không hoàn thành được nếu thiếu. ⛔ Thứ tự 11–12 là thứ tự MỞ VIỆC, không phải thứ tự phụ thuộc: 2.6 phải xong trước khi 2.4 được coi là đóng.

⚠️ 2.7 không phải trang đọc. Chỉ làm trang đọc thì không có bằng chứng ai đã đồng ý điều khoản phiên bản nào, lúc nào — đúng loại bằng chứng thanh tra hỏi. Cùng nếp BL-03 đã chốt cho hồ sơ: có phiên bản, không ghi đè tại chỗ. Bảng thời hạn lưu chạm Nghị định 13/2023/NĐ-CP và trục T_pii. ⛔ Phụ thuộc NGOÀI đội: câu chữ hiện tại trong thiết kế là bản nháp phục vụ thiết kế, phải thay bằng bản do Pháp chế và Tuân thủ MSB duyệt trước khi phát hành. Cấu trúc mục thì giữ, nội dung thì không.

PO duyệt 08/09/2026 — làm KHUNG ngay, nội dung thành NỢ CÓ CỔNG. 2.62.7 không chờ Pháp chế: nội dung là dữ liệu, không phải mã, nên khi có bản duyệt thì thay bằng cách thêm một phiên bản, không sửa dòng mã nào. Hai ràng buộc kèm theo, cả hai là điều kiện của lượt duyệt này:

  1. Bản nháp mang cờ NHAP ngay TRONG chính dữ liệu phiên bản, ⛔ không phải một banner rời trên giao diện — banner là thứ quên gỡ được mà không ai đỏ.
  2. Cổng fail-closed: môi trường thật từ chối mở đường đăng ký công khai khi phiên bản văn bản đang hiệu lực còn cờ NHAP. Đây là chỗ biến nợ thành thứ không quên được; một dòng ghi chú trong tài liệu thì không.

⚠️ Vì sao phải có cổng chứ không chỉ ghi nợ: vết đồng ý của 2.7 sẽ trỏ tới một phiên bản không có hiệu lực pháp lý — tức bằng chứng «ai đồng ý cái gì» vô giá trị đúng lúc thanh tra hỏi, mà đó chính là thứ 2.7 sinh ra để có. Thêm nữa, Nghị định 13/2023/NĐ-CP đòi thông báo xử lý dữ liệu cá nhân đúng nội dung (mục đích · loại dữ liệu · thời hạn lưu · quyền của chủ thể) — sai nội dung là vi phạm thật, không phải lỗi hình thức.

Điều kiện trả nợ: Pháp chế và Tuân thủ MSB duyệt câu chữ hai văn bản — và bắt buộc trước khi mở đăng ký cho TPP thật. Nợ ghi ở portal-fe (khung 2.6) và portal-be (phiên bản + vết đồng ý 2.7). ⚠️ Một câu chỉ Pháp chế trả lời được, hỏi cùng lượt: khi bản chính thức thay bản nháp, người đã đồng ý bản nháp có phải đồng ý lại không — kỹ thuật làm được cả hai đường, chọn đường nào là câu pháp lý.

Bổ sung 12/09/2026 (PO chốt cả 8 mục) — E-004/1.112.11, tệp đính kèm cho đơn nộp; spine AD-30. Làn portal-be đo 12/09 theo yêu cầu PO: chưa có issue nào mở được cho điểm cuối tải tệp — ba nợ ở ba repo (OAPI-149-kho-lưu-tệp-chưa-có-chủ admin-be#53 · OAPI-151-đính-kèm-tài-liệu-hồ-sơ portal-be#31 · OAPI-176-tải-tệp-màn-nộp-hồ-sơ portal-fe#26) cùng trỏ về một chỗ thiếu: spine không có quyết định lưu tệp (review-compliance.md Đ5/Đ8 treo từ 04/09) và epic không có story. Trên đĩa: admin-be V12 app.tpp_attachment chỉ metadata, nối tpp_profile, REVOKE ALL … FROM portal_app (PO 10/09, T_iso); app.submission V5 không có cột đính kèm ⇒ portal_app không có vật mang. ⇒ PO chốt AD-30 (nội dung tệp trong PostgreSQL, bảng riêng xoá được, khoá kho db:<uuid>, PDF/JPG ≤ 10 MB theo magic bytes, không inline, quét mã độc là nợ có cổng, tải về theo T_iso + nhật ký) và hai story này.

Hai bảng đính kèm là hai thực thể, không phải một bảng dùng chung. submission_attachment gắn với đơn (tự chứa, portal_app ghi); tpp_attachment gắn với phiên bản hồ sơ chính thức (admin_app ghi, V12). Khi 2.5 tiếp nhận đơn, admin-be chép metadata sang tpp_attachment với cùng bam và cùng khoá kho — ⛔ không chép byte, một hàng tep_noi_dung phục vụ cả hai. Đó là nợ có tên của 2.5, ghi ở AD-30.

Thứ tự thi công là ba nhịp, chép nguyên cặp 1.7/2.8: portal-be mở 2.11, chốt hình dạng hai bảng trong design.md kèm lý do từng cột, chỗ chưa chắc khai là chưa chắc (tiền lệ V5 noi_dung jsonb), ghi vào issue của 1.11admin-be khai + GRANT đúng hình dạng đó, báo portal-be trước khi mergeportal-be nối adapter, đóng 2.11. Số thứ tự 21–22 là thứ tự merge, không phải thứ tự bắt đầu. Ba điều kiện cổng khởi động portal-be (quyền ngoài hợp đồng · EXECUTE qua PUBLIC · CREATE/USAGE lạ) áp nguyên — trigger giữ mốc của bảng mới phải REVOKE EXECUTE … FROM PUBLIC như V12 đã làm cho tpp_attachment_giu_moc_tao().

Thành viên trong tổ chức — HOÃN CÓ GHI (PO duyệt 07/09/2026). Mô hình một tổ chức nhiều người dùng thuộc đợt sau: Thông tư không đòi, và giai đoạn 1 mỗi tổ chức có thể chỉ cần một tài khoản. ⛔ Nhưng phép kiểm trục T_iso phải viết theo «TẬP người dùng của tổ chức», không theo «người dùng duy nhất của tổ chức» — kỳ vọng là 404 vô hình giữa hai tổ chức. Viết đúng cách ngay thì thêm thành viên sau không phải viết lại mọi phép kiểm cô lập đã ký. Màn Tổ chức phía quản trị đã có khối «Người dùng thuộc tổ chức», nên quan hệ nhiều-một là có thật trong mô hình.

Vai của người dùng trong tổ chức — CHƯA LÀM, nợ có tên OAPI-205 (openapi-platform#23; PO chốt 12/09/2026). Đo 12/09 ở năm tầng: PRD chỉ nói «nhiều Vai» cho người dùng nội bộ; spine không AD nào; app.tpp_user (V2→V12) không cột vai, không bảng vai/gán vai; portal-be không thi hành; gói design chỉ có mock hai giá trị (Người đại diện · Kỹ thuật) — nguồn hình ảnh, không phải nguồn nghiệp vụ. GĐ1: mọi người dùng cùng tổ chức quyền như nhau, cách ly giữa tổ chức bằng T_iso. ⛔ E-005 không có story vai TPP — câu «chờ nguồn vai TPP (E-005)» ở 1.10 (11/09) là trỏ vào chỗ trống, đã sửa trỏ về nợ. Trả nợ đi ba chặng theo thứ tự (mô hình ở PRD/spine → admin-be khai bảng theo AD-14, story riêng → thi hành ở portal-be + hai front-end), sớm nhất cùng lúc mở mô hình thành viên ở đoạn trên; điều kiện trả ghi trên issue.

Thứ tự trộn hai nhóm là cố ý. Phía ngân hàng (1.11.3) phải xong trước khi cổng bên thứ ba mở, vì 2.5 tiếp nhận đơn cần hồ sơ chính thức đã có schema. Nhưng 2.12.3 chạy song song được — chúng chỉ ghi bảng đơn.

Bổ sung 08/09/2026 (PO duyệt) — E-004/2.8, mắt xích THỨ HAI và là mắt xích chặn nhiều nhất. PO phát hiện: gói design đã có thiết kế đăng ký/đăng nhập cho bên thứ ba, mà bảng story không có story back-end nào cho việc đó. Đo lại, đúng: E-004/2.1 (đã archive) chỉ giao kho tài khoản + xác minh email; E-001/5.9màn và hạ tầng phiên phía giao diện của portal-fe. Toàn bộ nửa back-end — xác thực, phiên, khoá tạm, quên mật khẩu, đổi mật khẩu — không thuộc story nào.

Đăng nhập chặn mọi story phía sau nó ở cổng bên thứ ba, kể cả 2.2: nộp hồ sơ là hành động của một người đã đăng nhập. Vì thế 2.8 xếp trước 2.2; số thứ tự của các story sau dời xuống. (Cập nhật cùng ngày: 2.8 nay ở thứ tự 7, sau khi 1.7 — bảng phiên — chèn vào vị trí 6. Bảng là nguồn; con số trong đoạn văn này chỉ để đọc.)

Bổ sung 08/09/2026 (PO duyệt) — E-004/1.71.8, hai cặp khai bảng còn thiếu. Cùng dạng 1.6, phát hiện khi soát 11 epic: AD-14 buộc mọi bảng do admin-be khai, kể cả bảng portal-be ghi. - 1.7 bảng phiênAD-19 đòi phiên có trạng thái, kiểm thu hồi mỗi yêu cầu, tức phải có nơi lưu. Đo trên admin-be 2d0909b: app.tpp_user 9 cột (id · email · email_normalized · password_hash · tpp_id · email_verified_at · disabled_at · created_at · updated_at), không cột nào giữ trạng thái phiên; V1V5 không migration nào khai bảng phiên.

⚠️ Phạm vi chốt bằng số đo của portal-be trước khi mở change — «bảng phiên trong CSDL hay phiên giữ nơi khác mà vẫn thoả AD-19» là quyết định thiết kế của 2.8, không phải của story này. ⛔ Làn portal-be không trả lời khi chưa được giao 2.8: kết luận lúc đó là ra quyết định kiến trúc cho một story chưa ai giao, rồi admin-be mở story dựa trên kết luận ấy.

PHẠM VI ĐÃ CHỐT 08/09/2026 — TỐI ĐA: «khai bảng + cấp quyền». Làn portal-be (được PO cho phép trả lời) soi bốn yêu cầu của 2.8 vào schema đang có (admin-be 2d0909b, đúng ba bảng tpp_user · tpp_user_verification · submission): thu hồi phiên — không cột nào mang được; khoá tạm 3 lần/15 phút — không cột nào đếm được lần sai hay giữ mốc hết khoá; quên mật khẩu — hình dạng trùng tpp_user_verification nhưng bảng đó của xác minh email, dùng chung vẫn phải thêm cột phân loại, tức vẫn đổi schema; đổi mật khẩu — chỉ vế ghi là có sẵn. ⛔ Và vế thu hồi không có đường tránh: AD-19 cho hai hình dạng (phiên phía máy chủ hoặc token có tra danh sách thu hồi) — hình một hiển nhiên cần bảng; hình hai cần chỗ giữ danh sách, mà disabled_at chỉ phủ khoá tài khoản, còn một cột kiểu sessions_valid_from phủ được «rụng TẤT CẢ phiên» nhưng không phủ được đăng xuất một phiên — muốn huỷ đúng một phiên thì phải có định danh phiên, tức trạng thái theo từng phiên. ⇒ Dưới mọi cách đọc AD-19, 2.8 cần trạng thái mới trong CSDL. Ba mảnh trạng thái chưa tồn tại, để 1.7 ước lượng đúng kích thước: ① phiên theo từng phiên (thu hồi được) · ② đếm lần đăng nhập sai + mốc hết khoá tạm · ③ mã đặt lại mật khẩu (hash, hạn, đã dùng). ⛔ Ba mảnh không đồng nghĩa ba bảng — chia thế nào là thiết kế của 2.8, không phải của 1.7. ⚠️ Hai điều khoản cộng lại chứ không mâu thuẫn: AD-27 đã liệt «khoá ký phiên» vào danh sách bí mật đọc qua configtree (spine dòng 914), tức kiến trúc đã tính tới token có ký; nhưng AD-19 vẫn đòi tra thu hồi mỗi yêu cầuký thôi chưa đủ, vẫn cần trạng thái. ⚠️ E-004/2.8 nhiều khả năng là lần đầu dự án dựng phiênE-001/2.2 (xác thực nội bộ) chưa mở issue nào. AD-20 cấm hai đường xác thực dùng chung, nên hai bên không dùng chung bảng; nhưng bản 1.7 khai sẽ thành khuôn tham chiếu cho E-001/2.2 sau này.

HÌNH DẠNG bảng phiên do 2.8 chốt, 1.7 KHÔNG tự đoán (làn admin-be hỏi 08/09/2026, và câu hỏi đó lộ ra một lỗ trong cách xếp thứ tự). Bảng story đặt 1.7 (khai) trước 2.8 (thiết kế), nhưng cột gì, thu hồi biểu diễn thế nào, ba mảnh trạng thái chia thành mấy bảng — là quyết định thiết kế của 2.8. admin-be khai trước rồi khoá portal-be vào một hình dạng họ không chọn là lặp lại đúng lỗi 1.6 theo chiều ngược. ⇒ Thứ tự thi công thực tế là ba nhịp: 1. portal-be mở change 2.8, chốt hình dạng phiên trong design.md và gửi thẳng admin-be (ghi vào OAPI-75) — chưa viết mã nối; 2. admin-be khai bảng + GRANT theo đúng hình dạng đó, báo portal-be TRƯỚC khi merge, merge; 3. portal-be khai hợp đồng quyền trong mã, nối adapter, đóng 2.8. Số thứ tự trong bảng (1.7 = 6, 2.8 = 7) là thứ tự merge: bảng phải lên trunk trước mã dùng nó. Nó không phải thứ tự bắt đầu — 2.8 bắt đầu trước để cho 1.7 đầu vào.

Nhịp 1 là nhịp MỘT CHIỀU — ràng buộc sinh từ chính ba nhịp (làn portal-be nêu 08/09/2026). design.md của 2.8 thành đầu vào cho một migration ở repo khác, mà AD-14.1 chỉ cho THÊM. ⇒ Từ lúc admin-be merge bảng theo hình dạng portal-be giao, portal-be không sửa lại hình dạng ấy được nữa — một cột đặt sai kiểu ở nhịp 1 là nợ vĩnh viễn, nằm trong repo của người khác. Không phải lý do đổi ba nhịp; là lý do đổi việc của nhịp 1: hình dạng giao đi phải kèm lý do cho từng cột, và chỗ chưa chắc phải khai là chưa chắc chứ không im lặng chọn một kiểu. Tiền lệ để chép: V5 — cột noi_dung jsonb + noi_dung_phien_ban, admin-be khai thẳng hình dạng thật chưa biết và mã hoá cái chưa-biết thành một cột có phiên bản, thay vì đoán tám cột.

Ba điều kiện làm cổng khởi động portal-be ĐỎ — để hai bên có cùng MỘT PHÉP THỬ thay vì cùng một niềm tin (đo ở OAPI-51, postgres:18, fixture thật): 1. portal_appbất kỳ quyền nào trong tám quyền mức bảng trên một bảng ngoài hợp đồng; 2. portal_app EXECUTE được bất kỳ hàm nào ngoài hợp đồng — ⛔ kể cả khi không ai GRANT, vì PostgreSQL cấp EXECUTE cho PUBLIC mặc định trên mọi hàm mới. Đây là ca dễ vướng nhất: một migration admin-be chỉ cần CREATE FUNCTION trong lược đồ app là cổng đỏ, dù không câu GRANT nào nhắc portal_app. ⚠️ REVOKE ALL ON <bảng> không phủ hàm — phải REVOKE EXECUTE … FROM PUBLIC, hoặc báo portal-be khai vào hợp đồng. Ca T1.30: CREATE FUNCTION app.ham_la() không kèm GRANT ⇒ đỏ; mutation-bite xác nhận phép quét hàm là load-bearing (vô hiệu ⇒ 3 ca đỏ); 3. portal_appCREATE trên app, hoặc USAGE trên một lược đồ ngoài app/public. Ngược lại, một bảng mà portal_app không có quyền nào thì không xuất hiện trong tập quét — vô hình với cổng đúng nghĩa, không phải may. Đó là lý do REVOKE ALL ON app.internal_user FROM portal_appV6 an toàn.

⛔⛔ NỐI ĐUÔI LÀ LUẬT HAI CHIỀU — THU HỒI quyền cũng là thay đổi phá vỡ, y như cấp thêm (làn portal-be đo 08/09/2026; làn admin-be đã nhận vào design.md D10 của OAPI-54). Cổng khởi động của portal-be kiểm hàm hai chiều: quyền ngoài hợp đồng ⇒ ĐỎ thừa; quyền hợp đồng khai mà CSDL không còn ⇒ ĐỎ thiếu. Ca cụ thể — app.dat_updated_at() (trigger updated_at, V2) lọt EXECUTE qua PUBLIC; hợp đồng portal-be đã khai nó (DatabaseContract.java:279, «PHẢI có mặt dù repo này KHÔNG BAO GIỜ gọi nó») nên hôm nay cổng XANH. Đo ba chiều: portal_app gọi thẳng ⇒ «trigger functions can only be called as triggers»; UPDATE ⇒ trigger chạy, updated_at đổi; REVOKE … FROM PUBLIC rồi UPDATEvẫn chạy — trigger dùng quyền chủ bảng, không dùng quyền người gọi. ⇒ REVOKE an toàn, đích là admin-be REVOKE + portal-be bỏ khai. Nhưng bốn trạng thái:

CSDL hợp đồng cổng
A · chưa REVOKE khai allowed XANH — hôm nay
B · đã REVOKE vẫn khai ⛔ ĐỎ thiếu
C · đã REVOKE đã bỏ khai XANH — đích
D · chưa REVOKE đã bỏ khai ⛔ ĐỎ thừa

Đi một mình bên nào cũng rơi vào ô đỏ — nên «admin-be REVOKE trước, OAPI-51 merge sau» là đường A→B→C và ô B đỏ. Cửa sổ đỏ ấy không tồn tại chỉ nhờ một điều dễ bỏ sót: portal-be trên trunk hôm nay chưa quét hàm — phép quét ra đời cùng OAPI-51. ⇒ Luật gọn thay mọi bảng thứ tự: OAPI-51 merge SAU CÙNG. (1) admin-be merge V7 REVOKE bất cứ lúc nào, tác động bằng không — báo portal-be trước khi merge đúng nếp, nhưng là báo, ⛔ không phải chờ họ bỏ khai rồi mới merge; (2) portal-be bỏ khai chép REVOKE vào fixture cùng một commit, và chỉ SAU KHI V7 đã lên main của admin-be — bỏ sớm là lưới của chính họ rơi ô D, hai file rời nhau cũng rơi ô D; (3) OAPI-51 merge, hạ cánh thẳng ô C. (Hai làn từng viết hai bản khác nhau về bước 1–2; bản này là bản khớp với bảng bốn trạng thái — khắc để không còn hai bản.) Điều kiện triển khai đi kèm là nếp AD-14 sẵn có: bản admin-be mang V7 triển khai trước bản portal-be mang OAPI-51.

⚠️ Cập nhật cùng ngày — «bỏ khai» KHÔNG nằm trong OAPI-51 nữa. PO (ở làn portal-be) chốt đóng OAPI-51 với app.dat_updated_at() vẫn khai là bắt buộc (executeAllowed = true, đúng với hôm nay), và tách việc bỏ khai thành nợ OAPI-89 (portal-be#21) — trả khi V7 của admin-be lên trunk. ⇒ Sau khi OAPI-51 merge, hợp đồng đòi hàm đó EXECUTE được; thứ tự ba bước ở trên đọc là: V7 merge (bất cứ lúc nào) → OAPI-89 merge (bỏ khai + fixture REVOKE cùng commit, sau V7 trên main) — còn OAPI-51 merge trước cả hai vì nó khai bắt buộc, không khai bỏ.

⛔⛔ NỬA SAU — chạm quy trình TRIỂN KHAI, và nếp AD-14 hiện hành đẩy ĐÚNG VÀO CHIỀU HỎNG (làn portal-be phát hiện 08/09/2026). V7 merge vô hại — không cổng nào đọc main của admin-be. Nhưng V7 TRIỂN KHAI vào một môi trường trước khi bản portal-be mang OAPI-89 triển khai vào đó ⇒ CSDL không còn EXECUTE, hợp đồng vẫn đòi ⇒ portal-be từ chối khởi động ở môi trường ấy (ô «THIẾU»). Mà AD-14 bảo «admin-be di trú TRƯỚC»làm đúng luật hiện hành là rơi thẳng vào ô đỏ. Nửa này không suy ra được từ nửa đầu: người đọc «thu hồi là phá vỡ» vẫn có thể merge đúng thứ tự rồi triển khai theo AD-14 như mọi lần, và hỏng.

nửa đầu nửa sau
chạm quy trình merge quy trình triển khai
ai đọc làn thi công người vận hành · uat
đang ở đâu design.md D10 của OAPI-54 (sắp archive) comment của OAPI-83, OAPI-89

CẦN PO CHỐT — MỘT GÓI, không phải hai, nâng lên AD-14/AD-15: (1) merge: thu hồi một quyền đã tồn tại là thay đổi phá vỡ với repo đang khai nó, y như cấp thêm — nối đuôi hai chiều; (2) triển khai: thứ tự «admin-be trước» của AD-14 áp cho chiều THÊM schema; chiều THU HỒI quyền thì ngược — bên mất quyền triển khai trước bên thu hồi. Hai nửa vào spine cùng một lượt; vào lệch lượt thì nửa sau — đang sống trong comment của hai issue — sẽ mất.⟩

(Ghi lại cận dưới của lượt trước, vì lập luận vẫn dùng được:) làn portal-be nêu 08/09: dù đáp án là gì thì 2.8 cũng chạm một mắt xích admin-be — vai portal_app hiện chỉ có quyền trên ba bảng; phiên trong CSDL thì cần bảng mới + GRANT, phiên ngoài CSDL thì vẫn cần thu hồi kiểm được mỗi yêu cầu, tức vẫn đi qua một câu GRANT mới. ⇒ Khác nhau ở kích thước, không ở việc có hay không. Phạm vi tối thiểu của 1.7cấp quyền; tối đa là khai bảng + cấp quyền.

⛔⛔ CẶP «admin-be KHAI + portal-be NỐI» NAY CÓ THỨ TỰ BẮT BUỘC, không còn song song. OAPI-51 (portal-be) mở rộng cổng khởi động để từ chối khởi động khi vai có quyền trên bất kỳ bảng hoặc hàm nào NGOÀI hợp đồng ghim trong mã — đo trên postgres:18 với fixture thật, bốn ca âm đều bắt được, kể cả hàm lạ mà không ai GRANT (PostgreSQL cấp EXECUTE cho PUBLIC mặc định). ⇒ Từ lúc OAPI-51 lên trunk, mỗi lượt di trú của admin-be cấp thêm bất cứ thứ gì cho portal_app sẽ CHẶN KHỞI ĐỘNG portal-be cho tới khi hợp đồng ở repo họ khai nó. Đó là chủ đích, nhưng nó đổi cách xếp lịch: hai nửa của cặp phải nối đuôi, và lượt admin-be đi trước thì portal-be phải có lượt khai hợp đồng ngay sau — không để cách quãng. - 1.8 bảng phiên bản văn bản pháp lý + vết đồng ý2.7 cấm ghi đè tại chỗ và đòi ghi ai đồng ý PHIÊN BẢN NÀO, lúc nào; không story nào khai bảng giữ được nhiều phiên bản ấy.

⚠️ Ma trận quyền portal_app là một nửa của mỗi story khai bảng, không phải phần phụ — portal-be có cổng khởi động đo quyền theo cột, thiếu GRANT đúng thì nó từ chối khởi động và triệu chứng trông như lỗi của portal-be.

PO chốt 09/09/2026 — ba đáp án cho lượt explore của 2.8:

Câu Chốt
1 NFR-003 không có số — bao lâu không hoạt động thì hết phiên 15 phút (áp cả E-001/2.3)
2 FR-007 ghi vào đâu E-001/4.1 — story đã có, ⛔ không mở story mới; xem E-001
3 đổi mật khẩu và đăng xuất, gói design chưa vẽ màn làm back-end trước

⚠️ 2.8 KHÔNG chờ E-001/4.1 — nên ô «Chặn bởi» ghi Đ: (chặn-ĐÓNG) chứ không phải M:. 2.8 dựng đường nối + bản hiện thực tối thiểu và chạy tiếp; nhưng nó sinh một nợ trỏ vào 4.1, và story chỉ tính là xong khi 4.1 archive.

Cái giá của bản tối thiểu, làn portal-be khai thẳng — giữ nguyên văn: bản tối thiểu ghi ra nhật ký ứng dụng (file log xoay vòng, xoá được), thứ không thoả K2nhật ký chỉ ghi thêm, không vai nào sửa hay xoá được. FR-007 thoả ở mức «có ghi»; K2 cho bốn sự kiện này CHƯA thoả cho tới khi bản thật cắm vào bảng trong vùng audit. ⚠️ K2 là một trong bốn thứ backlog-tuan-thu.md xếp vào loại không hoãn được — hoãn thì khoảng thời gian đã chạy không cứu lại được. Nợ này vì thế có mốc trả cứng: trước khi có TPP thật kết nối.

⚠️ Nửa còn lại của NFR-003 — «xác thực lại để thao tác nhạy cảm» — CHƯA có đáp. Làn portal-be đi tiếp bằng một giả định khai rõ: giai đoạn 1 không bắt xác thực lại, vì cổng bên thứ ba chưa có thao tác nào rơi vào nhóm đó (cấp và xoay khoá thuộc E-005). ⛔ Ghi trong design.md như giả định, không như quyết định đã duyệt.

Ràng buộc đã chốt sẵn, 2.8 không được quyết lại: - Khoá tạm 3 lần / 15 phút cho cổng bên thứ ba — ⚠️ khác con số 5 lần của bề mặt quản trị, và khác biệt đó là chủ đích: hai bề mặt không cùng mức phơi (AD-29 mục 0, gói design 05/09). ⛔ Ngưỡng là cấu hình, không phải hằng số rải trong mã. - Quên mật khẩu dùng câu trung lập — ⛔ không tiết lộ một email đã tồn tại trong hệ thống hay chưa; cùng lý do 2.3 cấm tiết lộ mã số thuế đã tồn tại: đó là kênh dò. - Phiên có trạng thái, kiểm thu hồi mỗi yêu cầu (AD-19) — như bề mặt quản trị, không có ngoại lệ. - ⛔ Tách hẳn khỏi đường xác thực nội bộ (AD-20): portal_app không chạm bảng người dùng nội bộ, và ngược lại. Cùng ranh giới mà 2.1 đã dựng cho bảng tài khoản.

⚠️ E-001/5.9 (portal-fe) phụ thuộc story này — màn đăng nhập, khoá tạm, quên mật khẩu, đổi mật khẩu đều cần nửa back-end ở đây. Ghi ra vì bảng E-001 không nói 5.9 chờ ai; nếu portal-fe mở 5.9 trước khi 2.8 xong thì họ sẽ dựng giao diện cho một hợp đồng chưa tồn tại.

⚠️ 2.8 RẤT CÓ THỂ LÀ MỘT CẶP NỮA — đang đo, chưa kết luận (làn oapi-portal-be nêu 08/09/2026). AD-19 đòi phiên có trạng thái, kiểm thu hồi mỗi yêu cầu, tức phải có nơi lưu phiên. Đo trên admin-be 2d0909b: app.tpp_user9 cột, không cột nào giữ phiên; V1V5 không migration nào khai bảng phiên. ⇒ Nếu 2.8 cần bảng, nó là cặp admin-be khai + portal-be nối, đúng khuôn 1.6, và mắt xích admin-be phải mở TRƯỚC. Làn portal-be đo kỹ rồi báo trước khi viết; kết luận về tới thì bảng story bổ sung dòng tương ứng. ⛔ Đây là cách một cặp thiếu lộ ra trước khi chặn thay vì lúc đang thi công — ngược hẳn ca 1.6, nơi làn phải dừng hẳn một story để chờ.

Bổ sung 08/09/2026 (PO duyệt) — E-004/1.6, mắt xích bảng story thiếu. Làn oapi-portal-be phát hiện khi đo trước lúc mở change cho 2.2: story ấy giao cho portal-be ghi SUBMISSION, nhưng portal-be không được có dòng di trú (AD-14, cưỡng chế bằng PomInvariantsTest), và không story nào khai bảng đógrep SUBMISSION trên epics.md ra ba dòng, cả ba nằm trong chính 2.2. Spine đã trả lời sẵn câu «ai khai»: «Bảng portal-be ghi (ví dụ SUBMISSION) vẫn do admin-be khai» (AD-14). Tức đây không phải xung đột kiến trúc, mà là bảng story thiếu một dòng so với chính spine. Số thứ tự của các story từ 2.2 trở đi dời xuống một bậc.

⚠️ Ma trận quyền là nửa dễ quên nhất của 1.6. portal-be nay có cổng khởi động đo quyền theo cột (OAPI-36/OAPI-37, đã lên trunk): bảng mới mà thiếu GRANT đúng cho portal_app thì portal-be từ chối khởi động — đúng thiết kế, nhưng nó sẽ trông như lỗi của portal-be.

⚠️ Tiền lệ E-004/2.1 đã để lại đúng lỗ này và không ai thấy. OAPI-14 mở ở admin-be với trailer trỏ story E-004/2.1, nên trong bảng story 2.1 chỉ có một dòng, service portal-be — phần việc admin-be khai bảng vô hình với mọi phép đo, kể cả tool/epic-status.sh. Nó archive rồi nên không lộ; lần này lộ vì việc chưa làm. ⇒ Từ nay việc khai bảng cho một service khác là một STORY, không phải một issue kèm theo.

Bổ sung 11/09/2026 tối (PO chốt từng mục — UU-TIEN-GD1 §G). Ba việc chạm epic này:

  • P4 — tách 2.4. Nửa đăng ký chỉ cần 2.1 (đã archive) + 5.6 (đã archive) + khung văn bản 2.6; nửa nộp hồ sơ cần 2.2portal-be chưa bắt đầu. Gộp thì B1 chờ cả chuỗi nộp hồ sơ. 2.9 mang M:2.4 vì tuyến hồ sơ đi từ tài khoản đã kích hoạt.
  • P2 — A3 chỉ xem. PO chọn mức thấp nhất trong bốn phương án (xem · xem + khoá/mở · đúng gói xem
  • gán vai · hoãn). Lý do: «gán vai trong tổ chức» chưa có nguồn ở tầng nào (~~vai TPP thuộc E-005, chưa story khai bảng~~ — đính chính 12/09: E-005 không có story vai TPP; nợ trỏ về OAPI-205, openapi-platform#23) nên lấy đúng gói là lặp lại ca ba cột của E-001/5.11; khoá/mở kéo E-001/4.13.1 vào đường găng A3. Hai phần bỏ là nợ có tên, ⛔ không phải cắt phạm vi.
  • P6 — BÁC (ghi ở E-005): đơn khai ứng dụng chỉ sau khi tổ chức được duyệt ⇒ chuỗi A5 (1.11.21.32.5) nằm trên đường găng của B3.

Các nhóm việc (feature)

Hệ Admin

Hệ Portal