iT邦幫忙

2026 iThome 鐵人賽

DAY 13
0
Modern Web

WebMCP:30 天打造 AI Agent 看得懂、也操作得動的網站系列 第 13

Day 13|「幫我填這張表」其實很難:WebMCP Form 從填值、驗證到送出

  • 分享至 

  • xImage
  •  

本篇重點

表單是 Browser Agent 最常見的任務,也是最容易出錯的地方之一。真正的流程不是「把值塞進 input」,而是:

理解欄位
→ 填值
→ Validation
→ 讓使用者看到
→ 確認
→ Submit
→ 回傳結果

今天用 Declarative API 做聯絡表單,並刻意不開 toolautosubmit,先保留使用者最後確認。

一張正常的人類表單

<form
  id="contact-form"
  toolname="prepare_contact_message"
  tooldescription="Fill the contact form with the user's name, email, subject, and message. The user reviews the form before submitting."
>
  <label for="name">姓名</label>
  <input id="name" name="name" required>

  <label for="email">Email</label>
  <input id="email" name="email" type="email" required>

  <label for="subject">主旨</label>
  <input id="subject" name="subject" required>

  <label for="message">訊息</label>
  <textarea id="message" name="message" required></textarea>

  <button type="submit">確認送出</button>
</form>

📸 圖片 1|聯絡表單還沒被 Agent 填值的狀態
https://ithelp.ithome.com.tw/upload/images/20260922/20121296eUv3mS28WV.png

這裡我把 Tool 叫:

prepare_contact_message

而不是:

submit_contact_message

因為我希望 Agent 的責任停在「準備內容」,最後真的送出由人確認。

Tool Name 本身就可以反映風險邊界。

HTML Validation 仍然有價值

例如:

<input type="email" required>
<textarea minlength="10" maxlength="1000" required></textarea>

Declarative API 會從既有 Form 語意建立 Tool parameters,代表你原本為人類做好:

  • label
  • input type
  • required
  • select options
  • validation

這些都不會浪費。

所以「Agent-friendly」不代表拋棄 Semantic HTML,反而更應該把 HTML 做好。

用 toolparamdescription 補充 AI 不懂的語意

<select
  name="topic"
  required
  toolparamdescription="The department that should receive the contact message."
>
  <option value="sales">業務合作</option>
  <option value="support">技術支援</option>
  <option value="billing">帳務問題</option>
</select>

Agent 不需要猜「topic」代表什麼。

我不開 toolautosubmit 的原因

聯絡表單看起來低風險,但它仍然可能:

  • 寄出 Email。
  • 建 CRM lead。
  • 建客服 Ticket。
  • 觸發通知。

如果 Agent 因為理解錯誤送出十次,這就是副作用。

所以我的第一版流程是:

User:
幫我寫信問合作方案

Agent:
填好 name/email/subject/message

Browser:
顯示已填好的 Form

User:
看過後按「確認送出」

這就是最簡單的 Human-in-the-loop。

📸 圖片 2|Agent 已填好內容,但尚未送出
https://ithelp.ithome.com.tw/upload/images/20260922/20121296DQAWnWwL9D.png

如果要攔截 Submit

const form = document.querySelector('#contact-form');

form.addEventListener('submit', async event => {
  event.preventDefault();

  if (!form.reportValidity()) {
    return;
  }

  const data = Object.fromEntries(new FormData(form));

  const response = await fetch('/api/contact', {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json'
    },
    body: JSON.stringify(data)
  });

  if (!response.ok) {
    alert('送出失敗,請稍後再試');
    return;
  }

  alert('已送出');
});

📸 圖片 3|表單 Validation/送出前確認
https://ithelp.ithome.com.tw/upload/images/20260922/201212961XsZYC9kp0.png

如果之後真的允許 Agent 自動 Submit,還可以針對:

event.agentInvoked

做不同處理,並透過 respondWith() 把結果回給 Agent。

敏感欄位不要因為 Tool 很方便就全暴露

例如表單有:

姓名
Email
身分證字號
信用卡
醫療資訊

不代表全部都適合由 Agent 自動填入與送出。

Tool Schema/Declarative Form 設計時要問:

這個欄位是否真的需要?
這份資料是否應該由 Agent 接觸?
送出前是否需要再次確認?

WebMCP 讓操作更容易,也等於放大錯誤操作的能力。

Imperative Form 也可以

如果你的表單不是標準 HTML,或送出前有複雜流程,可以改用 Imperative Tool:

await document.modelContext.registerTool({
  name: 'prepare_contact_message',
  description: 'Fill the visible contact form without submitting it.',
  inputSchema: { /* ... */ },
  execute: async (input) => {
    fillContactForm(input);
    return 'The contact form is filled and ready for user review.';
  }
});

核心仍然一樣:

Prepare ≠ Execute consequential action

可帶走的重點

  1. Form Tool 不只是自動填值,還要考慮 Validation 和 Submit。
  2. Semantic HTML/labels 對 Declarative WebMCP 很重要。
  3. Tool 可以只負責 prepare,不一定直接 submit。
  4. 表單一旦會建立外部副作用,就應考慮使用者確認。
  5. 敏感資料不要因為 Agent 可以填就全部開放。

上一篇
Day 12|AI 為什麼總在選單迷路?用 Navigation Tool 讓它直接去對的頁面
系列文
WebMCP:30 天打造 AI Agent 看得懂、也操作得動的網站13
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言