LLMOps 2 — Kiến trúc ứng dụng LLM

13 thg 7, 2026 2 lượt xem
#ai
#rag
#llmops
#agents
#architecture

Chọn kiến trúc: câu hỏi trước cả câu hỏi model

Bài LLMOps 1 — Tổng quan đặt vấn đề đưa LLM vào production một cách an toàn. Trước khi bàn prompt guardrail hay đánh giá, có một quyết định gốc thường bị bỏ qua: ứng dụng của bạn thuộc mẫu kiến trúc nào? Người mới thường mặc định "AI = chatbot đa năng trả lời mọi thứ", rồi lắp một agent tự chủ vào bài toán mà một prompt phân loại đơn giản đã thừa sức xử lý. Kết quả: hệ thống đắt, chậm, khó test, và không ai kiểm soát được nó làm gì.

Thực tế, phần lớn giá trị LLM trong ngân hàng đến từ các mẫu đơn giản và có kiểm soát, không phải từ agent tự chủ. Bài này trải ra một phổ kiến trúc bốn nấc — từ prompt đơn đến agent — kèm tiêu chí chọn nấc phù hợp, rồi bàn các thành phần kỹ thuật cắt ngang (function calling, structured output, orchestration, build-vs-buy, quản lý context, fallback). Nguyên tắc xuyên suốt: dùng cái đơn giản nhất đủ dùng (use the simplest thing that works).

Mọi ví dụ dùng họ model Claude của Anthropic qua SDK chính thức anthropic (Opus 4.8 claude-opus-4-8, Sonnet 4.6 claude-sonnet-4-6, Haiku 4.5 claude-haiku-4-5), nhưng nguyên tắc kiến trúc thì độc lập với nhà cung cấp.

Phổ bốn nấc kiến trúc

Càng sang phải, khả năng xử lý bài toán phức tạp/mở càng lớn, nhưng đổi lại mất dần khả năng kiểm soát, tăng chi phí token, tăng độ trễ, khó test và khó audit hơn. Ngân hàng nên nghiêng về phía trái nhất có thể.

Nấc 1 — Prompt đơn (zero/few-shot)

Một lần gọi model, không có bước trước sau, không tra cứu bên ngoài. Đầu vào cố định → đầu ra cố định. Đây là mẫu rẻ nhất, nhanh nhất, dễ test và dễ kiểm soát nhất.

Phù hợp khi tác vụ đóng, tự chứa và kiến thức cần thiết đã nằm trong prompt hoặc trong tham số model:

  • Phân loại (classification): định tuyến email khách hàng vào nhóm (khiếu nại / tra cứu / mở tài khoản / gian lận nghi ngờ).
  • Tóm tắt (summarization): rút gọn một biên bản họp, một đoạn hội thoại tổng đài.
  • Trích xuất (extraction): lấy số CIF, số tiền, ngày từ một đoạn text tự do thành JSON.

Zero-shot là chỉ mô tả nhiệm vụ; few-shot là kèm 2–5 ví dụ mẫu ngay trong prompt để "kéo" model vào đúng định dạng và tiêu chí. Với phân loại nghiệp vụ, few-shot thường tăng độ ổn định đáng kể mà không cần fine-tune. Chi tiết kỹ thuật viết prompt xem LLMOps 3 — Prompt & guardrail.

Nấc 2 — Workflow / prompt chaining (chuỗi bước cố định)

Khi một lần gọi không đủ, ta chia bài toán thành các bước cố định do CODE điều khiển, mỗi bước có thể là một lần gọi LLM. Điểm mấu chốt phân biệt với agent: luồng đi được quyết định trước bởi lập trình viên, không phải bởi model. Model chỉ điền vào chỗ trống của từng bước.

Các dạng workflow phổ biến:

DạngMô tảVí dụ ngân hàng
ChainingBước sau nhận đầu ra bước trướcTrích xuất → chuẩn hóa → sinh phản hồi
RoutingPhân loại trước, rồi rẽ nhánh xử lý chuyên biệtPhân loại email → gọi prompt tương ứng từng loại
ParallelChạy nhiều lời gọi độc lập rồi tổng hợpChấm 3 tiêu chí rủi ro song song → gộp điểm
Gate/kiểm traMột bước LLM/rule kiểm tra trước khi cho bước tiếpKiểm PII trước khi lưu, chặn nếu vi phạm

Đây nên là mặc định cho hầu hết ứng dụng LLM nghiêm túc trong ngân hàng. Mỗi bước quan sát được, log được, test được độc lập; khi lỗi bạn biết chính xác bước nào hỏng; và luồng nghiệp vụ nằm trong tay code — thứ đã có sẵn quy trình review, versioning, CI/CD. Bạn được phần lớn sức mạnh của LLM mà giữ được kỷ luật kỹ thuật phần mềm.

Nấc 3 — RAG (Retrieval-Augmented Generation)

Prompt và workflow đều giả định kiến thức cần thiết đã có sẵn. Khi cần trả lời dựa trên tri thức nội bộ / cập nhật / lượng lớn mà không thể nhồi hết vào prompt, ta dùng RAG: tìm các đoạn tài liệu liên quan rồi nhồi vào ngữ cảnh trước khi để model sinh câu trả lời.

Dùng RAG khi:

  • Cần trả lời từ kho tri thức nội bộ: quy định tín dụng, quy trình vận hành, văn bản pháp lý, FAQ sản phẩm.
  • Kiến thức thay đổi theo thời gian — không muốn (và không thể) fine-tune lại mỗi lần cập nhật.
  • Cần chống ảo giác (hallucination) và trích nguồn (citation) để cán bộ nghiệp vụ kiểm chứng.

RAG bản chất vẫn là một workflow: truy vấn → embed → tìm kiếm vector → rerank → nhồi context → sinh. Nó không tự chủ, luồng vẫn do code điều khiển. Chi tiết retrieval xem Vector DB 7 — Retrieval cho RAGLLM 4 — RAG. Trong phổ này, RAG là "workflow có thêm bước lấy tri thức".

Nấc 4 — Agent (LLM tự quyết hành động)

Nấc cao nhất: model tự quyết định làm gì tiếp theo — gọi tool nào, với tham số gì, có cần gọi tiếp không — qua nhiều vòng lặp (agentic loop) cho tới khi tự cho là xong. Luồng đi không cố định; chính LLM lái nó.

Agent mạnh khi bài toán mở, nhiều bước, không đoán trước được đường đi: điều tra một cảnh báo gian lận cần tra chéo nhiều nguồn, gỡ rối một sự cố dữ liệu. Nhưng cái giá rất thực:

  • Khó kiểm soát: mỗi lần chạy có thể đi một đường khác nhau → khó test, khó tái lập.
  • Đắt và chậm: mỗi vòng là một lần gọi model kèm toàn bộ lịch sử → token tích lũy nhanh, độ trễ cộng dồn.
  • Rủi ro an toàn: model có thể gọi tool sai, lặp vô hạn, hoặc bị prompt injection lái vào hành động ngoài ý muốn (xem LLMOps 4 — Bảo mật & injection).

Nguyên tắc dùng agent trong ngân hàng: thận trọng, giới hạn cứng. Chi tiết cơ chế agentic loop và MCP xem LLM 5 — Tool use & agents. Ràng buộc tối thiểu:

  • Giới hạn số vòng lặp (max iterations) — chặn lặp vô hạn.
  • Whitelist tool hẹp — chỉ cấp đúng tool cần, ưu tiên tool chỉ đọc; mọi hành động ghi/giao dịch phải qua bước con người duyệt (human-in-the-loop).
  • Ngân sách token/thời gian cho mỗi phiên.
  • Log đầy đủ mọi lời gọi tool để audit — xem LLMOps 6 — Observability & chi phí.

Nguyên tắc thép: đơn giản nhất đủ dùng

Với mỗi bài toán, hãy đi từ trái sang phải của phổ và dừng lại ở nấc đầu tiên giải quyết được:

Đừng chọn agent vì "nghe hiện đại". Một trợ lý tra cứu quy định gần như luôn nên là RAG (workflow), không phải agent: đường đi cố định, dễ trích nguồn, dễ kiểm soát. Chỉ leo lên nấc agent khi bạn thật sự cần khả năng tự quyết mà workflow không mô tả nổi — và khi đã có đủ observability để giám sát nó.

Function calling & structured output

Để LLM tích hợp vào hệ thống thay vì chỉ sinh văn xuôi, hai kỹ thuật là trụ cột.

Structured output buộc model trả về đúng định dạng máy đọc được (thường là JSON theo schema định trước), để code hạ nguồn parse an toàn không cần bóc chuỗi bằng regex. Ví dụ minh họa cho tác vụ phân loại email (JSON schema, không phải SQL chạy được):

{
  "name": "phan_loai_email",
  "input_schema": {
    "type": "object",
    "properties": {
      "loai":     { "type": "string",
                    "enum": ["khieu_nai","tra_cuu","mo_tai_khoan","gian_lan"] },
      "do_khan":  { "type": "string", "enum": ["thap","trung","cao"] },
      "so_cif":   { "type": ["string","null"] },
      "tom_tat":  { "type": "string", "maxLength": 200 }
    },
    "required": ["loai","do_khan"]
  }
}

Khai báo enum rất quan trọng: nó ràng buộc không gian đầu ra, tránh model bịa ra nhãn lạ mà code không xử lý được. Kết quả trả về khớp schema nên map thẳng vào bảng/hàng đợi được.

Function/tool calling là cùng cơ chế đó nhưng dùng để model yêu cầu ứng dụng chạy một hàm. Bạn khai báo tool (tên, mô tả, schema tham số); khi model quyết định cần, nó trả về một yêu cầu gọi có cấu trúc; ứng dụng của bạn thực thi rồi gửi kết quả lại. Model là bộ não, ứng dụng là đôi tay — ranh giới này là nền tảng bảo mật. Ngay cả trong workflow (không phải agent), structured output/tool calling là cách sạch nhất để LLM giao tiếp với phần còn lại của hệ thống.

Orchestration: framework hay tự viết?

Khi luồng có nhiều bước, câu hỏi là dùng framework điều phối (LangChain, LlamaIndex...) hay tự viết bằng code thuần gọi SDK.

Tiêu chíFrameworkTự viết
Tốc độ dựng prototypeNhanh, nhiều abstraction sẵnChậm hơn lúc đầu
Kiểm soát chi tiếtBị che sau abstractionToàn quyền
Debug khi lỗiKhó lần qua nhiều lớpDễ, stack rõ ràng
Phụ thuộc bên ngoàiThêm dependency, đổi API thường xuyênÍt, chỉ SDK model
Phù hợpỨng dụng phức tạp, đội quen toolLuồng đơn giản, cần kiểm soát chặt

Kinh nghiệm thực chiến: với các workflow đơn giản đến vừa — vốn chiếm đa số ca ngân hàng — tự viết một vòng lặp gọi SDK thường sạch và dễ kiểm soát hơn. Framework hữu ích khi cần nhiều connector/abstraction sẵn và đội đã thành thạo. Đừng để abstraction của framework che mất thứ bạn cần audit.

Build vs Buy & API vs Self-host

Hai trục quyết định lớn về hạ tầng, đặc biệt nhạy với ngân hàng vì dữ liệu nhạy cảm và tuân thủ.

Build vs Buy: tự dựng toàn bộ (thu thập dữ liệu, fine-tune, phục vụ model) hay mua/dùng dịch vụ có sẵn. Với hầu hết ứng dụng, buy khả năng nền (model) + build phần logic nghiệp vụ là cân bằng tốt: không ai muốn tự huấn luyện một mô hình nền chỉ để phân loại email.

API vs Self-host — quan trọng nhất với ngân hàng:

Yếu tốDùng API (managed)Self-host mô hình mở
Chất lượng modelThường cao nhất (model frontier)Tùy model mở, thường thấp hơn
Chi phí ban đầuThấp, trả theo dùngCao (GPU, vận hành)
Data residencyDữ liệu rời hạ tầng ngân hàngỞ lại hoàn toàn trong nội bộ
Kiểm soát/tuân thủPhụ thuộc cam kết nhà cung cấpToàn quyền
Công sức vận hànhThấpCao (MLOps, scaling, patch)

Với dữ liệu nhạy cảm (thông tin khách hàng, giao dịch), lựa chọn thường là:

  1. Self-host mô hình mở trong VPC/hạ tầng nội bộ khi yêu cầu data residency và tuân thủ đặt dữ liệu không được rời khỏi ngân hàng.
  2. API có cam kết hợp đồng: nhà cung cấp cam kết không lưu / không train trên dữ liệu, có tùy chọn triển khai riêng (private/dedicated deployment) trong vùng địa lý phù hợp.

Đây là đánh đổi bốn chiều chi phí ↔ chất lượng ↔ kiểm soát ↔ tuân thủ, không có lời giải chung — phải quyết theo mức nhạy cảm dữ liệu của từng use case và ràng buộc pháp lý. Xem thêm LLMOps 8 — Nền tảng LLM cho ngân hàng.

Quản lý context window

Context window là giới hạn số token model xử lý được trong một lần gọi (prompt + đầu ra). Nó là tài nguyên hữu hạn và tốn tiền theo token — quản lý context là kỹ năng vận hành cốt lõi:

  • RAG: chỉ nhồi các đoạn liên quan nhất (top-k sau rerank), không nhồi cả tài liệu — vừa tiết kiệm token, vừa giảm nhiễu khiến model lạc.
  • Agent/hội thoại dài: lịch sử phình theo mỗi vòng. Cần tóm tắt cuộn (rolling summary) hoặc cắt bớt các lượt cũ để không tràn window và không đốt token vô ích.
  • Đặt ngân sách token cho mỗi phiên và giám sát chi phí (xem LLMOps 6).

Context dài không phải lúc nào cũng tốt: nhồi quá nhiều thông tin không liên quan có thể làm loãng tín hiệu và giảm chất lượng trả lời.

Fallback & xử lý lỗi

Ứng dụng production phải giả định model sẽ thỉnh thoảng lỗi: timeout, quá tải (rate limit), trả JSON sai định dạng, hoặc từ chối trả lời. Không xử lý các ca này là lỗ hổng vận hành nghiêm trọng. Các cơ chế tối thiểu:

  • Timeout + retry với backoff (chờ tăng dần) cho lỗi tạm thời/quá tải.
  • Validate structured output: nếu JSON không khớp schema → thử lại (có thể kèm thông báo lỗi cho model tự sửa) hoặc rơi về xử lý mặc định.
  • Fallback theo tầng: ví dụ Sonnet lỗi → thử lại → nếu vẫn lỗi thì chuyển sang hàng đợi xử lý thủ công (con người), không bao giờ trả câu bịa cho khách.
  • Circuit breaker: khi nhà cung cấp gặp sự cố kéo dài, ngắt mạch để không dồn lỗi.

Với ngân hàng, nguyên tắc vàng: thà không trả lời còn hơn trả lời sai. Mọi đường fallback nên dẫn về "chuyển cho người" chứ không phải "đoán bừa".

Use case thực tế

Đội Vận hành số NCB cần hai ứng dụng LLM. Việc chọn đúng mẫu kiến trúc cho từng cái quyết định chi phí và độ an toàn.

Ứng dụng A — Trợ lý tra cứu quy định tín dụng. Cán bộ hỏi "điều kiện giải ngân khoản vay tiêu dùng dưới 500 triệu là gì?". Kiến thức nằm trong ~2.000 trang văn bản nội bộ, cập nhật hàng quý, và bắt buộc trích nguồn để cán bộ kiểm chứng.

  • Kiến trúc chọn: RAG (nấc 3, workflow). KHÔNG dùng agent — đường đi cố định, không cần model tự quyết.
  • Luồng: câu hỏi → embed → tìm top-20 đoạn → rerank còn top-5 → nhồi context (giới hạn ~4k token) → Sonnet 4.6 sinh câu trả lời kèm trích dẫn số điều/trang.
  • Guardrail: prompt ràng buộc "chỉ trả lời dựa trên tài liệu; nếu không có, nói không tìm thấy". Fallback: nếu retrieval không đủ tự tin → trả "không tìm thấy, vui lòng liên hệ phòng Tín dụng".
  • Kết quả minh họa: ~1.500 truy vấn/ngày, chi phí thấp vì mỗi query 1 lần gọi model; độ trễ ~2–3 giây; mọi câu đều có nguồn để audit.

Ứng dụng B — Phân loại & định tuyến yêu cầu khách hàng. ~8.000 email/tin nhắn/ngày cần phân loại (khiếu nại / tra cứu / mở tài khoản / nghi gian lận) và định mức khẩn để đẩy vào đúng hàng đợi.

  • Kiến trúc chọn: Prompt đơn (nấc 1) + structured output, tối đa gói trong workflow routing nhỏ. KHÔNG RAG, KHÔNG agent.
  • Luồng: mỗi email → 1 lần gọi Haiku 4.5 (rẻ, nhanh) với few-shot + JSON schema (loai, do_khan, so_cif) → code đẩy vào hàng đợi theo loai.
  • Fallback: JSON sai schema → retry 1 lần → vẫn sai thì gắn nhãn can_review cho người xử lý.
  • Kết quả minh họa: dùng model rẻ nhất vì tác vụ đóng; các ca nghi_gian_lando_khan=cao tự động ưu tiên, cắt thời gian phản hồi khiếu nại đáng kể.

Điểm rút ra: cùng một đội, hai ứng dụng, hai nấc kiến trúc khác nhau — và không cái nào cần agent. Chọn đúng nấc quan trọng hơn chọn model xịn.

Ghi nhớ

  • Phổ kiến trúc bốn nấc: prompt đơn → workflow → RAG → agent. Càng sang phải càng linh hoạt nhưng càng mất kiểm soát, đắt và rủi ro hơn.
  • Nguyên tắc thép: dùng cái đơn giản nhất đủ dùng. Dừng ở nấc đầu tiên giải quyết được bài toán.
  • Workflow (chuỗi bước do code điều khiển) nên là mặc định cho ngân hàng: quan sát được, test được, audit được, luồng nằm trong tay code.
  • RAG khi cần tri thức nội bộ/cập nhật + chống ảo giác + trích nguồn — bản chất vẫn là workflow, không tự chủ.
  • Agent (LLM tự quyết nhiều vòng) chỉ dùng thận trọng, với giới hạn cứng: max vòng lặp, whitelist tool hẹp (ưu tiên chỉ đọc), ngân sách token, log đầy đủ, human-in-the-loop cho hành động ghi.
  • Structured output + function calling (JSON schema, enum) là cách sạch để LLM tích hợp vào hệ thống; tránh regex bóc chuỗi.
  • Orchestration: với luồng đơn–vừa, tự viết code gọi SDK thường dễ kiểm soát và debug hơn framework.
  • API vs self-host là đánh đổi chi phí ↔ chất lượng ↔ kiểm soát ↔ tuân thủ; dữ liệu nhạy cảm → self-host mô hình mở hoặc API cam kết không lưu/không train + triển khai riêng theo data residency.
  • Quản lý context window (top-k, rolling summary), đặt ngân sách token; và luôn có fallback dẫn về "chuyển cho người" — thà không trả lời còn hơn trả lời sai.

Bài viết liên quan

Phân biệt AI/ML/DL, các kiểu học máy, quy trình ML end-to-end và thuật ngữ nền tảng.

13 thg 7, 2026 15

Chất lượng dữ liệu, xử lý thiếu/ngoại lai, mã hoá, chuẩn hoá, tạo đặc trưng và tránh data leakage.

13 thg 7, 2026 13

Mô hình ngôn ngữ lớn hoạt động ra sao, token, context window, tham số sinh, và kỹ thuật viết prompt.

13 thg 7, 2026 13

Retrieval-Augmented Generation, vector database, tool calling, agent và MCP để xây ứng dụng LLM thực tế.

13 thg 7, 2026 11