Điều làm agent "thông minh" là khả năng tự quyết bước tiếp theo và lặp lại cho đến khi đạt mục tiêu. Trong LangGraph, điều này thực hiện bằng conditional edge (rẽ nhánh) và cycle (vòng lặp trong graph). Đây là hai kỹ thuật nâng agent từ luồng thẳng cứng nhắc lên hành vi linh hoạt.
Conditional edge: để graph tự chọn đường
Edge cố định luôn đi đến cùng một node. Conditional edge dùng một hàm routing đọc state và trả về tên node (hoặc một nhãn) tiếp theo.
from langgraph.graph import StateGraph, START, END
def route_after_check(state) -> str:
if state["score"] >= 8:
return "finish"
return "retry"
builder.add_conditional_edges(
"check", # node nguồn
route_after_check, # hàm quyết định
{"finish": "publish", "retry": "generate"} # map nhãn -> node
)
Hàm route_after_check không làm việc gì ngoài quyết định — nó không gọi LLM, không sửa state. Nó chỉ đọc state và trả nhãn. Dict cuối cùng ánh xạ nhãn sang node đích thực. Giữ đúng nguyên tắc này giúp luồng minh bạch và dễ test.
Cyclic flow: vòng lặp generate → check → retry
Mẫu phổ biến nhất của agent là vòng "làm rồi tự đánh giá":
- Node
generatetạo kết quả. - Node
checkchấm điểm kết quả. - Conditional edge: nếu đạt thì đi
publish, chưa đạt thì quay lạigenerate.
check về generate chính là cycle. LangGraph cho phép điều này một cách tự nhiên — đó là lợi thế lớn so với các framework chỉ hỗ trợ luồng thẳng một chiều (DAG).builder.add_edge(START, "generate")
builder.add_edge("generate", "check")
builder.add_conditional_edges(
"check", route_after_check,
{"finish": END, "retry": "generate"}
)
Chặn vòng lặp vô hạn
Vòng lặp mạnh nhưng nguy hiểm: nếu điều kiện dừng không bao giờ đúng, agent chạy mãi và đốt token. Bạn cần hai lớp phòng vệ.
- Đếm số lần lặp trong state và ép dừng:
class State(TypedDict):
attempts: int
score: int
def route(state) -> str:
if state["score"] >= 8 or state["attempts"] >= 3:
return "finish"
return "retry"
- Giới hạn cứng của LangGraph: truyền
config={"recursion_limit": 10}khiinvoke. Khi vượt, LangGraph ném lỗi thay vì chạy vô tận. Hãy coi đây là phanh an toàn cuối cùng, không phải cơ chế điều khiển chính — điều kiện dừng nghiệp vụ vẫn phải nằm trong logic của bạn.
Các bước xây một cyclic agent an toàn
- Xác định điều kiện thành công rõ ràng và đo được (score, cờ hợp lệ...).
- Thêm biến đếm vào state, tăng chắc chắn ở mỗi vòng.
- Viết hàm routing kiểm tra cả điều kiện thành công và ngưỡng lặp tối đa.
- Đặt
recursion_limitlàm lớp bảo vệ dự phòng. - Log mỗi vòng để quan sát agent có đang tiến bộ không, tránh lặp vô ích.
Checklist trước khi bật cycle
- [ ] Có điều kiện dừng khi thành công.
- [ ] Có điều kiện dừng khi quá số lần thử.
- [ ] Biến đếm được tăng chắc chắn mỗi vòng.
- [ ] Đã đặt
recursion_limithợp lý. - [ ] Mỗi nhãn routing đều có node đích trong dict ánh xạ.
Sai lầm thường gặp
- Cho hàm routing sửa state hoặc gọi LLM: nó chỉ được phép quyết định. Muốn xử lý thì đặt vào một node riêng.
- Quên tăng biến đếm: vòng lặp không bao giờ chạm ngưỡng, chạy đến khi
recursion_limitném lỗi. - Nhãn trả về không có trong dict ánh xạ: LangGraph không biết đi đâu, báo lỗi runtime.
- Chỉ dựa vào
recursion_limitđể dừng: bạn mất kiểm soát nghiệp vụ và tốn token oan. Điều kiện dừng phải nằm trong logic. - Điều kiện thành công mơ hồ khiến agent lặp thừa. Hãy định nghĩa "đạt" cụ thể và đo được.