元件與 Modal

discli serve 模式支援 Discord 的互動式訊息元件:按鈕、選單與 modal 表單。這些元件透過 stdin 夾帶於 JSONL 協定一併送出。

按鈕

sendreply 動作加上 components 欄位即可傳送按鈕:

{"action": "send", "channel_id": "456", "content": "點擊按鈕:", "components": [
[
{"type": "button", "label": "核可", "style": "success", "custom_id": "approve", "emoji": "✅"},
{"type": "button", "label": "退回", "style": "danger", "custom_id": "reject", "emoji": "❌"},
{"type": "button", "label": "文件", "style": "link", "url": "https://example.com"}
]
]}

按鈕樣式

樣式顏色適用場景
primary藍色主要操作
secondary灰色次要操作
success綠色確認/通過
danger紅色破壞性或拒絕動作
link灰色外部連結(必須用 url,不可用 custom_id

加上 "disabled": true 可讓按鈕變灰且不可點選。

選單

字串選單

{"action": "send", "channel_id": "456", "content": "選擇:", "components": [
[{"type": "select", "custom_id": "color", "placeholder": "選擇一種顏色...", "options": [
{"label": "紅色", "value": "red", "emoji": "🔴", "description": "溫暖色系"},
{"label": "藍色", "value": "blue", "emoji": "🔵", "description": "清爽色系"}
]}]
]}

使用者、身分組、頻道選單

[{"type": "user_select", "custom_id": "pick_user", "placeholder": "選擇成員..."}]
[{"type": "role_select", "custom_id": "pick_role", "placeholder": "選擇身分組..."}]
[{"type": "channel_select", "custom_id": "pick_ch", "placeholder": "選擇頻道..."}]

處理互動

當使用者點擊按鈕或從選單選擇後,會收到 component_interaction 事件:

{"event": "component_interaction", "custom_id": "approve", "component_type": 2, "values": [], "user": "alice", "user_id": "123", "interaction_token": "ITK"}

可回應以下動作:

動作說明
interaction_respond立即回覆(支援 ephemeral: true
interaction_edit更新原始訊息(例如停用按鈕)
interaction_followup發送後續訊息
modal_send開啟 modal 表單

私訊回覆(僅點選者看得到)

{"action": "interaction_respond", "interaction_token": "ITK", "content": "完成!", "ephemeral": true}

更新原始訊息(停用按鈕)

{"action": "interaction_edit", "interaction_token": "ITK", "content": "已核可!✅", "components": [
[{"type": "button", "label": "已核可", "style": "secondary", "custom_id": "x", "disabled": true}]
]}

Modal 是彈出式表單,內含文字輸入欄位。只能從互動元件(按鈕)觸發。

開啟 modal

{"action": "modal_send", "interaction_token": "ITK", "title": "回饋表單", "custom_id": "feedback", "fields": [
{"label": "你的名字", "custom_id": "name", "style": "short", "placeholder": "輸入姓名...", "required": true},
{"label": "回饋內容", "custom_id": "feedback_text", "style": "long", "placeholder": "留下你的意見...", "max_length": 1000}
]}

欄位樣式為 short(單行)或 long(多行文字)。

處理提交

使用者提交後會收到 modal_submit 事件:

{"event": "modal_submit", "custom_id": "feedback", "fields": {"name": "Alice", "feedback_text": "這個機器人做得不錯!"}, "user": "alice", "interaction_token": "ITK2"}

回覆可用 interaction_followup

{"action": "interaction_followup", "interaction_token": "ITK2", "content": "感謝回覆!", "embed": {"title": "已收到回饋", "color": "57F287"}}

embed 與元件組合

{"action": "send", "channel_id": "456", "content": "", "embed": {
"title": "需要處理", "description": "要核可這個請求嗎?", "color": "FEE75C"
}, "components": [
[
{"type": "button", "label": "核可", "style": "success", "custom_id": "approve"},
{"type": "button", "label": "退回", "style": "danger", "custom_id": "reject"}
]
]}

注意事項

  • 元件僅能在 serve 模式 使用,CLI 單次指令無法直接傳送按鈕或選單
  • 每列最多可放 5 顆按鈕或 1 個選單
  • 一則訊息最多可有 5 列元件
  • 元件互動最晚須在 3 秒內回應(2.5 秒後會自動延遲)
  • Modal 每個文字欄位上限為 4000 字
  • custom_id 長度上限為 100 字元