Skip to content

iMessage

狀態:原生外部 CLI 整合。Gateway 會生成 imsg rpc 並透過 stdio 上的 JSON-RPC 進行通訊 (無需獨立的 daemon/port)。進階動作需要 imsg launch 以及成功的私人 API 探測。

Private API actions

回覆、點讚、特效、附件和群組管理。

Pairing

iMessage 私訊預設為配對模式。

Remote Mac

當 Gateway 未在 Messages Mac 上執行時,請使用 SSH 包裝器。

設定參考

完整的 iMessage 欄位參考。

  1. 安裝並驗證 imsg

    Terminal window
    brew install steipete/tap/imsg
    imsg rpc --help
    imsg launch
    openclaw channels status --probe
  2. 設定 OpenClaw

    {
    channels: {
    imessage: {
    enabled: true,
    cliPath: "/usr/local/bin/imsg",
    dbPath: "/Users/user/Library/Messages/chat.db",
    },
    },
    }
  3. 啟動 gateway

    Terminal window
    openclaw gateway
  4. 批准首次 DM 配對 (預設 dmPolicy)

    Terminal window
    openclaw pairing list imessage
    openclaw pairing approve imessage
    配對請求在 1 小時後過期。
  • Mac 上的 Messages 必須登入,並正在執行 imsg
  • 執行 OpenClaw/imsg 的程序上下文需要「完全磁碟存取權限」(用於存取 Messages 資料庫)。
  • 透過 Messages.app 傳送訊息需要「自動化」權限。
  • 若要使用進階動作(反應 / 編輯 / 取消傳送 / 視訊回覆 / 效果 / 群組操作),必須停用系統完整性保護 (SIP) —— 請參閱下方的啟用 imsg 私有 API。基本的文字與媒體傳送/接收不需要停用 SIP 也能運作。

imsg 提供兩種操作模式:

  • 基本模式(預設,無需更改 SIP):透過 send 傳送外寄文字與媒體、監看/接收傳入訊息、讀取歷史紀錄與聊天清單。這是您在全新安裝 brew install steipete/tap/imsg 並加上上述標準 macOS 權限後,開箱即得的體驗。
  • 私有 API 模式imsg 將一個輔助 dylib 注入 Messages.app 以呼叫內部 IMCore 函式。這能解鎖 reacteditunsendreply(視訊回覆)、sendWithEffectrenameGroupsetGroupIconaddParticipantremoveParticipantleaveGroup,以及輸入指示器和已讀回執。

若要達成本頻道文件所述的進階操作功能,您需要使用私有 API 模式。imsg README 中明確說明了此需求:

諸如 readtypinglaunch、橋接支援的豐富傳送、訊息變更與聊天管理等進階功能皆為選用。這些功能需要停用 SIP,並將一個輔助 dylib 注入 Messages.appimsg launch 會在 SIP 啟用時拒絕注入。

此輔助注入技術使用 imsg 自身的 dylib 來存取 Messages 私有 API。在 OpenClaw iMessage 路徑中,並不包含第三方伺服器或 BlueBubbles 執行環境。

  1. 在執行 Messages.app 的 Mac 上安裝(或升級) imsg

    Terminal window
    brew install steipete/tap/imsg
    imsg --version
    imsg status --json

    imsg status --json 輸出會報告 bridge_versionrpc_methods 以及每個方法的 selectors,因此您可以在開始之前查看目前版本支援的功能。

  2. 停用系統完整性保護。 這會因 macOS 版本而異,因為底層的 Apple 需求取決於作業系統和硬體:

    • macOS 10.13–10.15 (Sierra–Catalina): 透過終端機停用 Library Validation,重新啟動進入復原模式,執行 csrutil disable,然後重新啟動。
    • macOS 11+ (Big Sur 及更新版本),Intel: 進入復原模式 (或網際網路復原),執行 csrutil disable,然後重新啟動。
    • macOS 11+,Apple Silicon: 使用電源按鍵啟動順序進入復原模式;在最近的 macOS 版本中,當您點擊「繼續」時按住 左 Shift 鍵,然後執行 csrutil disable。虛擬機器設定遵循不同的流程 — 請先擷取虛擬機器快照。
    • macOS 26 / Tahoe: 庫驗證 原則和 imagent 私有權限 檢查進一步收緊;imsg 可能需要更新版本才能跟上。如果在 macOS 主要升級後,imsg launch 插入或特定的 selectors 開始返回 false,請在假設 SIP 步驟成功之前,先查看 imsg 的發行說明。

    在執行 imsg launch 之前,請遵循 Apple 的復原模式流程來停用 SIP。

  3. 注入輔助程式。 在 SIP 已停用且 Messages.app 已登入的情況下:

    Terminal window
    imsg launch

    當 SIP 仍啟用時,imsg launch 會拒絕插入,因此這也可以作為步驟 2 已完成的確認。

  4. 從 OpenClaw 驗證橋接:

    Terminal window
    openclaw channels status --probe

    iMessage 項目應報告 works,而 imsg status --json | jq '.selectors' 應顯示 retractMessagePart: true 加上您的 macOS 版本公開的任何 編輯 / 輸入 / 已讀 選擇器。actions.ts 中的 OpenClaw 外掛程式每個方法閘道只會宣傳基礎選擇器為 true 的動作,因此您在代理程式工具清單中看到的動作表面反映了橋接器在此主機上實際能執行的操作。

如果 openclaw channels status --probe 報告通道狀態為 works,但特定動作在調度時拋出「iMessage `

需要 imsg 私有 API 橋接」錯誤,請再次執行imsg launch— 輔助程式可能會失效(Messages.app 重啟、作業系統更新等),而快取的available: true` 狀態會繼續公告動作,直到下次探測重新整理。

如果您的威脅模型無法接受停用 SIP:

  • imsg 會回退到基本模式 — 僅限文字 + 媒體 + 接收。
  • OpenClaw 外掛程式仍然公告文字/媒體發送和入站監控;它只是從動作介面隱藏了 reacteditunsendreplysendWithEffect 和群組操作(根據每個方法的能力限制)。
  • 您可以在另一台非 Apple Silicon Mac(或專用的機器人 Mac)上關閉 SIP 以執行 iMessage 工作負載,同時在您的主要裝置上保持啟用 SIP。請參閱下方的 專用機器人 macOS 使用者(獨立的 iMessage 身份)

channels.imessage.dmPolicy 控制直接訊息:

  • pairing(預設)
  • allowlist
  • open(要求 allowFrom 包含 "*"
  • disabled

允許清單欄位:channels.imessage.allowFrom

允許清單項目必須識別發送者:代碼 或靜態發送者存取群組(`accessGroup:

)。對於 chat_id:chat_guid:chat_identifier:*等聊天目標使用channels.imessage.groupAllowFrom;對於數字 chat_id登錄金鑰使用channels.imessage.groups`。

舊版 iMessage 聊天也可以綁定到 ACP 工作階段。

快速操作員流程:

  • 在私訊或允許的群組聊天中執行 /acp spawn codex --bind here
  • 該同一 iMessage 對話中的後續訊息將路由到產生的 ACP 工作階段。
  • /new/reset 會就地重設相同的綁定 ACP 工作階段。
  • /acp close 會關閉 ACP 工作階段並移除綁定。

透過頂層 bindings[] 項目中的 type: "acp"match.channel: "imessage",支援設定的持久化綁定。

match.peer.id 可以使用:

` (建議用於穩定的群組綁定)

  • `chat_guid:

`

  • `chat_identifier:

`

範例:

{
agents: {
list: [
{
id: "codex",
runtime: {
type: "acp",
acp: { agent: "codex", backend: "acpx", mode: "persistent" },
},
},
],
},
bindings: [
{
type: "acp",
agentId: "codex",
match: {
channel: "imessage",
accountId: "default",
peer: { kind: "group", id: "chat_id:123" },
},
acp: { label: "codex-group" },
},
],
}

關於共享 ACP 綁定行為,請參閱 ACP Agents

Dedicated bot macOS user (separate iMessage identity)

使用專屬的 Apple ID 和 macOS 使用者,以便將機器人流量與您的個人「訊息」設定檔隔離。

典型流程:

  1. 建立/登入專屬的 macOS 使用者。
  2. 在該使用者中使用機器人 Apple ID 登入「訊息」。
  3. 在該使用者中安裝 imsg
  4. 建立 SSH 包裝器,以便 OpenClaw 可以在該使用者環境中執行 imsg
  5. 將 `channels.imessage.accounts.

.cliPath.dbPath` 指向該使用者設定檔。

首次執行可能需要在該機器人使用者工作階段中進行 GUI 核准 (自動化 + 完全磁碟存取權)。
透過 Tailscale 連接遠端 Mac(範例)

常見拓撲結構:

  • gateway 執行於 Linux/VM
  • iMessage + imsg 執行於您 tailnet 中的 Mac
  • cliPath wrapper 使用 SSH 來執行 imsg
  • remoteHost 啟用 SCP 附件擷取

範例:

{
channels: {
imessage: {
enabled: true,
cliPath: "~/.openclaw/scripts/imsg-ssh",
remoteHost: "[email protected]",
includeAttachments: true,
dbPath: "/Users/bot/Library/Messages/chat.db",
},
},
}
#!/usr/bin/env bash
exec ssh -T [email protected] imsg "$@"

使用 SSH 金鑰,讓 SSH 和 SCP 都能以非互動方式運作。 請確保主機金鑰已先被信任(例如 ssh [email protected]),以便填入 known_hosts

多帳號模式

iMessage 支援在 channels.imessage.accounts 下進行每個帳號的設定。

每個帳號都可以覆寫欄位,例如 cliPathdbPathallowFromgroupPolicymediaMaxMb、歷史記錄設定以及附件根目錄允許清單。

附件與媒體
  • 接收附件的功能預設為關閉 — 設定 channels.imessage.includeAttachments: true 以將照片、語音備忘錄、影片和其他附件轉送給 agent。若停用此功能,僅包含附件的 iMessage 訊息會在到達 agent 之前被丟棄,且可能完全不會產生 Inbound message 日誌行。
  • 當設定 remoteHost 時,可以透過 SCP 擷取遠端附件路徑
  • 附件路徑必須符合允許的根目錄:
    • channels.imessage.attachmentRoots (本機)
    • channels.imessage.remoteAttachmentRoots (遠端 SCP 模式)
    • 預設根目錄模式:/Users/*/Library/Messages/Attachments
  • SCP 使用嚴格的主機金鑰檢查 (StrictHostKeyChecking=yes)
  • 傳出媒體大小使用 channels.imessage.mediaMaxMb (預設 16 MB)
Outbound chunking
  • 文字區塊限制:channels.imessage.textChunkLimit (預設 4000)
  • 區塊模式:channels.imessage.chunkMode
    • length (預設)
    • newline (優先按段落分割)
Addressing formats

偏好的明確目標:

  • chat_id:123 (建議用於穩定路由)
  • chat_guid:...
  • chat_identifier:...

也支援帳號目標:

Terminal window
imsg chats --limit 20

imsg launch 正在運作且 openclaw channels status --probe 回報 privateApi.available: true 時,訊息工具除了正常的文字傳送外,還可以使用 iMessage 原生操作。

{
channels: {
imessage: {
actions: {
reactions: true,
edit: true,
unsend: true,
reply: true,
sendWithEffect: true,
sendAttachment: true,
renameGroup: true,
setGroupIcon: true,
addParticipant: true,
removeParticipant: true,
leaveGroup: true,
},
},
},
}
Available actions
  • react:新增/移除 iMessage 點回(messageIdemojiremove)。支援的點回對應至愛心、按讚、不喜歡、大笑、強調與問號。
  • reply:傳送串聯回覆給現有訊息(messageIdtextmessage,加上 chatGuidchatIdchatIdentifierto)。
  • sendWithEffect:傳送帶有 iMessage 特效的文字(textmessageeffecteffectId)。
  • edit:在支援的 macOS/私用 API 版本上編輯已傳送的訊息(messageIdtextnewText)。
  • unsend:在支援的 macOS/私用 API 版本上收回已傳送的訊息(messageId)。
  • upload-file:傳送媒體/檔案(buffer 為 base64 或已注水的 media/path/filePathfilename,選用 asVoice)。舊版別名:sendAttachment
  • renameGroupsetGroupIconaddParticipantremoveParticipantleaveGroup:當目前目標是群組對話時管理群組聊天。
Message IDs

入站 iMessage 上下文在可用時包含簡短的 MessageSid 值與完整的訊息 GUID。簡短 ID 的範圍限定於最近的記憶體內回覆快取,並在使用前會對目前的聊天進行檢查。如果簡短 ID 已過期或屬於其他聊天,請使用完整的 MessageSidFull 重試。

功能偵測

只有當緩存的探測狀態顯示橋接器不可用時,OpenClow 才會隱藏私有 API 操作。如果狀態未知,操作將保持可見並延遲發送探測,以便在 imsg launch 之後的第一個操作能夠成功,而無需單獨的手動狀態重新整理。

已讀回執與輸入狀態

當私有 API 橋接器正常運作時,接受的傳入聊天會在分派前標記為已讀,並且在代理程式產生回應時向發送者顯示輸入氣泡。使用以下方式停用已讀標記:

{
channels: {
imessage: {
sendReadReceipts: false,
},
},
}

較舊的 imsg 版本(早於逐方法功能列表)將會靜默地封鎖輸入/已讀功能;OpenClow 會在每次重新啟動時記錄一次警告,以便追溯缺失的回執。

傳入點讚

OpenClow 訂閱 iMessage 點讚,並將接受的回應作為系統事件而非一般訊息文字進行路由,因此使用者的點讚不會觸發普通的回應循環。

通知模式由 channels.imessage.reactionNotifications 控制:

  • "own"(預設):僅在使用者對由機器人發送的訊息做出反應時通知。
  • "all":對來自已授權發送者的所有傳入點讚進行通知。
  • "off":忽略傳入點讚。

每個帳戶的覆寫設定使用 `channels.imessage.accounts.

.reactionNotifications`。

iMessage 預設允許通道發起的設定寫入(當 commands.config: true 時用於 /config set|unset)。

停用方式:

{
channels: {
imessage: {
configWrites: false,
},
},
}

合併拆分發送的私訊(指令 + 網址在同一則組成中)

Section titled “合併拆分發送的私訊(指令 + 網址在同一則組成中)”

當使用者同時輸入指令和 URL 時 — 例如 Dump https://example.com/article — Apple 的訊息 應用程式會將發送拆分為 兩個獨立的 chat.db 資料列

  1. 一則文字訊息 ("Dump")。
  2. 一個 URL 預覽氣球 ("https://..."),並將 OG 預覽圖片作為附件。

這兩行資料在大多數設定中會相隔約 0.8-2.0 秒到達 OpenClaw。如果沒有合併,Agent 會在第一輪單獨收到指令,做出回覆(通常是「傳送網址給我」),然後直到第二輪才看到網址——此時指令的語境已經遺失。這是 Apple 的傳送管線特性,並非 OpenClaw 或 imsg 引入的問題。

channels.imessage.coalesceSameSenderDms 選項可讓私訊(DM)將連續的相同發送者行合併為單一 Agent 輪次。群組聊天則會繼續逐則訊息分發,以保留多使用者的輪次結構。

在以下情況啟用:

  • 您部署的技能期望在同一則訊息中收到 command + payload(例如:傾印、貼上、儲存、佇列等)。
  • 您的使用者會在指令旁貼上网址、圖片或長內容。
  • 您可以接受增加的私訊輪次延遲(見下文)。

在以下情況保持停用:

  • 您需要針對單字私訊觸發指令實現最低延遲。
  • 您所有的流程都是單次指令,沒有後續的資料負載。
使用者輸入chat.db 產生旗標關閉(預設)旗標開啟 + 2500 毫秒視窗
Dump https://example.com(一次發送)2 列,間隔約 1 秒兩次代理輪次:先「傾印」,然後是 URL一輪:合併文字 Dump https://example.com
Save this 📎image.jpg caption(附件 + 文字)2 列兩次輪次(合併時附件被捨棄)一次輪次:文字與圖片皆保留
/status(獨立指令)1 列即時發送等待至視窗結束,然後發送
單獨貼上 URL1 列即時發送即時發送(桶中只有一個項目)
文字 + URL 故意分為兩則訊息發送,間隔數分鐘2 列,超出視窗兩次輪次兩次輪次(視窗於期間過期)
快速連發(視窗內超過 10 則短私訊)N 列N 次輪次一次輪次,輸出受限(保留第一與最新的,套用文字/附件上限)
兩人在群組聊天中輸入M 位傳送者的 N 列M+ 次輪次(每個傳送者桶各一次)M+ 次輪次 — 群組聊天不合併

當閘道離線時(當機、重啟、Mac 睡眠、機器關機),imsg watch 會在閘道恢復上線後從目前的 chat.db 狀態繼續執行 — 預設情況下,間隔期間到達的任何訊息都不會被看到。補救機制會在下次啟動時重播這些訊息,以免代理無聲無息地錯過傳入流量。

追趕功能預設為停用。請針對每個頻道啟用它:

channels: {
imessage: {
catchup: {
enabled: true, // master switch (default: false)
maxAgeMinutes: 120, // skip rows older than now - 2h (default: 120, clamp 1..720)
perRunLimit: 50, // max rows replayed per startup (default: 50, clamp 1..500)
firstRunLookbackMinutes: 30, // first run with no cursor: look back 30 min (default: 30)
maxFailureRetries: 10, // give up on a wedged guid after 10 dispatch failures (default: 10)
},
},
}

每次 monitorIMessageProvider 啟動時執行一次,順序為 imsg launch 就緒 → watch.subscribeperformIMessageCatchup → 即時發送迴圈。補救機制本身會使用 chats.list 加上每個聊天室的 messages.history,透過與 imsg watch 相同的 JSON-RPC 用戶端運作。在補救期間到達的任何訊息會正常透過即時發送流程傳遞;現有的傳入去重快取會吸收與重播列的任何重疊。

每個重放的列都會通過即時分發路徑(evaluateIMessageInbound + dispatchInboundMessage)進行處理,因此允許清單、群組原則、去抖動器、回顯快取和已讀回執在重放訊息和即時訊息上的行為完全一致。

Catchup 會在 `

/imessage/catchup/

__

.json維護一個每個帳戶的游標(OpenClaw 狀態目錄預設為~/.openclaw,可透過 OPENCLAW_STATE_DIR` 覆寫):

{
"lastSeenMs": 1717900800000,
"lastSeenRowid": 482910,
"updatedAt": 1717900801234,
"failureRetries": { "

”: 1 } }

- 游標會在每次成功分派時推進,並在資料列分派擲回時保持不變——下次啟動時會從保持的游標重試同一列。
- 在對同一個 `guid` 連續拋出 `maxFailureRetries` 次錯誤後,catchup 會記錄一條 `warn` 並強制將游標推進到卡住的訊息之後,以便後續啟動能夠繼續進行。
- 已放棄的 guid 在後續運行中會被直接跳過(不嘗試分發),並計入運行摘要中的 `skippedGivenUp`。
### 操作員可見的訊號

imessage catchup: replayed=N skippedFromMe=… skippedGivenUp=… failed=… givenUp=… fetchedCount=… imessage catchup: giving up on guid=

after

failures; advancing cursor past it imessage catchup: fetched

rows across chats, capped to perRunLimit=

`WARN ... capped to perRunLimit` 行表示單次啟動未耗盡全部積壓。如果您的間隙經常超過預設的 50 行處理,請提高 `perRunLimit`(最高 500)。
### 何時保持停用
- Gateway 透過看門狗自動重啟持續運行,且間隙總是小於幾秒鐘——預設的關閉狀態即可。
- 私訊量很低,且錯過的訊息不會改變代理程式的行為 —— `firstRunLookbackMinutes` 初始視窗可能會在首次啟用時分發令人驚訝的舊上下文。
當您開啟 catchup 時,第一次沒有游標的啟動只會回溯 `firstRunLookbackMinutes`(預設 30 分鐘),而不是完整的 `maxAgeMinutes` 視窗 —— 這避免了重放啟用前的長時間歷史訊息。
## 疑難排解
imsg not found or RPC unsupported

驗證二進制檔案和 RPC 支援:

Terminal window
imsg rpc --help
imsg status --json
openclaw channels status --probe

如果探測報告 RPC 不支援,請更新 imsg。如果私有 API 操作不可用,請在登入的 macOS 使用者會話中執行 imsg launch 並再次探測。如果 Gateway 未在 macOS 上執行,請使用上述的 SSH 遠端 Mac 設定,而不是預設的本機 imsg 路徑。

Gateway is not running on macOS
預設的 `cliPath: "imsg"` 必須在登入 Messages 的 Mac 上執行。在 Linux 或 Windows 上,將 `channels.imessage.cliPath` 設定為 SSH 到該 Mac 並執行 `imsg "$@"` 的包裝腳本。
#!/usr/bin/env bash
exec ssh -T messages-mac imsg "$@"
然後執行:
Terminal window
openclaw channels status --probe --channel imessage
DMs are ignored

檢查:

  • channels.imessage.dmPolicy
  • channels.imessage.allowFrom
  • 配對核准(openclaw pairing list imessage
Group messages are ignored

檢查:

  • channels.imessage.groupPolicy
  • channels.imessage.groupAllowFrom
  • channels.imessage.groups 允許清單行為
  • 提及模式配置(agents.list[].groupChat.mentionPatterns
Remote attachments fail

檢查:

  • channels.imessage.remoteHost
  • channels.imessage.remoteAttachmentRoots
  • 從 Gateway 主機進行的 SSH/SCP 金鑰驗證
  • 主機金鑰存在於 Gateway 主機的 ~/.ssh/known_hosts
  • 執行 Messages 的 Mac 上遠端路徑的可讀性
macOS permission prompts were missed

在相同的使用者/工作階段內容中,於互動式 GUI 終端機重新執行並核准提示:

Terminal window
imsg chats --limit 1
imsg send

“test”

確認執行 OpenClaw/`imsg` 的程序內容已獲得「完全磁碟存取權」+「自動化」權限。