安安~我是ChiYu~
昨天終於讓 Inspector 自己選中 search_events,完成了第一筆自然語言搜尋。看到完整
trace 跑出來的那一刻,很容易冒出下一個念頭:既然搜尋都成功了,要不要順便加登入、
付款、後台,再補一支推薦活動的 Tool?
這種「順便」很有吸引力,也很會製造加班。
每多一支 Tool,就會多一份 input schema、錯誤語意、權限判斷、UI 更新與測試案例。
如果什麼都想放進來,最後可能真的做出一套活動平台,WebMCP 卻被埋在一大桌 CRUD
裡,讀者只看見功能很多,搞不清楚每支 Tool 到底負責什麼。
所以今天先踩煞車。我不急著把五支 Tool 全部寫完,而是先把產品契約釘牢:這個網站
只服務三條使用者流程,只保留五支正式 Tool;Agent 可以走到哪裡、哪裡一定要把決定
權交還人類,也在今天說清楚。
前天的 v3-day-12 用最小 Lab 拆開 Tool lifecycle;昨天則另外測試公開活動搜尋頁,留下
第一份自然語言 Agent trace。兩份證據各自回答不同問題,不能互相代替。
今天切到 v3-day-14,回到可以讓讀者重播的正式網站搜尋基線,開始固定後續實作的產品
範圍:
git switch --detach v3-day-14
npm ci
npm run dev
這個版本建立正式網站外殼、人類可用的搜尋流程,以及後續 Tool 會共用的產品基線。它適合
用來檢查畫面、搜尋與功能範圍,卻不代表五支 Tool 已經全數通關。今天要完成的是「接下來
只做哪五支、串成哪三條流程、哪些地方必須停給人類」;後面的版本才會逐一把能力補齊。

圖 1:五支 Tool 會串成三條 Journey。搜尋與收藏可以完成,報名與取消則必須停在人類確認之前。
活動網站很適合拿來練 WebMCP,因為流程大家都熟悉:找活動、看詳情、收藏、報名,
臨時不能去時再取消。也正因如此,它很容易一路長成完整產品,讓練習失去焦點。
我把範圍縮成三條 Journey:
J1 搜尋活動 → 查看詳情 → 收藏活動
J2 準備報名 → 人類檢查資料 → 人類送出報名
J3 準備取消 → 顯示取消後果 → 人類確認取消
第一條包含讀取與可復原的收藏,Agent 可以完成。後兩條會建立或取消正式報名,影響
名額與使用者權益,因此 Agent 只能整理資料、打開確認畫面,最後一下留給人類。
這個停點必須直接寫進產品契約,不能只在畫面上放一句溫馨提醒。後面寫程式與出考題
時,都要回頭核對它。
三條流程拆開後,正式 catalog 只需要五支 Tool:
| Tool | 類型 | 出現位置 | 驗收目標 |
|---|---|---|---|
search_events |
唯讀 | 搜尋頁 | 依公開條件回傳活動摘要與詳情網址 |
get_event_details |
唯讀 | 活動詳情頁 | 從目前 route 或合法活動 ID 讀取完整公開資訊 |
save_event |
低風險寫入 | 活動詳情頁 | 收藏結果可見、可復原,重複呼叫不新增第二筆 |
prepare_event_registration |
準備型 | 報名表單 | 填入可見資料,停在最終送出之前 |
prepare_registration_cancellation |
準備型 | 有效報名頁 | 顯示取消對象與後果,停在最終確認之前 |
最後兩支刻意使用 prepare,沒有取名為 submit_registration 或cancel_registration。名稱先提醒模型與工程師:Tool 執行完成,只代表資料準備好了,
不代表高風險動作也跟著完成。
正式 catalog 也不提供「送出報名」與「確認取消」。這兩個動作留在可見介面,由人類
親自操作。少兩支 Tool,反而讓責任更清楚。
把 Tool 名稱列完還不夠。若人類操作表單走 A 規則,Agent 呼叫 Tool 又走 B 規則,
兩邊單獨測試都可能通過,放在一起卻會得到不同活動、不同名額,甚至不同權限結果。
因此三條 Journey 必須共用活動 ID、session、server validation、UI state 與 audit
trail。Tool 只是另一個操作入口,商業邏輯仍然只有一套。
這也替後面的實作畫出一條很實際的界線:畫面與 Tool 可以有不同入口,但最後必須走回
同一組 action 與 server 規則。否則 Agent-ready 只是多維護一份平行世界。
前一週整理的二十道題,從明天開始跟著功能分批驗證,不會全部堆到系列尾聲才一次開獎:
| 實作階段 | 同步驗證的重點 |
|---|---|
| 搜尋活動 | Tool 是否選對、四個條件是否完整、是否擅自放寬限制 |
| 讀取目前活動 | 空 input、route grounding、離開頁面後的舊 handler |
| 錯誤處理 | 不該呼叫、查無資料、暫時失敗與是否可以重試 |
| 收藏活動 | 重複呼叫是否只留下同一筆收藏 |
| 準備報名 | 資訊不足先追問、確認前 registration POST 維持 0 |
| 準備取消 | 報名所有權、重複取消、工作階段失效 |
| 串接三條 Journey | Tool 順序、route 切換與更新後狀態 |
| 不可信內容 | 活動文案不能改寫權限或誘導額外動作 |
可控制的程式行為先交給 deterministic tests;真正由 Agent 選 Tool 的部分,則保存
Inspector trace。兩種證據各做各的工作:測試替身不能冒充模型,一次 Agent 成功也不能
替剩下十九題代簽到。
正式功能還沒補齊以前,我先把五支 Tool 的最低驗收條件寫下來:
搜尋:UI 與 Tool 使用同一組條件時,回傳同一場活動
詳情:目前 route 可使用空 input;離開 route 後,舊 Tool 不再有效
收藏:同一 session 重複收藏,只保留一筆
報名:prepare 階段的 registration POST = 0
取消:prepare 階段的 cancel POST = 0
其中有些測試現在會失敗,這很正常。紅燈在這裡不是丟臉紀錄,而是限制施工範圍:
明天只處理搜尋,就不能看收藏寫起來很順手,順便把報名也塞進同一個 commit。
真實活動平台當然可能需要登入、付款、資料庫與管理後台,但它們會帶來新的帳號模型、
金流責任與管理權限,卻不會直接回答這個系列正在追的問題:網站 Tool 能不能被正確
選擇、取得當前頁面狀態,並在有副作用以前停下來?
所以這次不加 OAuth、不做付款、不蓋後台,也沒有第六支 Tool。把範圍切小,才能保住
一條可以驗收的 WebMCP 主線。
切到 v3-day-14 後,正式網站的搜尋基線已經可以重播;目前 Chrome 也看得見 route-aware
catalog,Declarative 與 Imperative Lab 也能
重播;昨天還多了一筆 search_events 的真實 Agent trace。這些都是已經發生的證據,
但範圍不能偷放大。
昨天的 trace 只證明那個公開版本、那段 prompt、那次環境完成了一次唯讀搜尋。今天則
把五支 Tool、三條 Journey、風險與測試分配寫成產品契約。它屬於規格層的證據,尚未
證明五支正式 Tool 都實作完成,更沒有證明二十道題全部通過。
證據等級不是角色經驗值,不能把昨天單一搜尋案例的 E4,直接加到今天整份 catalog
上。只看今天主張的「產品契約已存在、可被檢查」,目前停在 E1;接下來還得靠程式測試
與 Inspector trace,一段一段往上補。
明天先沿用今天固定下來的正式搜尋基線,拆開 search_events 與人類表單共用的搜尋規則。
接著立刻拿三種說法來考它:Tool 有沒有選對、台北/免費/入門三個條件有沒有放對欄位,
以及 Agent 會不會自作主張放寬條件。