Bỏ qua để đến nội dung

Điều chỉnh ngữ cảnh công cụ của agent

Hướng dẫn này đề cập đến phần thực hành xoay quanh bề mặt công cụ hai tầng: xem một lượt chạy gửi đi những gì, thay đổi nó, và chẩn đoán một agent đã với tay lấy nhầm công cụ. Để hiểu vì sao nó hoạt động như vậy, hãy đọc Ngữ cảnh công cụ và bộ nhớ đệm prompt.

Xem một lượt chạy thực sự gửi đi những gì

Phần tiêu đề “Xem một lượt chạy thực sự gửi đi những gì”

Mở một cuộc hội thoại và nhấn vào chỉ báo mức sử dụng ngữ cảnh ở đầu cuộc hội thoại. Nó dựng lại đúng bề mặt mà lần điều phối kế tiếp sẽ gửi, mà không chạy bất cứ thứ gì. Xem thêm (hoặc lệnh /context) mở trình khám phá ngữ cảnh đầy đủ, nơi bạn có thể kiểm tra từng công cụ.

Ở đây có hai phân đoạn đáng chú ý:

  • Định nghĩa công cụ và MCP và công cụ động — tập thường trú, kèm chi phí token thật của từng công cụ.
  • Công cụ tải khi cần — chỉ mục bị trì hoãn. Mỗi mục chỉ bị tính đúng cái tên của nó, bởi yêu cầu chỉ mang theo tên; nhưng mở một mục vẫn hiển thị đầy đủ phần mô tả và lược đồ, để bạn thấy nó sẽ tốn bao nhiêu nếu lượt chạy kéo nó vào.

Nếu phân đoạn bị trì hoãn trống, tính năng trì hoãn đang tắt trên máy chủ này. Hãy kiểm tra --tool-deferral trong CLI cc_server.

Tập thường trú là chính sách, không phải cấu hình — nó nằm trong ModeToolPolicy (packages/cc_domain/lib/features/mcp/domain/value_objects/mode_tool_policy.dart) và áp dụng cho mọi lượt chạy:

  • residentBuiltins — từ vựng về tệp và shell.
  • residentDiscovery — search_tools và list_my_tools. Đừng loại bỏ chúng; chúng là cách agent tiếp cận mọi thứ còn lại.
  • residentMcpTools — một số ít công cụ Control Center đáng để mang theo lược đồ trong mọi yêu cầu.
  • Một khối riêng cho từng chế độ, dành cho những công cụ mà một chế độ nhất định dùng trong gần như mọi lượt.

Hai quy tắc khi chỉnh sửa nó:

Chỉ thêm một công cụ nếu hầu hết các lượt chạy đều dùng nó. Mỗi cái tên đều khiến mọi yêu cầu của mọi lượt chạy phải trả giá bằng lược đồ của nó, mãi mãi. Một công cụ quan trọng khi được dùng nhưng tổng thể thì hiếm khi dùng nên nằm ở nửa bị trì hoãn — agent vẫn sẽ tìm thấy nó.

Dùng tên thật của công cụ. Một tên thường trú không khớp với công cụ nào là vô tác dụng: không lỗi, không cảnh báo, công cụ đơn giản là bị trì hoãn. test/tooling/resident_tool_names_test.dart bắt được điều này và cũng giữ mỗi chế độ dưới 40 công cụ thường trú, đó chính là mục đích của việc này — vượt qua ngưỡng đó, việc chọn công cụ xuống cấp thấy rõ.

Các động từ bắt buộc và được ghim của một chế độ được thêm tự động, nên bạn không bao giờ cần liệt kê động từ đầu ra của chính chế độ đó.

Khi một agent dùng nhầm công cụ hoặc khẳng định nó không thể làm điều gì đó, hãy xác định xem trong ba tình huống sau, tình huống nào đã xảy ra.

Mỗi lượt chạy ghi lại những công cụ bị trì hoãn mà nó đã nạp cùng tác nhân kích hoạt — một lời gọi trực tiếp theo tên, hoặc một truy vấn search_tools. Hãy mở dòng sự kiện của lượt chạy (Cài đặt → Không gian làm việc → Agent → agent → Nhật ký → Xem) và tìm dòng [harness] loaded N deferred tool(s).

  • Không ghi gì, và agent nói rằng năng lực đó không tồn tại — nó chưa từng tìm. Đó là vấn đề ở prompt, không phải ở việc truy hồi: chỉ mục bị trì hoãn nằm trong prompt hệ thống của nó kèm chỉ dẫn không được tuyên bố một năng lực là thiếu cho tới khi một lần tìm kiếm trả về rỗng.
  • Có ghi một lần tìm kiếm, nhưng không nạp gì — một lần truy hồi trượt thật sự. Chuyển sang bước 2.
  • Có nạp công cụ, nhưng dùng nhầm — những công cụ nó tìm thấy quá giống nhau. Chuyển sang bước 3.

search_tools khớp dựa trên tên, phần mô tả và tên tham số. Một lần trượt gần như luôn có nghĩa là phần mô tả không chứa những từ mà agent đã dùng.

Hãy thêm chúng vào. Phần mô tả chính là chỉ mục truy hồi, nên hãy viết dài ra thay vì cắt bớt — hãy viết bằng từ vựng mà người vận hành thật sự sẽ gõ (“assign”, “hand off”, “give to”), chứ không chỉ là danh từ nội bộ. Cắt bớt một phần mô tả để tiết kiệm token khiến bạn mất cả khả năng khớp tìm kiếm lẫn độ chính xác khi chọn lựa, mà tiết kiệm được gần như không đáng kể so với lược đồ.

Nếu công cụ đúng có tồn tại nhưng xếp hạng thấp, đó chính là mục đích của tham số limit; phần mô tả của chính công cụ đó nhắc agent mở rộng một tìm kiếm có vẻ gần đúng nhưng lại trượt.

Nếu hai công cụ có phần mô tả mà một người chưa biết trước sự khác biệt sẽ đọc ra như nhau, thì mô hình đang đoán. Hãy gộp chúng thành một công cụ với một tham số phân biệt.

ticket_relation và ticket_pr_link đi theo khuôn mẫu này: mỗi công cụ xử lý việc liên kết và hủy liên kết thông qua một tham số phân biệt. Một lựa chọn được đưa ra bên trong một lời gọi, với đầy đủ ngữ cảnh của yêu cầu, đáng tin cậy hơn một lựa chọn được đưa ra giữa hai phần mô tả na ná nhau.

Hãy giữ các công cụ tách riêng khi chúng cần cổng phê duyệt khác nhau, kiểm toán khác nhau hoặc cách hiển thị khác nhau — đó là những lý do khiến việc gộp lại sẽ làm bạn mất đi thứ gì đó có thật.

Kiểm tra xem bộ nhớ đệm prompt có hoạt động không

Phần tiêu đề “Kiểm tra xem bộ nhớ đệm prompt có hoạt động không”

Tỷ lệ trúng bộ nhớ đệm xuất hiện trong Quan sát → Phân tích dưới dạng Tỷ lệ cache. Một cuộc hội thoại chạy dài khỏe mạnh sẽ giữ mức cao; nếu nó liên tục thấp, tức là có thứ gì đó đang viết lại tiền tố ở mỗi lượt.

Những nguyên nhân phổ biến, xếp theo mức độ khả dĩ:

  • Bất cứ thứ gì không tất định ở đầu prompt. Một dấu thời gian, một id yêu cầu, hay một tập hợp được duyệt theo thứ tự thay đổi đều đủ gây ra điều đó.
  • Thay đổi mô hình hoặc mức suy luận giữa cuộc hội thoại. Cả hai đều thay đổi tiền tố. Agent con đặc biệt dễ bị làm sai ở điểm này: chạy các agent con ở mức suy luận thấp hơn để tiết kiệm tiền có thể tốn nhiều hơn ở phần chia sẻ bộ nhớ đệm bị mất so với khoản tiết kiệm được.
  • Nén quá thường xuyên. Việc nén viết lại lịch sử theo thiết kế, nên cái giá của nó là có thật; cách khắc phục là nén thưa và sâu, thay vì nén thường xuyên và nông.

Tắt tính năng trì hoãn bằng --tool-deferral=off là một phép A/B hợp lệ để tách bạch xem một thay đổi hành vi có phải đến từ bề mặt hai tầng hay không. Nó tái tạo chính xác yêu cầu trước thời kỳ trì hoãn, nên nếu hành vi vẫn còn khi tắt nó đi, thì bề mặt không phải là nguyên nhân.