№ 51
Trợ lý AI tư vấn tài chính (bản mô phỏng) trên ví MoMo, thiết kế theo đúng cách người Việt thật sự quyết định vay — ưu tiên tốc độ và sự an tâm hơn là so lãi suất — và không bao giờ để AI tự sinh ra một con số tiền nào.
Ví điện tử tại Việt Nam đã trở thành kênh phân phối tín dụng chính cho một nhóm dân số chưa từng trải qua một chu kỳ tín dụng có kỷ luật nào: chỉ khoảng 4% dân số có thẻ tín dụng, trong khi thị trường BNPL tăng từ 1,32 tỷ USD (2023) lên dự báo 6,89 tỷ USD (2029, CAGR 29,2%). Nợ xấu cho vay tiêu dùng đã tăng gần gấp đôi trong cùng giai đoạn (từ ~2% lên 3,7%), nợ xấu toàn hệ thống từ 2,03% lên 4,55%. 61% người dùng ví đang giữ từ 2 ví trở lên, 2/3 dùng ví ít nhất hàng tuần, và 57% dự định tăng sử dụng trong 6 tháng tới — nhu cầu tín dụng số không chậm lại trong khi phần lớn người vay chưa có công cụ nào để tự đánh giá một khoản vay có phù hợp với mình hay không.
MoMo bản thân không tự cho vay, không tự bán bảo hiểm, không tự quản lý quỹ — nó là kênh phân phối cho hàng chục đối tác thật (ngân hàng, công ty tài chính, công ty bảo hiểm, công ty quản lý quỹ) trải trên nhiều nhóm sản phẩm hoàn toàn khác chất nhau: một khoản vay tiêu dùng, một thẻ tín dụng, một gói tích luỹ và một hợp đồng bảo hiểm không đo bằng cùng một đơn vị. Người dùng phải tự đọc, tự so, tự hiểu — trong khi tài liệu bảo vệ người tiêu dùng của Bộ Công Thương ghi nhận: khiếu nại tín dụng tiêu dùng phần lớn không đến từ lãi suất cao, mà từ việc không được cho biết trước — lãi suất không nói rõ, hợp đồng đến chậm, thu thập danh bạ không nói rõ mục đích, đòi nợ quá mức.
Tổng hợp 5 nghiên cứu định lượng về hành vi vay tại Việt Nam (n = 1.743, gồm khách hàng cá nhân tại TP.HCM và BIDV, công nhân Biên Hoà, sinh viên dùng P2P lending, người dùng Fintech, lao động phổ thông) cho một kết luận ngược trực giác:
| Yếu tố tác động đến quyết định vay | Điểm chuẩn hoá (0–100) | Số nghiên cứu đo |
|---|---|---|
| Động cơ / nhu cầu thực | 100 | 1 |
| Lợi ích cảm nhận | 92 | 2 |
| Thủ tục & tốc độ | 71 | 4 |
| Ảnh hưởng xã hội | 71 | 2 |
| Niềm tin & thương hiệu | 64 | 4 |
| Thông tin & truyền thông sản phẩm | 62 | 2 |
| Trải nghiệm & tư vấn | 59 | 3 |
| Chi phí thực (lãi & phí) | 57 — gần cuối bảng | 2 |
| Rủi ro cảm nhận |
| −24 — hệ số âm |
| 1 |
Ba hệ quả trực tiếp cho thiết kế agent:
Persona dựng từ hành vi và bối cảnh trong dữ liệu nghiên cứu, không từ nhân khẩu học đơn thuần — dùng để quyết định agent nên hỏi gì, hỏi bao nhiêu câu, và cảnh báo ở đâu:
| Persona | Bối cảnh | Agent phải |
|---|---|---|
| "Gấp" — vay khẩn cấp | Lao động phổ thông, thu nhập 5–10 triệu, quyết định trong một phiên, chọn theo thương hiệu quen | Hỏi tối đa vài câu trước khi ra đề xuất đầu tiên; luôn có phương án khi không đủ điều kiện — đây là nhóm dễ rơi vào tín dụng đen nhất nếu bị từ chối mà không có lối thoát |
| "Tính" — mua trả góp có kế hoạch | Nhân viên văn phòng, thu nhập ổn định, thực sự đọc bảng so sánh | Bảng so sánh đầy đủ, quy tất cả về "tổng tiền phải trả", tách riêng cột phí ẩn |
| "Thử" — vay lần đầu | Sinh viên/mới đi làm, chưa có lịch sử tín dụng (thuộc nhóm ~96% chưa có thẻ tín dụng) | Giáo dục tài chính chèn đúng lúc, một câu, gắn với con số của chính họ — không phải bài giảng |
| "Xoay" — tiểu thương (giả thuyết, chưa có dữ liệu trực tiếp) | Bán hàng online, vay vốn lưu động lặp lại theo chu kỳ | Cần "trí nhớ nhu cầu" nhất trong 4 persona — nhớ chu kỳ vay, cảnh báo khi tần suất tăng bất thường |
Trợ lý hội thoại tiếng Việt trong ví điện tử, tư vấn đủ 5 nhóm sản phẩm bằng dữ liệu thật, đã dẫn nguồn — không phải catalog giả lập. Mỗi đề xuất luôn gắn đúng tên tổ chức cấp tín dụng/bảo hiểm/quản lý quỹ thật — không bao giờ giấu sau nhãn "đối tác của MoMo", vì niềm tin của người dùng ví gắn với thương hiệu cụ thể như phát hiện 1.2(3) ở trên đã chỉ ra.
LLM không được sinh ra bất kỳ con số tiền/lãi/phí nào. Ranh giới này cưỡng chế ở tầng dữ liệu, không chỉ ở tầng prompt: kho tri thức RAG loại trừ sẵn mọi tài liệu chứa giá/lãi/phí ngay từ khâu chunk hoá, nên kể cả khi LLM hỏng cũng không có nguyên liệu để bịa số. Repositories đọc số từ PostgreSQL, không bao giờ đọc số từ vector store — vector store chỉ giữ văn bản pháp lý và điều khoản.
| # | Chốt | Việc | Hỏng thì sao |
|---|---|---|---|
| ① | Chặn injection | Regex trên văn bản đã chuẩn hoá (bỏ dấu, gấp ký tự thay thế) — chạy trước khi gọi LLM | Trả câu mẫu, 0 token |
| ② | Phân giải phiên | Mỗi phiên chat gắn owner; sai chủ sở hữu → cấp phiên mới, không dùng phiên cũ | Không ai đọc được dữ liệu của người khác |
| ③ | Nạp sổ cái (ToolLedger) | Ghi trước số liệu đã có nguồn hợp lệ: số user tự khai, kết quả tool lượt trước | Nhắc lại "bạn muốn vay 30 triệu" là xác nhận, không phải bịa |
| ④ | Vòng lặp ReAct (≤ 6 bước) | LLM chọn 1 trong 6 công cụ, tham số qua schema Pydantic có biên cứng (1–500 triệu, 1–60 tháng) | Quá 6 bước → trả câu mặc định; mô hình đề xuất, schema định đoạt |
| ⑤ | Tầng nghiệp vụ — 0 lệnh gọi LLM | điều kiện cứng → tính bằng Decimal (không float) → kiểm soát rủi ro (DTI) → xếp hạng | Lỗi tính → mã lý do CALCULATION_ERROR, không để LLM tính thay |
| ⑥ | Guard số | Mọi token tiền/% trong câu trả lời phải truy về được một giá trị tool đã trả trong lượt, đối chiếu theo loại đại lượng (tiền chỉ so với tiền, % chỉ so với %) | Bỏ câu của model, render lại bằng template — số vẫn đúng, văn phong kém hơn |
| ⑦ | Guard mệnh đề | Chặn các lời hứa bị cấm: "chắc chắn được duyệt", "đảm bảo giải ngân", "hồ sơ bạn ổn rồi" | Độc lập với chốt ⑥ — một câu có số đúng mà hứa duyệt vẫn bị chặn, vì câu nguy hiểm nhất là câu không có số để mà truy |
Thứ tự trong chốt ⑤ cố định và không đổi được: điều kiện cứng chạy trước tính (người chưa đủ tuổi phải nghe "chưa đủ tuổi" ngay, không phải sau khi bị hỏi hết bảng lương); kiểm soát rủi ro chạy sau tính (DTI cần khoản trả hàng tháng, là đầu ra của máy tính); xếp hạng chạy cuối, chỉ trên ứng viên đã đạt điều kiện. Trọng số xếp hạng cố định và có version: khả năng chi trả 35% · tổng chi phí 30% · độ khớp nhu cầu 25% · độ linh hoạt 10%. Hoà điểm thì gói tổng chi phí thấp hơn thắng; vẫn hoà thì sắp theo mã sản phẩm — không có bước nào ngẫu nhiên.
Dữ liệu là 10 sản phẩm thật của 11 đối tác (data_origin=PUBLISHED_REFERENCE), lấy từ công bố công khai — không phải dữ liệu mock:
| Nhóm | Sản phẩm thật trong hệ thống | Đối tác pháp lý | Xếp theo | Cảnh báo đặc thù |
|---|---|---|---|---|
| Vay tiêu dùng | Vay Nhanh · Vay Home Credit | MCredit · Home Credit VN | Tổng chi phí + APR + DTI | Gói bị loại kèm mã lý do |
| Trả góp | Ví Trả Sau · Trả Góp Flik | TPBank · M-Flik | Tổng chi phí + APR + DTI | Gói bị loại kèm mã lý do |
| Thẻ tín dụng | TPBank MoMo Visa Platinum · BVBank JCB Link | TPBank · BVBank | Chi phí khi trả đủ đúng hạn | Chi phí nếu không trả đủ — phí ẩn lớn nhất của thẻ |
| Tích luỹ | Túi Thần Tài · Tiết Kiệm Online | Finsight/TVAM (lưu ký Vietcombank) · BVBank | Lợi tức thực nhận — cao hơn = tốt hơn, ngược chiều mọi nhóm khác | Không có bảo hiểm tiền gửi, khác hẳn tiền gửi ngân hàng |
| Bảo hiểm | MoMoCare Sức khoẻ+ · Bảo hiểm Max (gói Bạch Kim) | Chubb Life · Manulife | Tổng phí cả kỳ hạn | Thời gian chờ; sản phẩm chưa công bố phí vẫn hiện nhưng không bịa số |
Toàn bộ 11 đối tác (kể cả MoMo với vai trò trung gian) được đối chiếu chéo giữa trang chính thức momo.vn, biểu phí đối tác và báo chí uy tín trước khi đưa vào catalog — mọi khoảng trống hoặc mâu thuẫn giữa nguồn (ví dụ lãi suất thẻ BVBank JCB Link: 2,71%/tháng theo trang MoMo vs 3,58%/tháng theo biểu phí BVBank) được ghi lại rõ ràng thay vì chọn liều một con số.
Hệ thống dựng hai gate bắt buộc trước khi một hồ sơ được coi là hoàn tất, đúng yêu cầu "cấm bypass HITL" của đề bài:
APPROVE · REJECT · REQUEST_INFORMATION · ESCALATE. Reviewer không được sửa dữ liệu người dùng hay override một sản phẩm hard-ineligible; "Approve" chỉ chuyển sang bước nộp mô phỏng, không đồng nghĩa phê duyệt tín dụng thật.Vòng đời một hồ sơ đi qua 8 trạng thái tường minh (DRAFT → ADVISED → USER_CONFIRMED → PENDING_HUMAN_REVIEW → NEEDS_INFO/APPROVED/REJECTED → SIMULATED_SUBMITTED), mỗi thay đổi ghi audit với vai trò người thực hiện (CUSTOMER, HUMAN_REVIEWER, PRODUCT_ADMIN, AUDITOR_COMPLIANCE, hoặc SYSTEM). Thay đổi dữ liệu người dùng, version sản phẩm, rule hay kết quả tính toán làm confirmation/approval cũ hết hiệu lực ngay, buộc xác nhận lại từ đầu.
RBAC 4 vai trò (CUSTOMER, HUMAN_REVIEWER, PRODUCT_ADMIN, AUDITOR_COMPLIANCE) tách bạch quyền: khách hàng chat và xác nhận, reviewer duyệt hàng đợi, admin quản lý danh mục/version, auditor xem read-only cho mục đích compliance. Rule engine đánh giá rủi ro tín dụng theo dữ liệu CIC mô phỏng — nợ nhóm 2 tạo cảnh báo, nợ nhóm 3–5 hoặc đang bị nhắc nợ/thu hồi chặn cứng sản phẩm, trễ hạn ≥3 lần trong 12 tháng tạo cảnh báo riêng — độc lập với eligibility theo sản phẩm.
Bảo mật có một bộ 172 test riêng (34 test guard số/mệnh đề/injection, 7 test phân tách phiên, 10 test rate limit) — mỗi test tương ứng một chuỗi tấn công đã đo là lọt qua được trước khi vá, không phải giả định lý thuyết.
bkai-foundation-models/vietnamese-bi-encoder), không gọi API ngoài cho bước này.AGENT_MODE=rules chuyển sang router quy tắc thuần, không cần OpenAI API key — demo xuống cấp về văn phong chứ không chết hoàn toàn.1.045 unit test, 100% pass.
Bộ eval hành vi 126 case, chia 3 tầng theo cách chấm (không theo chủ đề, để tách bạch "tính sai" khỏi "diễn đạt khác"):
| Tầng | Số case | Chấm bằng gì | Ngưỡng | Kết quả 24/08/2026 |
|---|---|---|---|---|
| A — tất định | 66 | Đáp án dựng sẵn từ công cụ tính + tên mục glossary | 100% | 66/66 (100%) |
| B — hành vi | 43 | Loại hành vi + ràng buộc nội dung (must_include/must_not_include) | ≥85% | 43/43 (100%) |
| C — nhiều lượt | 17 | Con số của lượt trước còn sống ở lượt sau | ≥80% | 17/17 (100%) |
Đây là lần đầu cả ba tầng cùng đạt tuyệt đối. Đáp án tầng A bị "đóng băng" (không tính lại lúc chạy) và có cơ chế tự phát hiện lệch — cơ chế này ra đời sau một sự cố thật: một khoản phí trả góp đổi trong công cụ tính ngày 19/08 mà đáp án đóng băng ngày 22/08 không mang theo, khiến tầng A báo 66/66 ba lần liên tiếp trong khi ứng dụng thiếu đúng 5.400.000đ so với đáp án đang dùng để chấm — hai cái sai giống nhau so ra bằng nhau. Từ đó, dựng lại đáp án dừng lại khi phát hiện số liệu đổi, chỉ ghi đè khi chạy với cờ xác nhận rõ ràng.
Chặn injection 100% ở cả chỉ số offline (ngưỡng chặn merge) lẫn 5 case injection riêng trong tầng A — kể cả các biến thể không dấu, leetspeak, diễn đạt lại.
Không bịa số: 100%, thực thi bằng guard chốt ⑥ trên mọi câu trả lời, không phải một mục tiêu đo bằng mẫu.
Runner loại các case lỗi do giới hạn tốc độ nhà cung cấp API khỏi mẫu số thay vì tính là trượt, để tránh nhầm lỗi hạ tầng với tín hiệu chất lượng thật.
Đã deploy trên Google Cloud Run, health check trả {"status":"ok","env":"production"}.
/login có thể bị vượt qua bằng cách đổi header mỗi request — điểm yếu đã biết, chưa vá, ghi công khai trong tài liệu bảo mật thay vì che giấu.Đây là những bước tiếp theo chúng tôi đề xuất, sắp theo mức độ cấp thiết đối với người dùng và doanh nghiệp, không phải theo độ khó kỹ thuật — để anh/chị dễ quyết định nên đầu tư thời gian vào đâu trước.
Nên làm ngay, trước khi mở rộng cho nhiều người dùng hơn
Nên làm trong giai đoạn thử nghiệm có người dùng thật
Duy trì lâu dài, không phải làm một lần rồi thôi