第四部|走向 Production · 第 8 章
測試、Observability 與安全邊界
用 deterministic fixtures 與 run events 提升成功率,同時劃清 MCP、sandbox 與多租戶責任。
這章證明迴圈值得信任——先用測試證明它平常做得對,再用 observability 證明它正在做得對,最後劃清安全邊界,證明「信任」本身有極限。你需要分開評估結果是否正確、過程為何失敗、成本花在哪裡,這三件事各自對應測試與 observability;但無論這三件事看起來多漂亮,都不能取代第三步:它是否越過了授權邊界。
三層測試
| 層級 | 驗證對象 | 是否呼叫真實模型 |
|---|---|---|
| Unit / contract | tools、provider normalization、Session reducer/planner | 否 |
| Conformance / integration | 四語言、MCP loopback、CLI behavior | 否 |
| Capability eval | Agent 能否完成真實 coding task | 是 |
一般 CI 必須免費且 deterministic。公開 MCP endpoints 只適合 optional compatibility smoke,不能成為 release gate。
Outcome 是分數,Trace 是解釋
Repo 內最小 eval 會複製 fixture 到 temp workspace,執行四個 CLI,再跑 hidden verifier:
make eval
AGENT=tiny-rs TASK=fix-bug make eval
主要分數只有:
verifier exit 0 → PASS
otherwise → FAIL
Duration、tokens 與 tool count 獨立報告,不能補償錯誤結果。Agent 少用兩個 tools 卻修錯 bug,不應取得較高分。
Structured Run Events
TypeScript 提供 one-shot machine mode:
tiny-ts --json "調查問題"
stdout 只輸出 JSONL:
{"type":"run.started","sessionId":"...","model":"..."}
{"type":"model.completed","durationMs":1589.31,"usage":{"input":157,"output":31,"cacheRead":1536,"cacheWrite":0,"cacheHitRate":90.72}}
{"type":"tool.started","toolCallId":"call_1","tool":"read"}
{"type":"tool.completed","toolCallId":"call_1","tool":"read","durationMs":12.4,"ok":true}
{"type":"run.completed","result":{"status":"succeeded","answer":"..."}}
Events 預設不含 prompt、tool arguments 與 results,避免 monitoring pipeline 複製企業資料。完整證據仍保存在 job 的
Session;Session 本身不會自動提供 tenant isolation。Go、Python、Rust 目前沒有 --json;不要把 TS
reference 能力寫成四語言共有。
觀察 Cache 崩潰
每個 model.completed 記錄當次 request 的 cache hit rate,因此可以看到:
turn 1 91.2%
turn 2 90.8%
turn 3 0.0% ← prompt prefix改變或cache失效
turn 4 89.7%
Run result 中的 rate 由整個 run 累計 counters 計算。兩種 scope 必須分開,才能最佳化成本而不誤判。
安全邊界:誰信任誰
還記得第 1 章的責任表嗎?這裡把「介面與部署」那一欄攤開,順便把「產生副作用」與「持續與恢復」兩欄裡「不該負責什麼」的部分也交代清楚。
| 責任 | 由誰負責 | 不該負責什麼 | 08 章對應說明 |
|---|---|---|---|
| 選擇下一步 | Model | 直接取得 host credential | Model output 視為 untrusted input,不是 trusted code 的一部分 |
| 控制迴圈 | Agent runtime | 理解每個領域的業務規則 | Agent implementation 本身是 trusted code,但執行的是 untrusted model 決定的 tool calls |
| 產生副作用 | Tool adapter | 自行改變授權範圍 |
MCP 是 Tool adapter,不是 authorization 或 sandbox;--plugin 是 capability
selector,不是 tenant ACL
|
| 持續與恢復 | Session | 猜測未記錄的 effect 是否成功 | Session 只保存 durable facts;tenant scope 是外層控制器的責任 |
| 介面與部署 | CLI / trusted host | 把 deployment security 假裝成 agent 功能 | Tool registration 是 trusted deployment action;多租戶需要 Execution Capsule(見下一節) |
- Agent implementation 與 server operator 是 trusted code。
- Model output、prompt、repository 與 dependency scripts 視為 untrusted。
- Tool registration 是 trusted deployment action;tool arguments 是 untrusted model input。
- MCP 是 Tool adapter,不是 authorization 或 sandbox。
--plugin是 capability selector,不是 tenant ACL。
多租戶需要 Execution Capsule
若外部客戶能提供 repository 或 prompt,Fence 或 path check 都不是完整租戶邊界。每個 job 至少需要獨立 container;hostile native code、高敏感資料、GPU 或 nested container 應升級 microVM/VM。部署層還要負責:
- CPU、RAM、PID、wall-clock 與 disk/inode limits。
- Network egress、SSRF 與 metadata protection。
- Tenant-scoped credentials、audit 與 retention。
- TERM → grace → KILL 與 descendant cleanup。
這些責任不放進 tiny-agent core。Tiny-agent 保持一般 CLI,由外層 trusted job controller 建立 execution capsule、綁定 tenant identity、配置 credential,並決定 Session 與 artifact 的儲存位置及存取權限。換句話說,Session 只保存 durable facts;tenant scope 是外層控制器的責任。
企業查詢 Tool 的原則
不要提供萬用 internal_search(query) 或讓模型直接寫 SQL。使用少量 typed operations,並讓 trusted context
注入 tenant、actor 與 credential。每筆結果帶 source、observedAt、retrievedAt、partial 與 conflicts,才能組成可審查的
evidence packet。
親手驗證
先跑全部離線 gate,確認測試、MCP loopback、安全界線與教學書都不需要真實 OpenRouter:
make test
make check
make build
npm --prefix book test
接著查看 capability eval 的 verifier,而不是直接花模型額度:
sed -n '1,220p' eval/run.ts
find eval/tasks -name 'verify.mjs' -o -name 'test.sh' | sort
最後做一個安全界線練習:列出哪些資料由 tiny-agent Session 保存,哪些必須由 job controller 提供。至少應把 tenant
identity、credential、network egress、CPU/RAM/PID/disk limits 與 retention 放在外層;若答案把它們交給 MCP arguments
或 --plugin,就跨錯邊界了。
-
第一部|最小閉環
無壓力
-
第二部|能力邊界
能力壓力
-
第三部|可靠執行
失敗壓力
-
第四部|走向 Production
觀測與信任壓力・你在這裡
一個迴圈 + 一份誠實的帳本——現在你知道帳本怎麼記了。
接下來要寫什麼,見 首頁的既有規劃。