Quay lại hướng dẫn
Thiết lập·21 tháng 9, 2026·Cập nhật 24 tháng 9, 2026·Đọc 9 phút

Vòng lặp vô hạn và mức sử dụng token của Nanobot: chẩn đoán một lượt Dream bị giới hạn

Thiết lập mà tiêu đề lỗi đề cập đã bị xóa, pull request khôi phục nó đã bị đóng mà không được hợp nhất, và giới hạn duy nhất còn lại áp dụng trên toàn bộ tiến trình.

Được xem xét lần cuối vào .

Một lần chạy nanobot trông như vòng lặp vô hạn thực chất là lần chạy có giới hạn: trong mã nguồn v0.3.5 được phát hành, mọi lượt agent đều bị giới hạn bởi agents.defaults.maxToolIterations, mặc định là 200, và một maintainer đã xác nhận công khai rằng đây không phải vòng lặp vô hạn theo nghĩa đen. Vấn đề thực sự là mức sử dụng token, vì lần chạy chạm giới hạn đó ghi nhận 201 lượt assistant và gửi lại prompt ngày càng lớn sau mỗi lượt. Để xác định bạn đang gặp trường hợp nào cần chẩn đoán bốn câu hỏi, và cách khắc phục có bằng chứng hỗ trợ không phải là một giá trị cấu hình.

Bắt đầu bằng việc loại bỏ manh mối rõ ràng. Báo cáo upstream là issue #5781, có tiêu đề trỏ tới dream.maxIterations, còn PR #5782 có tiêu đề "fix(dream): enforce configured iteration limit". Khóa đó không tồn tại trong v0.3.5, và PR đã bị đóng mà không merge vào ngày 16 tháng 9 năm 2026. Một tutorial dựa trên nó thực ra không cấu hình gì cả.

Một điểm phân biệt, vì truy vấn hiển thị nhầm trình theo dõi vấn đề. Trang này nói về HKUDS/nanobot, MIT, được cài dưới dạng gói PyPI nanobot-ai — 0.3.5, Python 3.11 trở lên, tải lên ngày 15 tháng 9 năm 2026. obot-platform/nanobot là một dự án Go khác, README của dự án này tuyên bố đang ở chế độ bảo trì với issue bị vô hiệu hóa; số issue của nó không phải bằng chứng ở đây. Còn pip install nanobot, không có hậu tố, cài một gói điều hướng robot không liên quan.

Điều được báo cáo và phiên bản liên quan

Dream là tác vụ hợp nhất bộ nhớ theo lịch của nanobot, được gateway chạy dưới dạng cron job có tên dream. Đây không phải tác vụ embedding hoặc vector-index: Kunavo không cung cấp model embedding, và Dream không cần model đó vì bộ nhớ bền vững của nanobot là các tệp thuần túy trong workspace, còn lần chạy Dream là lưu lượng chat thông thường.

Issue #5781 được BrianMwangi21 tạo ngày 15 tháng 9 năm 2026 cho nanobot v0.3.0, trên Python 3.12 với một model reasoning được truy cập thông qua OpenRouter. Triệu chứng: tác vụ Dream luân phiên read_file trên memory/history.jsonl với read_file trên một SKILL.md, hàng chục lần, trong khi reasoning trace liên tục cân nhắc lại nơi lưu một thông tin nhỏ duy nhất. Bảy lần chạy được ghi nhận trong khoảng 26 giờ kéo dài từ khoảng 25 phút đến khoảng 111 phút; những lần gần 200 tool call đã chạm giới hạn toàn cục, và một checkpoint của session cho thấy runtime_checkpoint.iteration: 164, phase tools_completed, trên cùng lần gọi read_file.

Có ba giới hạn phạm vi cần đặt cạnh các con số đó. Đây là log gateway do một người dùng tự báo cáo, trên một model, ở v0.3.0 — chưa maintainer nào tái hiện và chưa ai kiểm thử lại trên v0.3.5. Issue được gắn nhãn enhancement và priority: p2, không phải bug, và vẫn đang mở. Dạng này cũng từng xuất hiện: issue #3073, một vòng lặp read_file gần như giống hệt trên history.jsonl từ ngày 12 tháng 4 năm 2026, đã bị đóng với trạng thái not planned. Không điều nào trong số đó chứng minh nanobot nói chung là đắt; chúng chỉ hỗ trợ việc kiểm tra xem bản cài đặt của bạn có đang gặp tình trạng này hay không.

Khóa đã deprecated và giới hạn thực sự đang hoạt động

Toàn bộ nhầm lẫn là do khác biệt giữa các phiên bản, và mã nguồn làm rõ điều đó. Mã nguồn đã được đọc ở hai tag phát hành vào ngày 21 tháng 9 năm 2026:

Khóa cấu hìnhTrong v0.3.0Trong v0.3.5Việc cần làm hiện nay
dream.maxIterationsMặc định 15, được đánh dấu # Deprecated: no longer usedĐã xóa khỏi schemaKhông ghi khóa này; nó không cấu hình gì
dream.maxBatchSizeMặc định 20, cùng bình luận deprecatedĐã xóaKhông ghi khóa này
dream.annotateLineAgesMặc định true, cùng bình luận deprecatedĐã xóaKhông ghi khóa này
dream.enabledMặc định trueMặc định trueCó thể chỉnh sửa trong cài đặt runtime của WebUI
dream.intervalHMặc định 2Mặc định 2Chỉnh sửa config.json; không phải mục lá của WebUI
dream.cronNull; override cũNull; override cũĐược ưu tiên hơn intervalH khi được đặt
dream.modelOverrideĐược khai báo, có bình luận pending implementationĐã triển khaiChỉ tên preset, không bao giờ là raw model id
agents.defaults.maxToolIterations200200Giới hạn duy nhất, áp dụng trên toàn process

Hai điều khiến bảng này dễ bị hiểu sai. Con số 200 đúng theo hai nghĩa — đó là giá trị trong cấu hình của người báo lỗi và giá trị mặc định được phát hành tại dòng 129 của nanobot/config/schema.py, giống hệt trong tag v0.3.5 và trên main, vì vậy người đọc chưa từng đặt giá trị này vẫn có 200. Và nó không được tài liệu hóa: lần tải tài liệu tham chiếu cấu hình 0.3.5 của chính nanobot vào ngày 21 tháng 9 năm 2026 trả về 488.608 byte HTML với không lần xuất hiện nào của maxToolIterations, và tệp docs/configuration.md trong kho mã tại tag đó cũng không có lần xuất hiện nào. Con số này có thể chứng minh từ mã nguồn và bình luận của maintainer, không phải từ một trang tài liệu — vì vậy hãy nghi ngờ mọi tutorial trích dẫn con số khác.

modelOverride là biện pháp duy nhất có điều kiện phiên bản. Trong v0.3.0, trường này tồn tại với bình luận pending implementation nhưng hoàn toàn không có mã phân giải; PR #5107, được merge ngày 27 tháng 7 năm 2026, đã triển khai nó cho v0.3.5. Trang bộ nhớ chính thức của 0.3.5 nêu rằng trường này chọn một entry có tên từ model_presets cho Dream, chỉ chấp nhận tên preset và không hỗ trợ raw model identifier. Trang đó ghi nhận ba khóa Dream và không đề cập giới hạn số vòng lặp ở bất kỳ đâu. Dưới đây là toàn bộ bề mặt hiện tại, cùng khối providers mà nó dựa vào, được đề cập trên trang thiết lập nanobot:

~/.nanobot/config.json — toàn bộ Dream surface của v0.3.5
{
  "modelPresets": {
    "dream-cheap": {
      "provider": "kunavo",
      "model": "claude-haiku-4-5",
      "maxTokens": 8192
    }
  },
  "agents": {
    "defaults": {
      "maxToolIterations": 200,
      "dream": {
        "enabled": true,
        "intervalH": 2,
        "modelOverride": "dream-cheap"
      }
    }
  }
}

Lưu ý những gì không có trong tệp đó: không có cách nào giới hạn riêng Dream. AgentLoop được tạo một lần với max_iterations từ các mặc định của process, và cả đường dẫn cron của Dream lẫn đường dẫn /dream thủ công đều gọi process_direct(...) mà không truyền đối số số vòng lặp, tương tự subagent. Hạ giới hạn này sẽ hạ giới hạn cho chat, Dream, heartbeat và subagent cùng lúc.

Chẩn đoán theo thứ tự này

Hãy trả lời bốn câu hỏi dưới đây trước khi thay đổi bất cứ điều gì, vì ba câu không tốn gì và câu thứ tư cho biết ba câu đầu có quan trọng hay không. Các chuỗi log là văn bản nguyên văn trong v0.3.5; dấu ngoặc nhọn là giá trị runtime.

Câu hỏiNơi cần xemÝ nghĩa của câu trả lời
1. Lần chạy tự dừng hay đã chạm giới hạn?Gateway log: Max iterations (200) reached, từ agent/loop.pyCó nghĩa là lần chạy bị giới hạn, với khoảng 201 lượt assistant. Không có nghĩa là lần chạy kết thúc trước giới hạn — model đã hội tụ hoặc lần chạy thất bại hoàn toàn và ghi Dream cron job failed
2. Cursor Dream có tiến lên không?Ba dòng riêng biệt trong cli/gateway_runtime.py: Dream cron job completed, cursor advanced to …; … completed with no memory changes; cursor advanced to …; Dream cron job did not complete (…); cursor remains at …Dòng thứ ba là cơ chế an toàn khi lỗi của v0.3.5 đang hoạt động: lần chạy chưa hoàn tất để lại batch để retry. Điều đó cũng có nghĩa là cùng batch sẽ quay lại ở tick kế tiếp
3. Cùng một tool với cùng đối số có lặp lại không?Các dòng Tool call: giữa hai marker đóTool và đối số giống hệt nhau lặp đi lặp lại là trạng thái model không hội tụ, đúng với kết luận của upstream. Cơ chế chặn lặp duy nhất trong v0.3.5 khớp với web_fetch và web_search; read_file lặp lại sẽ không bị bắt
4. Chi phí là bao nhiêu?llm_usage.sqlite3 trong thư mục cấu hình, tổng hợp theo ngày và source; ở phía gateway, theo khóa và theo ngày trong dữ liệu mức sử dụngDream được gắn nhãn dream. Heartbeat được gắn nhãn cron, vì vậy lọc theo "heartbeat" sẽ không tìm thấy gì

Bạn không cần chờ hai giờ đến tick cron để tái hiện. Lệnh /dream chạy cùng tác vụ theo yêu cầu và báo cùng sự phân biệt trong chat: Dream completed in Ns. hoặc Dream completed in Ns; no memory changes. khi thành công, đối với Dream did not complete after Ns (reason); memory cursor was not advanced. khi không hoàn tất. Một thay đổi khác trong v0.3.5 có ý nghĩa khi bạn đang tìm bằng chứng: các tệp JSONL của session đã được chuyển vào cây sessions/<workspace-id>/ trong thư mục cấu hình, vì vậy các đường dẫn v0.3.0 được trích dẫn trong chuỗi issue không phải nơi checkpoint của bạn nằm.

Năm cơ chế và bằng chứng thực sự hỗ trợ cho từng cơ chế

Đòn bẩyBằng chứng hỗ trợCó lợi khiBạn phải đánh đổi điều gì
Nâng cấp v0.3.0 lên v0.3.5Commit 4e2640f, có trong v0.3.5 nhưng không có trong v0.3.0, chỉ khiến cursor tiến lên khi lý do dừng là completedTriệu chứng của bạn là bộ nhớ bị bỏ qua chứ không phải chi tiêuNó không rút ngắn vòng lặp không hội tụ, và chưa ai kiểm thử lại #5781 trên 0.3.5
Đổi model cho DreamBiện pháp duy nhất có kết quả trước và sau: trong bản audit của người báo lỗi, một batch mà một model mất 91 phút vẫn chưa hoàn tất đã được lần chạy tiếp theo hoàn tất bằng model khác trong khoảng một phút với 6 tool call, cùng prompt, cùng lịch sử và cùng toolChất lượng chat phải tiếp tục dùng model đắt tiền của bạnYêu cầu v0.3.5 và một preset được định nghĩa; trên v0.3.0, trường này phân giải thành không có gì
Hạ maxToolIterationsCó thể chỉnh sửa trong cài đặt runtime của WebUI, tối thiểu là 1, cho mỗi webui/settings_runtime.pyBạn muốn có mức trần xấu nhất trong khi chẩn đoánMột nút điều khiển cho chat, Dream, heartbeat và subagent; lần chạy bị giới hạn không tiến cursor, nên cùng batch sẽ được retry ở tick kế tiếp
Làm chậm hoặc tắt DreamintervalH, hoặc dream.enabled trong WebUI; PR #5407 đã merge sẽ loại bỏ job đã lưu khi bị tắtViệc hợp nhất không đáng với chi phí trong workload của bạnBạn mất tính năng hợp nhất bộ nhớ, vốn chính là chức năng này
Định tuyến để việc gửi lại rẻ hơnTrong v0.3.5, chính xác hai provider spec đặt supports_prompt_caching: anthropic và openrouter; trường này mặc định là falseBạn chấp nhận các lần chạy dài và muốn chúng tốn ít hơnPhụ thuộc vào đường dẫn giao thức bạn đã cấu hình và việc tự xác minh usage được trả về

Hai ID mô hình mà người báo cáo sử dụng qua OpenRouter là deepseek/deepseek-v4-flash-0731 và openai/gpt-5.6-luna, đúng như cách anh ấy đã ghi; các ID này và giá của chúng chưa được kiểm chứng ở đây, vì vậy hãy xem phần so sánh này là bằng chứng cho thấy mô hình quyết định khả năng hội tụ, chứ không phải là lời khuyến nghị sử dụng một trong hai mô hình. Phía dự án gốc cũng đi đến kết luận tương tự: khi thông báo đóng PR #5782 trên issue #5781, chengyongru viết rằng giới hạn cố định về số vòng lặp Dream không giải quyết được vấn đề hội tụ cốt lõi vốn phụ thuộc vào mô hình và có thể khiến những lần chạy vốn có khả năng thành công bị thử lại liên tục.

Chi phí của một lần chạy bị giới hạn: phép tính minh họa

Đây là phép tính token mang tính minh họa, không phải chi phí tác vụ được đo lường và không phải mức trần hóa đơn. nanobot không công bố số token trên mỗi lần chạy cho Dream, vì vậy mọi dữ liệu đầu vào ở đây đều là giả định mà bạn nên thay thế bằng số đo của riêng mình. Giả sử một lần chạy đạt giới hạn ở 201 lượt của assistant — số lượng trong bản kiểm tra của phóng viên — mỗi lượt gửi lại một prompt được giữ cố định ở mức 25.000 token, đây là cách ông ấy mô tả workspace của mình, không phải số liệu được công bố. Như vậy là 5,03M token đầu vào. Token đầu ra bị loại trừ, và prompt thực tế tăng lên sau mỗi kết quả công cụ, nên cách tính này đồng thời đánh giá thấp một lần chạy thực tế theo hai hướng. Mức giá là giá trực tiếp từ danh mục Kunavo.

Mô hìnhĐầu vào trên mỗi 1MĐọc từ cache trên mỗi 1MMột lần chạy đạt giới hạn, không có cacheCùng lần chạy đó, các lần gửi lại được đọc từ cache
Claude Haiku 4.5$0,70$0,07$3,52$0,37
GPT-5.6 Terra$0,70$0,07$3,52$0,37
Claude Sonnet 5$1,40$0,14$7,04$0,74

Cột cuối giả định một trường hợp tốt nhất mà không có dữ liệu nào ở đây kiểm chứng: lần gửi đầu tiên áp dụng mức giá đầu vào thông thường và tất cả 200 lần gửi lại đều được phục vụ bằng cache. Việc ghi cache được tính theo mức giá riêng, ở một số mô hình cao hơn mức giá đầu vào thông thường; mục nhập cache sẽ hết hạn; và một prompt tăng kích thước sẽ được ghi lại thay vì đọc lại — vì vậy hãy xem khoảng cách giữa hai cột cuối là quy mô phần tiết kiệm có thể đạt được, không phải báo giá. Điểm duy nhất là trong một lần chạy dài và lặp lại nhiều, chính việc gửi lại, chứ không phải mô hình, là nơi tiền được chi.

Việc các dấu đánh dấu cache có thực sự được truyền đi hay không do cấu hình nanobot của bạn quyết định, và điều này có thể thấy trong mã nguồn được đóng gói. Một khóa nhà cung cấp tự tạo dưới providers được coi là nhà cung cấp tương thích OpenAI thông thường và giữ supports_prompt_caching ở giá trị mặc định là false, vì vậy client của nanobot không gửi dấu cache_control trên đường dẫn đó, ngay cả với id mô hình có dạng Claude. Giữ preset trên nhà cung cấp tích hợp sẵn anthropic và ghi đè providers.anthropic.apiBase sẽ giữ các dấu này. Đây là tuyên bố về những gì client của nanobot gửi đi, không phải về những gì bất kỳ endpoint nào tự xử lý ở phía mình, và Kunavo chưa kiểm thử nanobot trong runtime. Hãy đọc usage được trả về từ một cuộc gọi thực tế trước khi lập ngân sách cho một tác vụ định kỳ dưới dạng đã cache — tài liệu về caching cho thấy cache hoạt động trông như thế nào và tài liệu tham chiếu base URL cung cấp cả hai quy ước endpoint.

Số tiền trong danh mục của Kunavo là mức sàn thanh toán chứ không phải mức trần: khi upstream báo cáo khoản phí của mình, hóa đơn là giá trị lớn hơn giữa chi phí trong danh mục và chi phí upstream nhân với mức markup áp dụng. Mức nạp tối thiểu là $10 tín dụng trả trước — đây là mức tối thiểu để nạp tiền, không phải phí tác vụ hay gói đăng ký. Xem chi tiết thanh toán và tối ưu hóa chi phí để biết phương pháp đo lường thay thế các giả định ở trên.

Xác minh bản sửa trong một lần chạy

Thay đổi một điều, sau đó chạy /dream một lần thay vì chờ lịch, rồi kiểm tra ba dấu theo thứ tự: không có cảnh báo Max iterations (200) reached, có một dòng cursor advanced to … thay vì cursor remains at …, và số lần gọi công cụ ở giữa phải hợp lý. Sau đó đọc khoản phí mà tài khoản của chính bạn đã ghi nhận trong khoảng thời gian đó, theo từng khóa và từng ngày, tại dữ liệu mức sử dụng; bộ lưu trữ của nanobot đếm token chứ không đếm tiền. Nếu bạn đang cấu hình endpoint lần đầu, hướng dẫn bắt đầu nhanh và trang thiết lập nanobot trình bày cả hai đường dẫn giao thức, còn tạo tài khoản Kunavo là bước cần thực hiện trước khi nạp tiền cho một khóa. Đang so sánh thời gian chạy? nanobot và OpenClaw đặt hai nhịp chạy nền cạnh nhau, còn danh bạ agent API lập chỉ mục các client theo giao thức truyền tải.

Câu hỏi thường gặp

Nanobot có thực sự bị kẹt trong vòng lặp vô hạn không?

Không, và một maintainer đã xác nhận công khai điều đó. Khi bình luận về issue #5324 vào ngày 10 tháng 8 năm 2026, chengyongru viết rằng agent runner của nanobot bị giới hạn bởi agents.defaults.maxToolIterations, mặc định là 200, nên đây không phải vòng lặp vô hạn theo nghĩa đen — đồng thời nói thêm rằng một vòng lặp dài nhưng có giới hạn vẫn có thể gây mức sử dụng token tích lũy rất cao, vì vậy tác động thực tế là có thật. Mã nguồn v0.3.5 được phát hành cũng xác nhận: max_tool_iterations mặc định là 200 trong nanobot/config/schema.py, và agent/loop.py ghi cảnh báo "Max iterations (200) reached" khi một lần chạy chạm giới hạn. Điều mọi người gọi là vòng lặp vô hạn thực chất là một lần chạy đạt tới mức trần đó; trong log của một người báo lỗi, điều này có nghĩa là 201 lượt assistant đọc lại cùng hai tệp.

Tại sao đặt dream.maxIterations lại không có tác dụng?

Vì trường đó không còn tồn tại. Trong nanobot v0.3.0, cấu hình Dream có max_iterations, max_batch_size và annotate_line_ages, mỗi trường đều được đánh dấu trong mã nguồn bằng bình luận "Deprecated: no longer used"; trong tag v0.3.5, cả ba đều đã bị xóa, và class chỉ định nghĩa enabled, intervalH, cron và modelOverride. Maintainer chengyongru nói ngày 15 tháng 9 năm 2026 rằng dream.maxIterations đã được cố ý đánh dấu là deprecated và không sử dụng khi Dream được chuyển sang agent loop thông thường, rồi sau đó bị xóa khỏi main. Pull request lẽ ra sẽ khôi phục trường này, #5782, đã bị đóng mà không merge vào ngày hôm sau. Ghi khóa đó vào cấu hình v0.3.5 chỉ tạo ra một khóa không được schema định nghĩa.

Làm thế nào để giới hạn token chỉ cho tác vụ Dream của nanobot?

Không thể làm như một ngân sách tích lũy trong nanobot v0.3.5. Không có phần nào trong mã nguồn được phát hành cộng tổng token của một lần chạy rồi dừng khi đạt một con số, và agents.defaults.maxToolIterations là giới hạn số vòng lặp duy nhất — nó áp dụng trên toàn process, đồng thời cho các lượt chat thông thường, Dream, heartbeat và subagent. Có hai thứ bạn có thể giới hạn riêng cho Dream thông qua agents.defaults.dream.modelOverride: model và các giới hạn mỗi lần gọi của preset đó, vì ModelPresetConfig có maxTokens và contextWindowTokens, còn dream_runtime() phân giải preset được đặt tên thành môi trường thực thi mà lần chạy Dream hoạt động trong đó. Các giới hạn này áp dụng cho từng lần gọi riêng lẻ, không phải toàn bộ lần chạy, nên 200 lần gọi với maxTokens thấp vẫn là 200 lần gọi. Lịch chạy cũng có thể giới hạn phạm vi thông qua intervalH. Một ngân sách tích lũy là thứ upstream hiện đã từ chối bổ sung: trong issue #5781 ngày 16 tháng 9 năm 2026, cùng ngày đóng PR #5782, chengyongru viết rằng ngân sách token hoặc tài nguyên cho tác vụ nền cần thiết kế chi tiết hơn về đơn vị và phạm vi ngân sách, ngữ nghĩa kết thúc, hành vi retry và cursor, khả năng quan sát, cũng như tương tác với các model khác nhau, và hiện họ không có kế hoạch thúc đẩy việc này.

Làm thế nào để dừng một lần chạy Dream của nanobot đang diễn ra?

Không phải bằng /stop, theo cách đọc mã nguồn v0.3.5. /stop được mô tả là hủy lượt agent đang hoạt động của chat này và được triển khai dưới dạng hủy các tác vụ đã đăng ký theo session key của chat, trong khi một lần chạy Dream được tạo dưới khóa tạm thời riêng có dạng dream:YYYYMMDD-HHMMSS. Đây là cách đọc đường dẫn mã, không phải kết quả đã kiểm thử — /stop chưa được thực thi với một lần chạy Dream trực tiếp ở đây. Các cơ chế được tài liệu hóa là /restart, tắt agents.defaults.dream.enabled hoặc dừng process gateway. PR #5407 đã merge trong v0.3.5 là thay đổi khiến việc tắt thực sự loại bỏ system job đã lưu thay vì để nó tiếp tục được lên lịch.

Làm thế nào để xem các tác vụ nền của nanobot đã dùng bao nhiêu token?

Hãy đọc kho lưu trữ mức sử dụng cục bộ, không phải dùng slash command. Nanobot v0.3.5 ghi nhận mọi lần gọi model với trường source có các giá trị user, api, cron, dream hoặc system, ghi chúng vào llm_usage.sqlite3 trong thư mục cấu hình — mặc định là ~/.nanobot — với các cột token input, output, cache-read và cache-write, rồi tổng hợp theo ngày và source. Có hai điểm dễ nhầm. Không có lệnh /insights hoặc /cost: cả hai pull request đề xuất chúng, #3735 và #3921, đều bị đóng mà không merge, và danh sách builtin của v0.3.5 là /new, /compact, /stop, /restart, /status, /model, /history, /goal, /trigger, /dream, /dream-log, /dream-restore, /dream-prompt, /evaluator-prompt, /skill, /help và /pairing. Nhãn cũng không đối xứng: chi tiêu Dream được gắn dream, còn chi tiêu heartbeat được gắn cron, vì session key của heartbeat đúng là "heartbeat". Đây là số lượng token, không phải tiền, nên hãy đối soát với sổ cái riêng của nhà cung cấp.

Nâng cấp lên nanobot v0.3.5 có sửa được vòng lặp không?

Không ai nói rằng có, và trang này cũng sẽ không khẳng định như vậy. Issue #5781 được tạo cho v0.3.0 và vẫn đang mở, gắn nhãn enhancement và priority p2; người báo lỗi chưa kiểm thử lại sau khi nâng cấp và chưa maintainer nào tái hiện được. Những gì v0.3.5 sửa được hẹp hơn nhưng vẫn đáng có: commit 4e2640f ngăn lần chạy chưa hoàn tất tiến cursor Dream và âm thầm bỏ qua lịch sử, PR #5442 đã merge khiến lần chạy chưa hoàn tất báo lý do không hoàn thành, còn PR #5325 đã merge khiến edit_file trả về "Error: new_text must be different from old_text." thay vì báo thành công khi chỉnh sửa không tạo thay đổi. Thay đổi cuối xử lý vòng lặp đọc rồi chỉnh sửa của issue #5324, không xử lý vòng lặp chỉ đọc của #5781. v0.3.5 cũng không cung cấp cơ chế chặn chung đối với các lần gọi tool giống hệt lặp lại. Cơ chế duy nhất trong mã nguồn được phát hành, repeated_external_lookup_error trong nanobot/utils/runtime.py, chặn web_fetch hoặc web_search giống hệt sau hai lần thử và không khớp tên tool nào khác, nên read_file lặp lại vẫn chạy tới giới hạn số vòng lặp. Năm pull request đề xuất cơ chế chặn chung — #3077, #4522, #5344, #3701 và #4154 — đều chưa được merge.

Đã kiểm tra ngày 21 tháng 9 năm 2026: API GitHub cho HKUDS/nanobot, các issue #5781, #5324 và #3073, cùng các pull request #5782, #5107, #5325, #5442, #5407, #3077, #4522, #5344, #3701, #4154, #3735, #3921 và #4622; bản ghi PyPI cho nanobot-ai 0.3.5; tài liệu bộ nhớ và cấu hình nanobot 0.3.5; và mã nguồn được đóng gói tại tag v0.3.5 cho mọi giá trị mặc định, chuỗi log và đường dẫn mã được trích dẫn ở trên, đối chiếu với v0.3.0 ở những điểm khác nhau. Kunavo chưa cài đặt hoặc chạy nanobot, không có hành vi nào ở đây được Kunavo kiểm thử, và vòng lặp của issue #5781 chưa được bất kỳ ai kiểm thử lại trên v0.3.5. Mức giá token lấy từ danh mục trực tiếp và mọi con số đô la đều là phép tính minh họa theo các giả định đã nêu.