OpenClaw 接入 iMessage:BlueBubbles 频道完整配置、访问控制与高级操作指南

原创2026-10-03 12:08:161,416 阅读
文章标签:人工智能AI Agent即时通讯后端本地部署语音

OpenClaw 接入 iMessage:BlueBubbles 频道完整配置、访问控制与高级操作指南

BlueBubbles 是 OpenClaw 官方捆绑(bundled)的 iMessage 接入频道,通过 HTTP REST API 与本机 macOS 上的 BlueBubbles 服务器通信,实现收发消息、打字指示、已读回执、Tapback 反应与消息编辑撤回等能力。本文基于 docs/channels/bluebubbles.md 整理完整配置项与操作流程,并结合仓库插件源码说明其底层原理,帮助你在一台 Mac 上把 OpenClaw 打造成真正可用的 iMessage 智能助手。

架构与工作方式:OpenClaw 如何驱动 iMessage

BlueBubbles 频道的核心思路是"代理桥接":iMessage 消息本身由 macOS 端的 BlueBubbles 辅助应用管理,OpenClaw 只通过 HTTP 与它对话。从插件注册代码 extensions/bluebubbles/index.ts 可以看到,插件在运行时做了两件事:注册频道(api.registerChannel)与注册 Webhook HTTP 处理器(api.registerHttpHandler),前者负责出站调用,后者负责接收入站消息。

具体来说,OpenClaw 依赖以下几类 BlueBubbles REST API 端点:

  • 连通性探测:GET /api/v1/ping,用于网关健康检查与 openclaw status 状态展示(见 probe.ts);
  • 发送文本:POST /api/v1/message/text,携带 chatGuid、message 等参数(见 send.ts);
  • 会话级操作:POST /api/v1/chat/:id/*,包括已读(/read)、打字(/typing)、改名(PUT)、增删成员、退群、设置群头像等(见 chat.ts)。

入站方向完全依赖 Webhook:BlueBubbles 服务器把新消息、消息更新、消息反应推送到 OpenClaw 网关;出站方向(回复、打字指示、已读回执、Tapback)则是 OpenClaw 主动发起的 REST 调用。附件与贴纸会被当作入站媒体摄入,并在可能的情况下以媒体占位符形式呈现给 Agent(源码中会将图片/视频/音频分别格式化为 <media:image>、<media:video>、<media:audio> 等占位符,见 monitor.ts)。

从频道能力声明(channel.ts 的 capabilities 字段)看,该频道原生支持私聊(direct)与群聊(group)、媒体(media)、反应(reactions)、编辑(edit)、撤回(unsend)、回复线程(reply)、消息特效(effects)以及群组管理(groupManagement)。相比传统 imsg 频道,其 API 更丰富、配置更简单,因此被标记为 iMessage 集成的推荐方案(preferOver: ["imessage"])。

系统兼容性:推荐且经过验证的系统是 macOS Sequoia(15)。macOS Tahoe(26)可以运行,但编辑功能目前不可用(Apple 在 26 中移除了相关私有 API),群组头像更新可能显示成功但实际不生效。

快速开始:五分钟接入 iMessage

  1. 在 Mac 上安装 BlueBubbles 服务器应用,并按其官方安装指引完成基础配置;
  2. 在 BlueBubbles 的配置中启用 Web API 并设置 API 密码;
  3. 运行 openclaw onboard 并选择 BlueBubbles,或手动写入配置:
{
  channels: {
    bluebubbles: {
      enabled: true,
      serverUrl: "http://192.168.1.100:1234",
      password: "example-password",
      webhookPath: "/bluebubbles-webhook",
    },
  },
}
  1. 在 BlueBubbles 中把 Webhook 指向你的网关,例如 https://your-gateway-host:3000/bluebubbles-webhook?password=<password>;
  2. 启动网关。网关会注册该 Webhook 处理器并开始配对流程。

其中 serverUrl 是 BlueBubbles REST API 的基地址,源码在 types.ts 的 normalizeBlueBubblesServerUrl 中会做归一化:未带协议时自动补 http://,并去除末尾多余的 /。password 同时用于 API 调用鉴权(以 query 参数形式附加在每个请求上)与 Webhook 回调鉴权,务必妥善保管。

Onboarding:向导与 CLI 两种配置途径

交互式向导:

openclaw onboard

向导会依次询问以下信息(流程实现在 onboarding.ts 中,含 URL 格式校验与密码必填校验):

  • Server URL(必填):BlueBubbles 服务器地址,如 http://192.168.1.100:1234,可在 BlueBubbles 应用的 Connection 设置中查看;
  • Password(必填):BlueBubbles 服务器设置中的 API 密码;
  • Webhook path(可选):默认 /bluebubbles-webhook,自定义时必须 / 开头;
  • DM policy:pairing、allowlist、open、disabled;
  • Allow list:手机号、邮箱或聊天目标(支持逗号或换行分隔多条)。

命令行直接添加:

openclaw channels add bluebubbles --http-url http://192.168.1.100:1234 --password <password>

从 channel.ts 的 setup.validateInput 可见,CLI 方式强制要求 --http-url 与 --password 二者齐全,缺一即报错。此外该频道支持多账号:除默认账号外,可通过 channels.bluebubbles.accounts.<id> 配置多个独立的 BlueBubbles 服务器(如多台 Mac),每个账号可独立设置 serverUrl、password、webhookPath 与各自的访问策略。

访问控制:私聊配对、群组策略与提及门控

私聊(DM)策略

  • 默认 channels.bluebubbles.dmPolicy = "pairing",即使用配对码做身份交换;
  • 未知发送者会收到一个配对码,其消息会被忽略,直到通过审批;配对码 1 小时后过期;
  • 审批命令:
openclaw pairing list bluebubbles
openclaw pairing approve bluebubbles <CODE>
  • 其他取值:allowlist(仅允许 allowFrom 中的发送者)、open(所有人)、disabled(关闭私聊)。完整配对流程见 配对指南。

群组策略

  • channels.bluebubbles.groupPolicy = open | allowlist | disabled,默认 allowlist;
  • 当为 allowlist 时,channels.bluebubbles.groupAllowFrom 控制哪些发送者可以触发机器人。

提及门控(Mention Gating)

BlueBubbles 支持群聊提及门控,行为与 iMessage/WhatsApp 一致:

  • 使用 agents.list[].groupChat.mentionPatterns(或 messages.groupChat.mentionPatterns)检测提及;
  • 当群组开启 requireMention 时,Agent 只在被点名时才回复;
  • 来自已授权发送者的控制命令可以绕过提及门控。

按群组精细化配置示例:

{
  channels: {
    bluebubbles: {
      groupPolicy: "allowlist",
      groupAllowFrom: ["+15555550123"],
      groups: {
        "*": { requireMention: true }, // 所有群默认需要提及
        "iMessage;-;chat123": { requireMention: false }, // 特定群覆盖
      },
    },
  },
}

从 config-schema.ts 可见,每组除 requireMention 外还支持 tools: { allow: [], deny: [] } 做工具策略覆盖。群组 ID 使用 chat_guid 或聊天标识(见后文"目标寻址")。群组消息被 allowlist 拦截时,monitor.ts 会打印明确的引导日志,提示你应将该群 ID 加入 groupAllowFrom。

控制命令门控

控制命令(如 /config、/model)要求发送者授权:私聊依据 allowFrom,群聊依据 groupAllowFrom。已授权发送者在群聊中即使未提及也可执行控制命令。底层发送者校验逻辑在 targets.ts 的 isAllowedBlueBubblesSender 中实现:支持 chat_id、chat_guid、chat_identifier、手机号/邮箱句柄多种匹配方式,通配符 * 放行全部。

打字指示、已读回执与流式分块

  • 打字指示:在回复生成期间自动发送打字开始事件,由 BlueBubbles 在发送完成或超时后自动清除(手动发送停止事件并不可靠,源码中 DELETE /typing 仅作为降级手段,见 chat.ts);
  • 已读回执:由 channels.bluebubbles.sendReadReceipts 控制,默认 true,通过 POST /api/v1/chat/:id/read 实现。
{
  channels: {
    bluebubbles: {
      sendReadReceipts: false, // 关闭已读回执
    },
  },
}

Block streaming(分块流式发送)控制回复是"一次性整条发送"还是"按块流式发送",默认关闭(false),需要流式回复时必须开启:

{
  channels: {
    bluebubbles: {
      blockStreaming: true,
    },
  },
}

开启后,流式生成的文本会以分块形式发送到 iMessage,降低首字延迟感知。

高级消息操作(Advanced Actions)

BlueBubbles 频道支持多种原生级消息操作,通过 channels.bluebubbles.actions 统一开关,默认全部开启:

{
  channels: {
    bluebubbles: {
      actions: {
        reactions: true, // Tapback 反应(默认 true)
        edit: true, // 编辑已发送消息(macOS 13+,macOS 26 Tahoe 上不可用)
        unsend: true, // 撤回消息(macOS 13+)
        reply: true, // 按消息 GUID 回复线程
        sendWithEffect: true, // 消息特效(slam、loud 等)
        renameGroup: true, // 重命名群聊
        setGroupIcon: true, // 设置群头像/照片(macOS 26 Tahoe 上不稳定)
        addParticipant: true, // 添加群成员
        removeParticipant: true, // 移除群成员
        leaveGroup: true, // 退出群聊
        sendAttachment: true, // 发送附件/媒体
      },
    },
  },
}

各操作所需参数如下:

操作 参数 说明
react messageId、emoji、remove 添加/移除 Tapback 反应,需 BlueBubbles 私有 API(POST /api/v1/message/react)
edit messageId、text 编辑已发送消息,macOS 26 Tahoe 上不可用
unsend messageId 撤回消息
reply messageId、text、to 回复指定消息(线程)
sendWithEffect text、to、effectId 带 iMessage 特效发送
renameGroup chatGuid、displayName 重命名群聊
setGroupIcon chatGuid、media 设置群头像(macOS 26 Tahoe 上 API 可能返回成功但不同步)
addParticipant chatGuid、address 添加群成员
removeParticipant chatGuid、address 移除群成员
leaveGroup chatGuid 退出群聊
sendAttachment to、buffer、filename、asVoice 发送媒体/文件

消息特效(sendWithEffect)细节:源码 send.ts 内置了一张 Apple 特效 ID 映射表,支持短名自动归一化(大小写、空格、下划线、连字符均可容忍)。气泡特效包括 slam、loud、gentle、invisible-ink;屏幕特效包括 echo、spotlight、balloons、confetti、love/heart/hearts、lasers、fireworks、celebration。传入未知名称时按原文透传。带特效发送与回复线程都要求 method: "private-api",即需要启用 BlueBubbles 私有 API。

语音消息:sendAttachment 设置 asVoice: true,并提供 MP3 或 CAF 格式音频,即可作为 iMessage 语音消息发送——BlueBubbles 会在发送时自动把 MP3 转换为 CAF。

动作自动隐藏:OpenClaw 会依据 BlueBubbles 服务器上报的 macOS 版本(来自 GET /api/v1/server/info 的 os_version,见 probe.ts)自动隐藏已知不可用的操作(如 macOS 26 上的 edit)。若 edit 在 macOS 26 上仍然出现,可手动关闭:channels.bluebubbles.actions.edit=false。

消息 ID:短 ID 与完整 ID 的选择

为节省 Token,OpenClaw 可能向 Agent 暴露短消息 ID(如 1、2)。要点:

  • MessageSid / ReplyToId 可能是短 ID;
  • MessageSidFull / ReplyToIdFull 始终是提供方完整 ID;
  • 短 ID 保存在进程内存中,重启或缓存淘汰后会失效;
  • 操作(react/edit/unsend/reply 等)接受短 ID 或完整 ID,但短 ID 若已失效会直接报错。

从 monitor.ts 的实现看,短 ID 由进程内的双向映射表(blueBubblesShortIdToUuid / blueBubblesUuidToShortId)维护:完整 GUID 按序分配递增数字短 ID,缓存上限 2000 条、TTL 6 小时,过期或超限时双向映射会被同步清理;解析时若发现数字型短 ID 已不在映射表中,且调用方要求必须已知(requireKnownShortId: true),会抛出明确错误"使用 MessageSidFull"。

因此,需要持久化或自动化重放的操作,请一律使用完整 ID:

  • 模板变量:{{MessageSidFull}}、{{ReplyToIdFull}}
  • 入站上下文:MessageSidFull / ReplyToIdFull

完整模板变量清单见 网关配置文档。

媒体与消息长度限制

  • 入站附件会被下载并存入媒体缓存;
  • 媒体大小上限:channels.bluebubbles.mediaMaxMb,默认 8 MB;
  • 出站文本分块:channels.bluebubbles.textChunkLimit,默认 4000 字符;
  • 分块模式:channels.bluebubbles.chunkMode:
    • length(默认):仅当超出 textChunkLimit 时才按长度切分;
    • newline:先按空行(段落边界)切分,再做长度切分,适合保留语义的段落式长文。

另外,入站 Webhook 事件默认带有 500ms 的去抖窗口(monitor.ts),用于合并 BlueBubbles 在发送 URL 文本 + 链接预览气泡时产生的两条独立事件;控制命令不参与去抖,会被立即处理。

配置参考(完整清单)

Provider 选项(默认账号直接写于 channels.bluebubbles,多账号场景下对应字段写入 channels.bluebubbles.accounts.<id>):

  • channels.bluebubbles.enabled:启用/禁用频道。
  • channels.bluebubbles.serverUrl:BlueBubbles REST API 基地址。
  • channels.bluebubbles.password:API 密码。
  • channels.bluebubbles.webhookPath:Webhook 端点路径(默认 /bluebubbles-webhook)。
  • channels.bluebubbles.dmPolicy:pairing | allowlist | open | disabled(默认 pairing)。
  • channels.bluebubbles.allowFrom:私聊白名单(句柄、邮箱、E.164 号码、chat_id:*、chat_guid:*)。
  • channels.bluebubbles.groupPolicy:open | allowlist | disabled(默认 allowlist)。
  • channels.bluebubbles.groupAllowFrom:群组发送者白名单。
  • channels.bluebubbles.groups:按群组配置(requireMention、tools 等)。
  • channels.bluebubbles.sendReadReceipts:发送已读回执(默认 true)。
  • channels.bluebubbles.blockStreaming:启用分块流式发送(默认 false;流式回复必需)。
  • channels.bluebubbles.textChunkLimit:出站分块字符数(默认 4000)。
  • channels.bluebubbles.chunkMode:length(默认)按长度切分;newline 先按段落边界切分。
  • channels.bluebubbles.mediaMaxMb:入站媒体大小上限 MB(默认 8)。
  • channels.bluebubbles.historyLimit:群聊上下文保留的最大消息数(0 表示关闭)。
  • channels.bluebubbles.dmHistoryLimit:私聊历史上限。
  • channels.bluebubbles.actions:按操作启用/禁用。
  • channels.bluebubbles.accounts:多账号配置。

相关全局选项:

  • agents.list[].groupChat.mentionPatterns(或 messages.groupChat.mentionPatterns)。
  • messages.responsePrefix。

完整配置体系见 网关配置文档。

目标寻址与投递目标

发送消息时优先使用 chat_guid 以获得稳定路由:

  • chat_guid:iMessage;-;+15555550123(群聊首选格式)
  • chat_id:123
  • chat_identifier:...
  • 直接句柄:+15555550123、user@example.com

从 targets.ts 的解析实现可以确认三种地址形态的语义:

  • chat_guid 是 service;separator;identifier 三段结构,其中 iMessage;-;handle 表示私聊(分隔符为 -),iMessage;+;groupId 表示群聊(分隔符为 +);私聊的 chat_guid 可被归一化为纯句柄参与白名单匹配;
  • chat_id 为数值型聊天 ID(兼容 chatid:、chat: 前缀);
  • chat_identifier 为 GUID 结构中的第三段标识(兼容 UUID/hex/chat<digits> 形态),并支持 imessage:、sms:、auto: 服务前缀强制指定发送渠道。

自动建会话:如果直接句柄尚不存在对应的私聊会话,OpenClaw 会通过 POST /api/v1/chat/new 自动创建(携带 addresses 与首条消息,见 send.ts)。该端点要求启用 BlueBubbles 私有 API,未启用时请求会以 400/403 失败并提示。向不存在的句柄发消息时,建议优先检查 BlueBubbles 的私有 API 开关。

安全建议

  • Webhook 请求通过比对 query 参数或请求头中的 guid/password 与 channels.bluebubbles.password 完成鉴权。从 monitor.ts 的 handleBlueBubblesWebhookRequest 可以看到支持 guid、password query 参数以及 x-guid、x-password、x-bluebubbles-guid、authorization 等请求头;无论回环还是代理拓扑,鉴权始终强制开启,无法匹配时返回 401 并在日志中打码记录来源;
  • 把 API 密码与 Webhook 端点视为凭据,勿泄露到公共配置或聊天记录;
  • 如需将 BlueBubbles 服务器暴露到局域网外,请启用 HTTPS 并配置防火墙规则。

故障排查

  • 打字/已读事件不工作:检查 BlueBubbles 的 Webhook 日志,确认网关路径与 channels.bluebubbles.webhookPath 一致;
  • 配对码过期:配对码 1 小时后过期,用 openclaw pairing list bluebubbles 与 openclaw pairing approve bluebubbles <code> 重新审批;
  • 反应不可用:Tapback 依赖 BlueBubbles 私有 API(POST /api/v1/message/react),确认服务器版本已暴露该端点;
  • 编辑/撤回失败:需要 macOS 13+ 与兼容的 BlueBubbles 服务器版本;macOS 26(Tahoe)因私有 API 变更,编辑功能当前不可用;
  • 群头像不同步:macOS 26(Tahoe)上 API 可能返回成功但图标不更新,属于已知不稳定的表现;
  • 查看健康状态:openclaw status --all 或 openclaw status --deep,其中会包含对 BlueBubbles 服务器的 ping 探测结果(probe.ts 的 /api/v1/ping)。

延伸阅读

登录后查看全文
openclaw-cn