agent-messenger 2.27.2 → 2.28.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/README.md +11 -1
- package/.claude-plugin/marketplace.json +14 -1
- package/.claude-plugin/plugin.json +4 -2
- package/AGENTS.md +4 -0
- package/README.md +40 -9
- package/dist/package.json +10 -2
- package/dist/src/cli.d.ts.map +1 -1
- package/dist/src/cli.js +3 -0
- package/dist/src/cli.js.map +1 -1
- package/dist/src/platforms/discordbot/cli.js +1 -1
- package/dist/src/platforms/imessage/cli.d.ts +5 -0
- package/dist/src/platforms/imessage/cli.d.ts.map +1 -0
- package/dist/src/platforms/imessage/cli.js +31 -0
- package/dist/src/platforms/imessage/cli.js.map +1 -0
- package/dist/src/platforms/imessage/client.d.ts +43 -0
- package/dist/src/platforms/imessage/client.d.ts.map +1 -0
- package/dist/src/platforms/imessage/client.js +190 -0
- package/dist/src/platforms/imessage/client.js.map +1 -0
- package/dist/src/platforms/imessage/commands/auth.d.ts +31 -0
- package/dist/src/platforms/imessage/commands/auth.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/auth.js +100 -0
- package/dist/src/platforms/imessage/commands/auth.js.map +1 -0
- package/dist/src/platforms/imessage/commands/chat.d.ts +3 -0
- package/dist/src/platforms/imessage/commands/chat.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/chat.js +42 -0
- package/dist/src/platforms/imessage/commands/chat.js.map +1 -0
- package/dist/src/platforms/imessage/commands/doctor.d.ts +25 -0
- package/dist/src/platforms/imessage/commands/doctor.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/doctor.js +101 -0
- package/dist/src/platforms/imessage/commands/doctor.js.map +1 -0
- package/dist/src/platforms/imessage/commands/index.d.ts +7 -0
- package/dist/src/platforms/imessage/commands/index.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/index.js +7 -0
- package/dist/src/platforms/imessage/commands/index.js.map +1 -0
- package/dist/src/platforms/imessage/commands/message.d.ts +5 -0
- package/dist/src/platforms/imessage/commands/message.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/message.js +127 -0
- package/dist/src/platforms/imessage/commands/message.js.map +1 -0
- package/dist/src/platforms/imessage/commands/setup.d.ts +20 -0
- package/dist/src/platforms/imessage/commands/setup.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/setup.js +57 -0
- package/dist/src/platforms/imessage/commands/setup.js.map +1 -0
- package/dist/src/platforms/imessage/commands/shared.d.ts +10 -0
- package/dist/src/platforms/imessage/commands/shared.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/shared.js +53 -0
- package/dist/src/platforms/imessage/commands/shared.js.map +1 -0
- package/dist/src/platforms/imessage/commands/whoami.d.ts +3 -0
- package/dist/src/platforms/imessage/commands/whoami.d.ts.map +1 -0
- package/dist/src/platforms/imessage/commands/whoami.js +20 -0
- package/dist/src/platforms/imessage/commands/whoami.js.map +1 -0
- package/dist/src/platforms/imessage/credential-manager.d.ts +22 -0
- package/dist/src/platforms/imessage/credential-manager.d.ts.map +1 -0
- package/dist/src/platforms/imessage/credential-manager.js +111 -0
- package/dist/src/platforms/imessage/credential-manager.js.map +1 -0
- package/dist/src/platforms/imessage/ensure-auth.d.ts +2 -0
- package/dist/src/platforms/imessage/ensure-auth.d.ts.map +1 -0
- package/dist/src/platforms/imessage/ensure-auth.js +13 -0
- package/dist/src/platforms/imessage/ensure-auth.js.map +1 -0
- package/dist/src/platforms/imessage/errors.d.ts +3 -0
- package/dist/src/platforms/imessage/errors.d.ts.map +1 -0
- package/dist/src/platforms/imessage/errors.js +25 -0
- package/dist/src/platforms/imessage/errors.js.map +1 -0
- package/dist/src/platforms/imessage/index.d.ts +7 -0
- package/dist/src/platforms/imessage/index.d.ts.map +1 -0
- package/dist/src/platforms/imessage/index.js +5 -0
- package/dist/src/platforms/imessage/index.js.map +1 -0
- package/dist/src/platforms/imessage/rpc.d.ts +20 -0
- package/dist/src/platforms/imessage/rpc.d.ts.map +1 -0
- package/dist/src/platforms/imessage/rpc.js +133 -0
- package/dist/src/platforms/imessage/rpc.js.map +1 -0
- package/dist/src/platforms/imessage/types.d.ts +59 -0
- package/dist/src/platforms/imessage/types.d.ts.map +1 -0
- package/dist/src/platforms/imessage/types.js +29 -0
- package/dist/src/platforms/imessage/types.js.map +1 -0
- package/dist/src/platforms/instagram/cli.js +1 -1
- package/dist/src/platforms/instagram/client.d.ts +6 -1
- package/dist/src/platforms/instagram/client.d.ts.map +1 -1
- package/dist/src/platforms/instagram/client.js +17 -0
- package/dist/src/platforms/instagram/client.js.map +1 -1
- package/dist/src/platforms/instagram/hybrid-listener.d.ts +48 -0
- package/dist/src/platforms/instagram/hybrid-listener.d.ts.map +1 -0
- package/dist/src/platforms/instagram/hybrid-listener.js +154 -0
- package/dist/src/platforms/instagram/hybrid-listener.js.map +1 -0
- package/dist/src/platforms/instagram/index.d.ts +2 -0
- package/dist/src/platforms/instagram/index.d.ts.map +1 -1
- package/dist/src/platforms/instagram/index.js +2 -0
- package/dist/src/platforms/instagram/index.js.map +1 -1
- package/dist/src/platforms/instagram/mqtt/connection.d.ts +4 -0
- package/dist/src/platforms/instagram/mqtt/connection.d.ts.map +1 -0
- package/dist/src/platforms/instagram/mqtt/connection.js +66 -0
- package/dist/src/platforms/instagram/mqtt/connection.js.map +1 -0
- package/dist/src/platforms/instagram/mqtt/thrift.d.ts +22 -0
- package/dist/src/platforms/instagram/mqtt/thrift.d.ts.map +1 -0
- package/dist/src/platforms/instagram/mqtt/thrift.js +143 -0
- package/dist/src/platforms/instagram/mqtt/thrift.js.map +1 -0
- package/dist/src/platforms/instagram/mqtt/transport.d.ts +42 -0
- package/dist/src/platforms/instagram/mqtt/transport.d.ts.map +1 -0
- package/dist/src/platforms/instagram/mqtt/transport.js +246 -0
- package/dist/src/platforms/instagram/mqtt/transport.js.map +1 -0
- package/dist/src/platforms/instagram/realtime-listener.d.ts +33 -0
- package/dist/src/platforms/instagram/realtime-listener.d.ts.map +1 -0
- package/dist/src/platforms/instagram/realtime-listener.js +151 -0
- package/dist/src/platforms/instagram/realtime-listener.js.map +1 -0
- package/dist/src/platforms/kakaotalk/cli.js +1 -1
- package/dist/src/platforms/line/cli.js +1 -1
- package/dist/src/platforms/webex/cli.js +1 -1
- package/dist/src/platforms/webexbot/cli.js +1 -1
- package/dist/src/platforms/wechatbot/cli.js +1 -1
- package/dist/src/platforms/whatsapp/cli.js +1 -1
- package/dist/src/platforms/whatsappbot/cli.js +1 -1
- package/dist/src/tui/adapters/imessage-adapter.d.ts +21 -0
- package/dist/src/tui/adapters/imessage-adapter.d.ts.map +1 -0
- package/dist/src/tui/adapters/imessage-adapter.js +110 -0
- package/dist/src/tui/adapters/imessage-adapter.js.map +1 -0
- package/dist/src/tui/app.d.ts.map +1 -1
- package/dist/src/tui/app.js +9 -0
- package/dist/src/tui/app.js.map +1 -1
- package/docs/content/docs/agent-skills.mdx +1 -1
- package/docs/content/docs/cli/imessage.mdx +99 -0
- package/docs/content/docs/cli/instagram.mdx +1 -1
- package/docs/content/docs/cli/meta.json +1 -0
- package/docs/content/docs/index.mdx +9 -6
- package/docs/content/docs/quick-start.mdx +2 -0
- package/docs/content/docs/sdk/instagram.mdx +90 -5
- package/docs/content/docs/tui.mdx +4 -3
- package/package.json +10 -2
- package/scripts/postbuild.ts +12 -15
- package/skills/agent-channeltalk/SKILL.md +1 -1
- package/skills/agent-channeltalkbot/SKILL.md +1 -1
- package/skills/agent-discord/SKILL.md +1 -1
- package/skills/agent-discordbot/SKILL.md +1 -1
- package/skills/agent-imessage/SKILL.md +133 -0
- package/skills/agent-imessage/references/authentication.md +66 -0
- package/skills/agent-imessage/references/permissions.md +31 -0
- package/skills/agent-imessage/references/setup.md +49 -0
- package/skills/agent-instagram/SKILL.md +72 -2
- package/skills/agent-instagram/references/common-patterns.md +36 -0
- package/skills/agent-instagram/templates/monitor-chat.sh +5 -0
- package/skills/agent-kakaotalk/SKILL.md +1 -1
- package/skills/agent-line/SKILL.md +1 -1
- package/skills/agent-slack/SKILL.md +1 -1
- package/skills/agent-slackbot/SKILL.md +1 -1
- package/skills/agent-teams/SKILL.md +1 -1
- package/skills/agent-telegram/SKILL.md +1 -1
- package/skills/agent-telegrambot/SKILL.md +1 -1
- package/skills/agent-webex/SKILL.md +1 -1
- package/skills/agent-webexbot/SKILL.md +1 -1
- package/skills/agent-wechatbot/SKILL.md +1 -1
- package/skills/agent-whatsapp/SKILL.md +1 -1
- package/skills/agent-whatsappbot/SKILL.md +1 -1
- package/src/cli.ts +4 -0
- package/src/platforms/imessage/cli.ts +39 -0
- package/src/platforms/imessage/client.test.ts +137 -0
- package/src/platforms/imessage/client.ts +253 -0
- package/src/platforms/imessage/commands/auth.ts +142 -0
- package/src/platforms/imessage/commands/chat.ts +51 -0
- package/src/platforms/imessage/commands/doctor.test.ts +80 -0
- package/src/platforms/imessage/commands/doctor.ts +139 -0
- package/src/platforms/imessage/commands/index.ts +6 -0
- package/src/platforms/imessage/commands/message.test.ts +20 -0
- package/src/platforms/imessage/commands/message.ts +151 -0
- package/src/platforms/imessage/commands/setup.test.ts +52 -0
- package/src/platforms/imessage/commands/setup.ts +76 -0
- package/src/platforms/imessage/commands/shared.test.ts +19 -0
- package/src/platforms/imessage/commands/shared.ts +69 -0
- package/src/platforms/imessage/commands/whoami.ts +22 -0
- package/src/platforms/imessage/credential-manager.test.ts +122 -0
- package/src/platforms/imessage/credential-manager.ts +123 -0
- package/src/platforms/imessage/ensure-auth.ts +18 -0
- package/src/platforms/imessage/errors.ts +27 -0
- package/src/platforms/imessage/index.test.ts +13 -0
- package/src/platforms/imessage/index.ts +16 -0
- package/src/platforms/imessage/rpc.ts +157 -0
- package/src/platforms/imessage/test-stub-imsg.mjs +147 -0
- package/src/platforms/imessage/types.test.ts +47 -0
- package/src/platforms/imessage/types.ts +95 -0
- package/src/platforms/instagram/client.ts +23 -0
- package/src/platforms/instagram/hybrid-listener.test.ts +135 -0
- package/src/platforms/instagram/hybrid-listener.ts +196 -0
- package/src/platforms/instagram/index.ts +10 -0
- package/src/platforms/instagram/mqtt/connection.ts +72 -0
- package/src/platforms/instagram/mqtt/thrift.test.ts +91 -0
- package/src/platforms/instagram/mqtt/thrift.ts +159 -0
- package/src/platforms/instagram/mqtt/transport.ts +285 -0
- package/src/platforms/instagram/realtime-listener.test.ts +34 -0
- package/src/platforms/instagram/realtime-listener.ts +201 -0
- package/src/platforms/webexbot/cli.ts +0 -0
- package/src/tui/adapters/imessage-adapter.ts +131 -0
- package/src/tui/app.ts +13 -0
package/.claude-plugin/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# Agent Messenger - Claude Code Plugin
|
|
2
2
|
|
|
3
|
-
Messaging platform interaction skills for AI agents and Claude Code. Supports Slack, Discord, Microsoft Teams, Telegram, Telegram Bot, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk (beta).
|
|
3
|
+
Messaging platform interaction skills for AI agents and Claude Code. Supports Slack, Discord, Microsoft Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, iMessage (Mac-only), Instagram, KakaoTalk, and Channel Talk (beta).
|
|
4
4
|
|
|
5
5
|
## Installation
|
|
6
6
|
|
|
@@ -108,6 +108,14 @@ Enables AI agents to interact with messaging platforms through CLI interfaces:
|
|
|
108
108
|
- **QR code login** — authenticates as secondary device
|
|
109
109
|
- **Multi-account support** with easy switching
|
|
110
110
|
|
|
111
|
+
### iMessage (`agent-imessage`) — Mac-only
|
|
112
|
+
- **Send messages** to chats, groups, and phone/email recipients
|
|
113
|
+
- **Read chats** and message history
|
|
114
|
+
- **List chats** (source of chat ids/guids)
|
|
115
|
+
- **Watch for new messages** in real time (resumable JSON lines)
|
|
116
|
+
- **Standard tapbacks** (love, like, dislike, etc.)
|
|
117
|
+
- **Runs on a Mac** via the [imsg](https://github.com/openclaw/imsg) tool — no API, no network, no server
|
|
118
|
+
|
|
111
119
|
### Instagram (`agent-instagram`)
|
|
112
120
|
- **Send messages** to DM conversations
|
|
113
121
|
- **Read chats** and message history
|
|
@@ -190,6 +198,7 @@ All commands output JSON by default for easy AI consumption. Use `--pretty` for
|
|
|
190
198
|
|
|
191
199
|
- Desktop app installed and logged in for the platform(s) you want to use (Slack, Discord, Teams, KakaoTalk, and/or Channel Talk). For Slack and Discord, QR code sign-in is the recommended alternative — no desktop app required (Discord needs the mobile app to scan). Instagram uses username/password auth
|
|
192
200
|
- For Telegram: TDLib is bundled; API credentials are auto-provisioned on first login
|
|
201
|
+
- For iMessage: macOS only — requires [imsg](https://github.com/openclaw/imsg) installed, with Full Disk Access and Automation → Messages granted to the launching app/terminal (macOS grants these to the parent process, not the `imsg` binary)
|
|
193
202
|
- Node.js 18+ or Bun runtime
|
|
194
203
|
|
|
195
204
|
## Quick Start
|
|
@@ -276,6 +285,7 @@ agent-discord file upload <channel-id> ./report.pdf
|
|
|
276
285
|
- [WhatsApp Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-whatsapp/SKILL.md)
|
|
277
286
|
- [WhatsApp Bot Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-whatsappbot/SKILL.md)
|
|
278
287
|
- [LINE Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-line/SKILL.md)
|
|
288
|
+
- [iMessage Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-imessage/SKILL.md)
|
|
279
289
|
- [Instagram Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-instagram/SKILL.md)
|
|
280
290
|
- [KakaoTalk Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-kakaotalk/SKILL.md)
|
|
281
291
|
- [Channel Talk Skill Documentation](https://github.com/agent-messenger/agent-messenger/blob/main/skills/agent-channeltalk/SKILL.md)
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://anthropic.com/claude-code/marketplace.schema.json",
|
|
3
3
|
"name": "agent-messenger",
|
|
4
|
-
"description": "Messaging platform interaction skills for AI agents - Slack, Discord, Microsoft Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk",
|
|
4
|
+
"description": "Messaging platform interaction skills for AI agents - Slack, Discord, Microsoft Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, iMessage, Instagram, KakaoTalk, and Channel Talk",
|
|
5
5
|
"owner": {
|
|
6
6
|
"name": "agent-messenger",
|
|
7
7
|
"url": "https://github.com/agent-messenger"
|
|
@@ -136,6 +136,19 @@
|
|
|
136
136
|
"category": "productivity",
|
|
137
137
|
"homepage": "https://github.com/agent-messenger/agent-messenger",
|
|
138
138
|
"keywords": ["channel-talk", "channeltalkbot", "bot", "messaging", "ai-agent", "cli", "ci-cd"]
|
|
139
|
+
},
|
|
140
|
+
{
|
|
141
|
+
"name": "agent-imessage",
|
|
142
|
+
"description": "Interact with iMessage on a Mac via the imsg tool. Apple has no public API, so it runs locally on macOS (no network, no server) and drives Messages.app through imsg over JSON-RPC. Supports send/list messages, direct & group chats, chat listing, real-time watch, and standard tapbacks. Requires Full Disk Access and Automation permissions.",
|
|
143
|
+
"version": "2.27.2",
|
|
144
|
+
"author": {
|
|
145
|
+
"name": "agent-messenger",
|
|
146
|
+
"url": "https://github.com/agent-messenger"
|
|
147
|
+
},
|
|
148
|
+
"source": "./",
|
|
149
|
+
"category": "productivity",
|
|
150
|
+
"homepage": "https://github.com/agent-messenger/agent-messenger",
|
|
151
|
+
"keywords": ["imessage", "imsg", "macos", "apple", "messaging", "ai-agent", "cli", "communication"]
|
|
139
152
|
}
|
|
140
153
|
]
|
|
141
154
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "agent-messenger",
|
|
3
|
-
"version": "2.
|
|
4
|
-
"description": "Messaging platform interaction skills for AI agents. Interact with Slack, Discord, Microsoft Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk - send messages, read channels, manage reactions, upload files, and more through simple CLI interfaces.",
|
|
3
|
+
"version": "2.28.0",
|
|
4
|
+
"description": "Messaging platform interaction skills for AI agents. Interact with Slack, Discord, Microsoft Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, iMessage, Instagram, KakaoTalk, and Channel Talk - send messages, read channels, manage reactions, upload files, and more through simple CLI interfaces.",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "agent-messenger",
|
|
7
7
|
"url": "https://github.com/agent-messenger"
|
|
@@ -18,6 +18,7 @@
|
|
|
18
18
|
"kakaotalk",
|
|
19
19
|
"channel-talk",
|
|
20
20
|
"line",
|
|
21
|
+
"imessage",
|
|
21
22
|
"instagram",
|
|
22
23
|
"messaging",
|
|
23
24
|
"workspace",
|
|
@@ -41,6 +42,7 @@
|
|
|
41
42
|
"./skills/agent-whatsapp",
|
|
42
43
|
"./skills/agent-whatsappbot",
|
|
43
44
|
"./skills/agent-line",
|
|
45
|
+
"./skills/agent-imessage",
|
|
44
46
|
"./skills/agent-instagram",
|
|
45
47
|
"./skills/agent-kakaotalk",
|
|
46
48
|
"./skills/agent-channeltalk",
|
package/AGENTS.md
CHANGED
|
@@ -2,6 +2,10 @@
|
|
|
2
2
|
|
|
3
3
|
Multi-platform messaging CLI for AI agents (Slack, Discord, Teams).
|
|
4
4
|
|
|
5
|
+
## Platform Notes
|
|
6
|
+
|
|
7
|
+
Each platform lives in `src/platforms/<name>/` and follows the same convention (cli, index, client, types, credential-manager, ensure-auth, commands). **iMessage (`agent-imessage`) is the one platform that must run on a Mac:** Apple has no public API, so it shells out to the local [imsg](https://github.com/openclaw/imsg) CLI and talks to it over JSON-RPC (stdin/stdout) — there is no network/server. Its client (`ImsgClient`, over an `ImsgRpc` transport) spawns a long-lived `imsg rpc` child for chats/history/watch/send, and shells out to `imsg react` for standard tapbacks. Credentials are provider-aware (`{ provider: "imsg", binaryPath?, region? }`) with no secrets — it relies on macOS Full Disk Access + Automation permissions.
|
|
8
|
+
|
|
5
9
|
## TypeScript Execution Model
|
|
6
10
|
|
|
7
11
|
### Local Development
|
package/README.md
CHANGED
|
@@ -2,13 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
# Agent Messenger
|
|
4
4
|
|
|
5
|
-
[](https://www.npmjs.com/package/agent-messenger) [](https://agent-messenger.dev/docs/cli/slack) [](https://agent-messenger.dev/docs/cli/discord) [](https://agent-messenger.dev/docs/cli/teams) [](https://agent-messenger.dev/docs/cli/webex) [](https://agent-messenger.dev/docs/cli/telegram) [](https://agent-messenger.dev/docs/cli/whatsapp) [](https://agent-messenger.dev/docs/cli/line) [](https://agent-messenger.dev/docs/cli/wechatbot) [](https://agent-messenger.dev/docs/cli/instagram) [](https://agent-messenger.dev/docs/cli/kakaotalk) [](https://agent-messenger.dev/docs/cli/channeltalk)
|
|
5
|
+
[](https://www.npmjs.com/package/agent-messenger) [](https://agent-messenger.dev/docs/cli/slack) [](https://agent-messenger.dev/docs/cli/discord) [](https://agent-messenger.dev/docs/cli/teams) [](https://agent-messenger.dev/docs/cli/webex) [](https://agent-messenger.dev/docs/cli/telegram) [](https://agent-messenger.dev/docs/cli/whatsapp) [](https://agent-messenger.dev/docs/cli/line) [](https://agent-messenger.dev/docs/cli/wechatbot) [](https://agent-messenger.dev/docs/cli/imessage) [](https://agent-messenger.dev/docs/cli/instagram) [](https://agent-messenger.dev/docs/cli/kakaotalk) [](https://agent-messenger.dev/docs/cli/channeltalk)
|
|
6
6
|
|
|
7
7
|
**Your agent messages as you — not as a bot**
|
|
8
8
|
|
|
9
9
|
</div>
|
|
10
10
|
|
|
11
|
-
One CLI for Slack, Discord, Teams, Webex, Telegram, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk. Credentials extracted from desktop apps and browsers, or authenticated in seconds — no API keys, no OAuth, no admin approval. TypeScript SDK included.
|
|
11
|
+
One CLI for Slack, Discord, Teams, Webex, Telegram, WhatsApp, LINE, WeChat, iMessage, Instagram, KakaoTalk, and Channel Talk. Credentials extracted from desktop apps and browsers, or authenticated in seconds — no API keys, no OAuth, no admin approval. TypeScript SDK included.
|
|
12
12
|
|
|
13
13
|
> [!TIP]
|
|
14
14
|
> 🎉 Agent Messenger powers multi-channel messaging in [TypeClaw](https://github.com/typeclaw/typeclaw), a TypeScript-native agent runtime.
|
|
@@ -51,7 +51,7 @@ Agent Messenger reads session tokens from your Slack, Discord, Teams, KakaoTalk,
|
|
|
51
51
|
- **QR Code Sign-In (Slack & Discord)** — The recommended, safest auth: sign in through the platform's official flow, no credential extraction and no desktop app required (Discord scans with the mobile app)
|
|
52
52
|
- **Auto-Extract Auth** — Reads tokens from Slack, Discord, Teams, KakaoTalk, and Channel Talk desktop apps, with browser fallback and custom Chromium profile paths via `--browser-profile`. Webex and Instagram tokens extracted from Chromium browsers. Telegram and WhatsApp authenticate with a one-time code — still under a minute
|
|
53
53
|
- **Act As Yourself** — Extracts your user session — not a bot token. Your agent sends messages, reacts, and searches as you. Need bot mode? Bot CLIs are included too
|
|
54
|
-
- **One Interface** — Consistent command style across
|
|
54
|
+
- **One Interface** — Consistent command style across 12 platforms for supported actions (e.g. message send, message search, channel list, snapshot). Learn once
|
|
55
55
|
- **Agent-Native Output** — JSON by default for LLM tool use. `--pretty` for human-readable. Structured output your agent can parse and act on
|
|
56
56
|
- **Token Efficient** — CLI, not MCP. One skill file, one shell command per action. No server to run, no tool registration. ([Why not MCP?](#philosophy))
|
|
57
57
|
- **Persistent Memory** — Stores workspace IDs, channel mappings, and preferences in ~/.config so your agent never asks twice
|
|
@@ -88,6 +88,7 @@ This installs:
|
|
|
88
88
|
- `agent-whatsappbot` — WhatsApp Bot CLI (Cloud API, for server-side/CI/CD)
|
|
89
89
|
- `agent-line` — LINE CLI (QR code login, Thrift protocol)
|
|
90
90
|
- `agent-wechatbot` — WeChat Bot CLI (Official Account API, for server-side/CI/CD)
|
|
91
|
+
- `agent-imessage` — iMessage CLI (runs on a Mac via the [imsg](https://github.com/openclaw/imsg) tool)
|
|
91
92
|
- `agent-instagram` — Instagram DM CLI (browser cookie extraction + username/password auth)
|
|
92
93
|
- `agent-kakaotalk` — KakaoTalk CLI (sub-device login, LOCO protocol)
|
|
93
94
|
- `agent-channeltalk` — Channel Talk CLI (beta, zero-config, extracted cookies)
|
|
@@ -101,7 +102,7 @@ Agent Messenger includes [Agent Skills](https://agentskills.io/) that teach your
|
|
|
101
102
|
|
|
102
103
|
SkillPad is a GUI app for Agent Skills. See [skillpad.dev](https://skillpad.dev/) for more details.
|
|
103
104
|
|
|
104
|
-
[](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-slack) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-slackbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-discord) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-discordbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-teams) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-webex) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-webexbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-telegram) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-telegrambot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-whatsapp) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-whatsappbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-line) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-wechatbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-instagram) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-kakaotalk) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-channeltalk) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-channeltalkbot)
|
|
105
|
+
[](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-slack) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-slackbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-discord) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-discordbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-teams) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-webex) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-webexbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-telegram) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-telegrambot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-whatsapp) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-whatsappbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-line) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-wechatbot) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-imessage) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-instagram) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-kakaotalk) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-channeltalk) [](https://skillpad.dev/install/agent-messenger/agent-messenger/agent-channeltalkbot)
|
|
105
106
|
|
|
106
107
|
### Skills CLI
|
|
107
108
|
|
|
@@ -155,7 +156,7 @@ export AGENT_MESSENGER_CONFIG_DIR="$HOME/.local/share/agent-messenger"
|
|
|
155
156
|
agent-slack auth extract
|
|
156
157
|
```
|
|
157
158
|
|
|
158
|
-
The variable is read on every CLI/SDK invocation and applies to all platforms (Slack, Discord, Teams, Webex, Telegram, WhatsApp, LINE, WeChat, Instagram, KakaoTalk, Channel Talk, and their bot variants). Explicit `configDir` arguments to credential managers still take precedence.
|
|
159
|
+
The variable is read on every CLI/SDK invocation and applies to all platforms (Slack, Discord, Teams, Webex, Telegram, WhatsApp, LINE, WeChat, iMessage, Instagram, KakaoTalk, Channel Talk, and their bot variants). Explicit `configDir` arguments to credential managers still take precedence.
|
|
159
160
|
|
|
160
161
|
## Telegram Quick Start
|
|
161
162
|
|
|
@@ -206,12 +207,13 @@ const slack = await new SlackClient().login({ token: 'xoxc-...', cookie: 'xoxd-.
|
|
|
206
207
|
| `agent-messenger/whatsappbot` | `WhatsAppBotClient` |
|
|
207
208
|
| `agent-messenger/line` | `LineClient` |
|
|
208
209
|
| `agent-messenger/wechatbot` | `WeChatBotClient` |
|
|
210
|
+
| `agent-messenger/imessage` | `ImsgClient` |
|
|
209
211
|
| `agent-messenger/instagram` | `InstagramClient` |
|
|
210
212
|
| `agent-messenger/kakaotalk` | `KakaoTalkClient` |
|
|
211
213
|
| `agent-messenger/channeltalk` | `ChannelClient` |
|
|
212
214
|
| `agent-messenger/channeltalkbot` | `ChannelBotClient` |
|
|
213
215
|
|
|
214
|
-
Each module also exports its credential manager, Zod schemas, and TypeScript types:
|
|
216
|
+
Each module also exports its credential manager, Zod schemas, and TypeScript types (except `imessage`, which exports its client, credential manager, and TypeScript types — no Zod schemas):
|
|
215
217
|
|
|
216
218
|
```typescript
|
|
217
219
|
import { SlackClient, SlackCredentialManager, SlackMessageSchema } from 'agent-messenger/slack'
|
|
@@ -379,9 +381,31 @@ listener.on('slash_commands', ({ ack, body }) => {
|
|
|
379
381
|
await listener.start()
|
|
380
382
|
```
|
|
381
383
|
|
|
384
|
+
### Real-time Events (Instagram)
|
|
385
|
+
|
|
386
|
+
Stream Instagram DMs in real time over Instagram's MQTToT transport (a persistent TLS connection to `edge-mqtt.facebook.com`), with automatic fallback to polling if the connection can't be established.
|
|
387
|
+
|
|
388
|
+
```typescript
|
|
389
|
+
import { InstagramClient, InstagramHybridListener } from 'agent-messenger/instagram'
|
|
390
|
+
|
|
391
|
+
const client = await new InstagramClient().login()
|
|
392
|
+
const listener = new InstagramHybridListener(client)
|
|
393
|
+
|
|
394
|
+
listener.on('message', (msg) => {
|
|
395
|
+
if (msg.is_outgoing) return
|
|
396
|
+
console.log(`New DM in ${msg.thread_id}: ${msg.text}`)
|
|
397
|
+
})
|
|
398
|
+
|
|
399
|
+
listener.on('connected', ({ userId, transport }) => {
|
|
400
|
+
console.log(`Listening as ${userId} via ${transport}`)
|
|
401
|
+
})
|
|
402
|
+
|
|
403
|
+
await listener.start()
|
|
404
|
+
```
|
|
405
|
+
|
|
382
406
|
## TUI (Experimental)
|
|
383
407
|
|
|
384
|
-
A unified terminal interface for all your messaging platforms in one screen. Navigate between Slack, Discord, Teams, Webex, Telegram, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk — all from your terminal.
|
|
408
|
+
A unified terminal interface for all your messaging platforms in one screen. Navigate between Slack, Discord, Teams, Webex, Telegram, WhatsApp, iMessage, LINE, Instagram, KakaoTalk, and Channel Talk — all from your terminal.
|
|
385
409
|
|
|
386
410
|
> **Note**: The TUI is a showcase of what's possible with Agent Messenger's SDK. It demonstrates the power of having a unified adapter layer across all platforms.
|
|
387
411
|
|
|
@@ -392,7 +416,7 @@ agent-messenger tui
|
|
|
392
416
|

|
|
393
417
|
|
|
394
418
|
Key features:
|
|
395
|
-
- **Multi-platform** — All
|
|
419
|
+
- **Multi-platform** — All 11 platforms in one sidebar, auto-login on startup
|
|
396
420
|
- **Real-time messages** — Live message streaming for supported platforms
|
|
397
421
|
- **Fuzzy pickers** — `Ctrl+K` for channels, `Ctrl+W` for workspaces
|
|
398
422
|
- **Interactive auth** — Authenticate platforms that aren't set up yet, right in the TUI
|
|
@@ -429,6 +453,8 @@ See the [TUI docs](https://agent-messenger.dev/docs/tui) for keybindings, archit
|
|
|
429
453
|
|
|
430
454
|
> ⚠️ **Teams tokens expire in 60-90 minutes.** Re-run `agent-teams auth extract` to refresh. See [Teams Guide](skills/agent-teams/SKILL.md) for details.
|
|
431
455
|
|
|
456
|
+
> 💬 **iMessage** is supported via the local [imsg](https://github.com/openclaw/imsg) tool (`agent-imessage`), not the table above. It runs **on a Mac** (Apple has no API). v1 covers send & list messages, direct & group chats, chat listing, real-time watch, and standard tapbacks. Typing, edit/unsend, group management, and targeted/custom reactions require imsg's bridge (SIP disabled) and are a later tier. See the [iMessage Guide](skills/agent-imessage/SKILL.md).
|
|
457
|
+
|
|
432
458
|
## Platform Guides
|
|
433
459
|
|
|
434
460
|
- **[Slack Guide](https://agent-messenger.dev/docs/cli/slack)** — Full command reference for Slack
|
|
@@ -444,11 +470,16 @@ See the [TUI docs](https://agent-messenger.dev/docs/tui) for keybindings, archit
|
|
|
444
470
|
- **[WhatsApp Bot Guide](https://agent-messenger.dev/docs/cli/whatsappbot)** — Cloud API integration for WhatsApp Business
|
|
445
471
|
- **[LINE Guide](https://agent-messenger.dev/docs/cli/line)** — QR code login and Thrift protocol integration
|
|
446
472
|
- **[WeChat Bot Guide](https://agent-messenger.dev/docs/cli/wechatbot)** — Official Account API integration for WeChat
|
|
473
|
+
- **[iMessage Guide](skills/agent-imessage/SKILL.md)** — iMessage on a Mac via the imsg tool
|
|
447
474
|
- **[Instagram Guide](https://agent-messenger.dev/docs/cli/instagram)** — Browser cookie extraction and Instagram DM integration
|
|
448
475
|
- **[KakaoTalk Guide](https://agent-messenger.dev/docs/cli/kakaotalk)** — Sub-device login and LOCO protocol integration
|
|
449
476
|
- **[Channel Talk Guide](https://agent-messenger.dev/docs/cli/channeltalk)** — Full command reference for Channel Talk (beta, zero-config)
|
|
450
477
|
- **[Channel Talk Bot Guide](https://agent-messenger.dev/docs/cli/channeltalkbot)** — Bot API integration for Channel Talk (beta)
|
|
451
478
|
|
|
479
|
+
### iMessage is different
|
|
480
|
+
|
|
481
|
+
Most agent-messenger platforms run anywhere. **iMessage is the exception:** Apple provides no API, so `agent-imessage` runs **on a Mac** and drives Messages locally through the [imsg](https://github.com/openclaw/imsg) tool. You still act as yourself with your own Apple ID and run one shell command per action, but the agent must run on the Mac (imsg is local-only — no network or server) with Full Disk Access and Automation granted. See the [setup guide](skills/agent-imessage/references/setup.md).
|
|
482
|
+
|
|
452
483
|
## Use Cases
|
|
453
484
|
|
|
454
485
|
### Gathering Context
|
|
@@ -495,7 +526,7 @@ Wire messaging into your CI, scripts, or agent workflows.
|
|
|
495
526
|
|
|
496
527
|
### ...and More
|
|
497
528
|
|
|
498
|
-
These are just starting points. Your agent has full read/write access to Slack, Discord, Teams, Telegram, WhatsApp, LINE, Instagram, KakaoTalk, and Channel Talk — anything you'd do manually in a chat app, it can handle for you. If you build something cool with Agent Messenger, [let me know](https://x.com/devxoul)!
|
|
529
|
+
These are just starting points. Your agent has full read/write access to Slack, Discord, Teams, Telegram, WhatsApp, LINE, iMessage, Instagram, KakaoTalk, and Channel Talk — anything you'd do manually in a chat app, it can handle for you. If you build something cool with Agent Messenger, [let me know](https://x.com/devxoul)!
|
|
499
530
|
|
|
500
531
|
## Philosophy
|
|
501
532
|
|
package/dist/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "agent-messenger",
|
|
3
|
-
"version": "2.
|
|
4
|
-
"description": "Multi-platform messaging CLI for AI agents (Slack, Discord, Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, Instagram, KakaoTalk, Channel Talk)",
|
|
3
|
+
"version": "2.28.0",
|
|
4
|
+
"description": "Multi-platform messaging CLI for AI agents (Slack, Discord, Teams, Webex, Telegram, Telegram Bot, WhatsApp, LINE, iMessage, Instagram, KakaoTalk, Channel Talk)",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
7
7
|
"url": "https://github.com/agent-messenger/agent-messenger"
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
"agent-channeltalkbot": "./src/platforms/channeltalkbot/cli.ts",
|
|
12
12
|
"agent-discord": "./src/platforms/discord/cli.ts",
|
|
13
13
|
"agent-discordbot": "./src/platforms/discordbot/cli.ts",
|
|
14
|
+
"agent-imessage": "./src/platforms/imessage/cli.ts",
|
|
14
15
|
"agent-instagram": "./src/platforms/instagram/cli.ts",
|
|
15
16
|
"agent-kakaotalk": "./src/platforms/kakaotalk/cli.ts",
|
|
16
17
|
"agent-line": "./src/platforms/line/cli.ts",
|
|
@@ -65,6 +66,9 @@
|
|
|
65
66
|
"wechatbot": [
|
|
66
67
|
"./src/platforms/wechatbot/index.ts"
|
|
67
68
|
],
|
|
69
|
+
"imessage": [
|
|
70
|
+
"./src/platforms/imessage/index.ts"
|
|
71
|
+
],
|
|
68
72
|
"instagram": [
|
|
69
73
|
"./src/platforms/instagram/index.ts"
|
|
70
74
|
],
|
|
@@ -132,6 +136,10 @@
|
|
|
132
136
|
"types": "./src/platforms/wechatbot/index.ts",
|
|
133
137
|
"default": "./src/platforms/wechatbot/index.ts"
|
|
134
138
|
},
|
|
139
|
+
"./imessage": {
|
|
140
|
+
"types": "./src/platforms/imessage/index.ts",
|
|
141
|
+
"default": "./src/platforms/imessage/index.ts"
|
|
142
|
+
},
|
|
135
143
|
"./instagram": {
|
|
136
144
|
"types": "./src/platforms/instagram/index.ts",
|
|
137
145
|
"default": "./src/platforms/instagram/index.ts"
|
package/dist/src/cli.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../../src/cli.ts"],"names":[],"mappings":";AAKA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAQnC,QAAA,MAAM,OAAO,SAAgB,CAAA;
|
|
1
|
+
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../../src/cli.ts"],"names":[],"mappings":";AAKA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAQnC,QAAA,MAAM,OAAO,SAAgB,CAAA;AA+E7B,eAAe,OAAO,CAAA"}
|
package/dist/src/cli.js
CHANGED
|
@@ -48,6 +48,9 @@ program.command('kakaotalk', 'Interact with KakaoTalk', {
|
|
|
48
48
|
program.command('channeltalk', 'Interact with Channel Talk', {
|
|
49
49
|
executableFile: join(__dirname, 'platforms', 'channeltalk', `cli${ext}`),
|
|
50
50
|
});
|
|
51
|
+
program.command('imessage', 'Interact with iMessage via imsg (local, on-Mac)', {
|
|
52
|
+
executableFile: join(__dirname, 'platforms', 'imessage', `cli${ext}`),
|
|
53
|
+
});
|
|
51
54
|
program.command('channeltalkbot', 'Interact with Channel Talk using API credentials', {
|
|
52
55
|
executableFile: join(__dirname, 'platforms', 'channeltalkbot', `cli${ext}`),
|
|
53
56
|
});
|
package/dist/src/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../../src/cli.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../../src/cli.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
import { Command } from 'commander';
|
|
3
3
|
import pkg from '../../../package.json' with { type: 'json' };
|
|
4
4
|
import { authCommand, channelCommand, fileCommand, messageCommand, reactionCommand, serverCommand, snapshotCommand, threadCommand, userCommand, whoamiCommand, } from './commands/index.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../../../../src/platforms/imessage/cli.ts"],"names":[],"mappings":";AAEA,OAAO,KAAK,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,WAAW,CAAA;AAkBvD,QAAA,MAAM,OAAO,aAAgB,CAAA;AAkB7B,eAAe,OAAO,CAAA"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { Command } from 'commander';
|
|
3
|
+
import pkg from '../../../package.json' with { type: 'json' };
|
|
4
|
+
import { authCommand, chatCommand, doctorCommand, messageCommand, setupCommand, whoamiCommand } from './commands/index.js';
|
|
5
|
+
import { ensureIMessageAuth } from './ensure-auth.js';
|
|
6
|
+
const UNGUARDED = new Set(['auth', 'setup', 'doctor']);
|
|
7
|
+
function isUnguarded(command) {
|
|
8
|
+
let cmd = command;
|
|
9
|
+
while (cmd) {
|
|
10
|
+
if (UNGUARDED.has(cmd.name()))
|
|
11
|
+
return true;
|
|
12
|
+
cmd = cmd.parent;
|
|
13
|
+
}
|
|
14
|
+
return false;
|
|
15
|
+
}
|
|
16
|
+
const program = new Command();
|
|
17
|
+
program.name('agent-imessage').description('CLI tool for iMessage via imsg (local, on-Mac)').version(pkg.version);
|
|
18
|
+
program.hook('preAction', async (_thisCommand, actionCommand) => {
|
|
19
|
+
if (isUnguarded(actionCommand))
|
|
20
|
+
return;
|
|
21
|
+
await ensureIMessageAuth();
|
|
22
|
+
});
|
|
23
|
+
program.addCommand(authCommand);
|
|
24
|
+
program.addCommand(setupCommand);
|
|
25
|
+
program.addCommand(doctorCommand);
|
|
26
|
+
program.addCommand(chatCommand);
|
|
27
|
+
program.addCommand(messageCommand);
|
|
28
|
+
program.addCommand(whoamiCommand);
|
|
29
|
+
program.parse(process.argv);
|
|
30
|
+
export default program;
|
|
31
|
+
//# sourceMappingURL=cli.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../../../../src/platforms/imessage/cli.ts"],"names":[],"mappings":";AAGA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAEnC,OAAO,GAAG,MAAM,uBAAuB,CAAC,OAAO,IAAI,EAAE,MAAM,EAAE,CAAA;AAC7D,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,aAAa,EAAE,cAAc,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAA;AACvH,OAAO,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAA;AAElD,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,CAAC,MAAM,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC,CAAA;AAEtD,SAAS,WAAW,CAAC,OAAoB;IACvC,IAAI,GAAG,GAAuB,OAAO,CAAA;IACrC,OAAO,GAAG,EAAE,CAAC;QACX,IAAI,SAAS,CAAC,GAAG,CAAC,GAAG,CAAC,IAAI,EAAE,CAAC;YAAE,OAAO,IAAI,CAAA;QAC1C,GAAG,GAAG,GAAG,CAAC,MAAM,CAAA;IAClB,CAAC;IACD,OAAO,KAAK,CAAA;AACd,CAAC;AAED,MAAM,OAAO,GAAG,IAAI,OAAO,EAAE,CAAA;AAE7B,OAAO,CAAC,IAAI,CAAC,gBAAgB,CAAC,CAAC,WAAW,CAAC,gDAAgD,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,OAAO,CAAC,CAAA;AAEjH,OAAO,CAAC,IAAI,CAAC,WAAW,EAAE,KAAK,EAAE,YAAY,EAAE,aAAa,EAAE,EAAE;IAC9D,IAAI,WAAW,CAAC,aAAa,CAAC;QAAE,OAAM;IACtC,MAAM,kBAAkB,EAAE,CAAA;AAC5B,CAAC,CAAC,CAAA;AAEF,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC,CAAA;AAC/B,OAAO,CAAC,UAAU,CAAC,YAAY,CAAC,CAAA;AAChC,OAAO,CAAC,UAAU,CAAC,aAAa,CAAC,CAAA;AACjC,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC,CAAA;AAC/B,OAAO,CAAC,UAAU,CAAC,cAAc,CAAC,CAAA;AAClC,OAAO,CAAC,UAAU,CAAC,aAAa,CAAC,CAAA;AAEjC,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,CAAA;AAE3B,eAAe,OAAO,CAAA"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { ImsgRpc } from './rpc.js';
|
|
2
|
+
import { type IMessageChatSummary, type IMessageMessageSummary, type IMessageStatus } from './types.js';
|
|
3
|
+
export interface SendTarget {
|
|
4
|
+
chatId?: number;
|
|
5
|
+
chatGuid?: string;
|
|
6
|
+
chatIdentifier?: string;
|
|
7
|
+
to?: string;
|
|
8
|
+
}
|
|
9
|
+
export type OneShotRunner = (binaryPath: string, args: string[]) => Promise<{
|
|
10
|
+
code: number;
|
|
11
|
+
stdout: string;
|
|
12
|
+
stderr: string;
|
|
13
|
+
}>;
|
|
14
|
+
export declare class ImsgClient {
|
|
15
|
+
private binaryPath;
|
|
16
|
+
private region;
|
|
17
|
+
private rpc;
|
|
18
|
+
private runner;
|
|
19
|
+
constructor(deps?: {
|
|
20
|
+
rpc?: ImsgRpc;
|
|
21
|
+
runner?: OneShotRunner;
|
|
22
|
+
});
|
|
23
|
+
login(credentials?: {
|
|
24
|
+
binaryPath?: string;
|
|
25
|
+
region?: string;
|
|
26
|
+
}): Promise<this>;
|
|
27
|
+
connect(): Promise<void>;
|
|
28
|
+
getVersion(): Promise<string | null>;
|
|
29
|
+
getStatus(): Promise<IMessageStatus>;
|
|
30
|
+
listChats(limit?: number): Promise<IMessageChatSummary[]>;
|
|
31
|
+
searchChats(query: string, limit?: number): Promise<IMessageChatSummary[]>;
|
|
32
|
+
getMessages(chatId: number, limit?: number, start?: string): Promise<IMessageMessageSummary[]>;
|
|
33
|
+
sendMessage(target: SendTarget, text: string): Promise<IMessageMessageSummary>;
|
|
34
|
+
sendReaction(chatId: number, reaction: string, messageGuid?: string): Promise<void>;
|
|
35
|
+
watch(onMessage: (msg: IMessageMessageSummary) => void, options?: {
|
|
36
|
+
chatId?: number;
|
|
37
|
+
sinceRowId?: number;
|
|
38
|
+
onError?: (msg: string) => void;
|
|
39
|
+
}): Promise<() => Promise<void>>;
|
|
40
|
+
getProfile(): Promise<IMessageStatus>;
|
|
41
|
+
close(): Promise<void>;
|
|
42
|
+
}
|
|
43
|
+
//# sourceMappingURL=client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../../../src/platforms/imessage/client.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,OAAO,EAAE,MAAM,OAAO,CAAA;AAC/B,OAAO,EAAE,KAAK,mBAAmB,EAAE,KAAK,sBAAsB,EAAE,KAAK,cAAc,EAAiB,MAAM,SAAS,CAAA;AA0BnH,MAAM,WAAW,UAAU;IACzB,MAAM,CAAC,EAAE,MAAM,CAAA;IACf,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,cAAc,CAAC,EAAE,MAAM,CAAA;IACvB,EAAE,CAAC,EAAE,MAAM,CAAA;CACZ;AAED,MAAM,MAAM,aAAa,GAAG,CAC1B,UAAU,EAAE,MAAM,EAClB,IAAI,EAAE,MAAM,EAAE,KACX,OAAO,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC,CAAA;AAsD9D,qBAAa,UAAU;IACrB,OAAO,CAAC,UAAU,CAAS;IAC3B,OAAO,CAAC,MAAM,CAAoB;IAClC,OAAO,CAAC,GAAG,CAAS;IACpB,OAAO,CAAC,MAAM,CAAe;gBAEjB,IAAI,CAAC,EAAE;QAAE,GAAG,CAAC,EAAE,OAAO,CAAC;QAAC,MAAM,CAAC,EAAE,aAAa,CAAA;KAAE;IAKtD,KAAK,CAAC,WAAW,CAAC,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAa5E,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAKxB,UAAU,IAAI,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;IAMpC,SAAS,IAAI,OAAO,CAAC,cAAc,CAAC;IAuBpC,SAAS,CAAC,KAAK,SAAK,GAAG,OAAO,CAAC,mBAAmB,EAAE,CAAC;IAKrD,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,SAAK,GAAG,OAAO,CAAC,mBAAmB,EAAE,CAAC;IAQtE,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,KAAK,SAAK,EAAE,KAAK,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,sBAAsB,EAAE,CAAC;IAS1F,WAAW,CAAC,MAAM,EAAE,UAAU,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,sBAAsB,CAAC;IAwB9E,YAAY,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IA6BnF,KAAK,CACT,SAAS,EAAE,CAAC,GAAG,EAAE,sBAAsB,KAAK,IAAI,EAChD,OAAO,GAAE;QAAE,MAAM,CAAC,EAAE,MAAM,CAAC;QAAC,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAA;KAAO,GACtF,OAAO,CAAC,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAezB,UAAU,IAAI,OAAO,CAAC,cAAc,CAAC;IAIrC,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;CAG7B"}
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
import { spawn } from 'node:child_process';
|
|
2
|
+
import { classifyImsgFailure } from './errors.js';
|
|
3
|
+
import { ImsgRpc } from './rpc.js';
|
|
4
|
+
import { IMessageError } from './types.js';
|
|
5
|
+
const STANDARD_REACTIONS = new Set(['love', 'like', 'dislike', 'laugh', 'emphasis', 'question']);
|
|
6
|
+
const defaultRunner = (binaryPath, args) => new Promise((resolve, reject) => {
|
|
7
|
+
let proc;
|
|
8
|
+
try {
|
|
9
|
+
proc = spawn(binaryPath, args, { stdio: ['ignore', 'pipe', 'pipe'] });
|
|
10
|
+
}
|
|
11
|
+
catch {
|
|
12
|
+
reject(new IMessageError(`Could not run "${binaryPath}".`, 'imsg_not_found'));
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
let stdout = '';
|
|
16
|
+
let stderr = '';
|
|
17
|
+
proc.stdout?.on('data', (c) => (stdout += c.toString()));
|
|
18
|
+
proc.stderr?.on('data', (c) => (stderr += c.toString()));
|
|
19
|
+
proc.once('error', (err) => {
|
|
20
|
+
reject(err.code === 'ENOENT'
|
|
21
|
+
? new IMessageError(`Could not run "${binaryPath}".`, 'imsg_not_found', {
|
|
22
|
+
suggestion: 'Install imsg: "brew install steipete/tap/imsg".',
|
|
23
|
+
doctorCommand: 'agent-imessage doctor',
|
|
24
|
+
})
|
|
25
|
+
: err);
|
|
26
|
+
});
|
|
27
|
+
proc.once('close', (code) => resolve({ code: code ?? 0, stdout, stderr }));
|
|
28
|
+
});
|
|
29
|
+
function summarizeMessage(msg) {
|
|
30
|
+
return {
|
|
31
|
+
id: msg.id,
|
|
32
|
+
guid: msg.guid,
|
|
33
|
+
chat_id: msg.chat_id,
|
|
34
|
+
from: msg.is_from_me ? '' : (msg.sender ?? ''),
|
|
35
|
+
from_name: msg.sender_name ?? undefined,
|
|
36
|
+
is_outgoing: Boolean(msg.is_from_me),
|
|
37
|
+
timestamp: msg.created_at ?? new Date(0).toISOString(),
|
|
38
|
+
text: msg.text ?? undefined,
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
function summarizeChat(chat) {
|
|
42
|
+
return {
|
|
43
|
+
id: chat.id,
|
|
44
|
+
guid: chat.guid ?? null,
|
|
45
|
+
identifier: chat.identifier ?? null,
|
|
46
|
+
name: chat.name?.trim() || chat.identifier || chat.guid || String(chat.id),
|
|
47
|
+
service: chat.service ?? 'iMessage',
|
|
48
|
+
is_group: Boolean(chat.is_group),
|
|
49
|
+
participants: chat.participants ?? [],
|
|
50
|
+
last_message: chat.last_message ? summarizeMessage(chat.last_message) : undefined,
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
export class ImsgClient {
|
|
54
|
+
binaryPath = 'imsg';
|
|
55
|
+
region;
|
|
56
|
+
rpc;
|
|
57
|
+
runner;
|
|
58
|
+
constructor(deps) {
|
|
59
|
+
this.rpc = deps?.rpc ?? new ImsgRpc();
|
|
60
|
+
this.runner = deps?.runner ?? defaultRunner;
|
|
61
|
+
}
|
|
62
|
+
async login(credentials) {
|
|
63
|
+
if (credentials) {
|
|
64
|
+
this.binaryPath = credentials.binaryPath ?? 'imsg';
|
|
65
|
+
this.region = credentials.region;
|
|
66
|
+
return this;
|
|
67
|
+
}
|
|
68
|
+
const { IMessageCredentialManager } = await import('./credential-manager.js');
|
|
69
|
+
const resolved = await new IMessageCredentialManager().resolveAccount();
|
|
70
|
+
this.binaryPath = resolved?.binary_path ?? 'imsg';
|
|
71
|
+
this.region = resolved?.region;
|
|
72
|
+
return this;
|
|
73
|
+
}
|
|
74
|
+
async connect() {
|
|
75
|
+
await this.rpc.start(this.binaryPath);
|
|
76
|
+
await this.rpc.request('chats.list', { limit: 1 });
|
|
77
|
+
}
|
|
78
|
+
async getVersion() {
|
|
79
|
+
const result = await this.runner(this.binaryPath, ['--version']);
|
|
80
|
+
if (result.code !== 0)
|
|
81
|
+
return null;
|
|
82
|
+
return result.stdout.trim() || null;
|
|
83
|
+
}
|
|
84
|
+
async getStatus() {
|
|
85
|
+
let version = null;
|
|
86
|
+
let fullDiskAccess = false;
|
|
87
|
+
try {
|
|
88
|
+
version = await this.getVersion();
|
|
89
|
+
}
|
|
90
|
+
catch {
|
|
91
|
+
version = null;
|
|
92
|
+
}
|
|
93
|
+
try {
|
|
94
|
+
await this.rpc.request('chats.list', { limit: 1 });
|
|
95
|
+
fullDiskAccess = true;
|
|
96
|
+
}
|
|
97
|
+
catch {
|
|
98
|
+
fullDiskAccess = false;
|
|
99
|
+
}
|
|
100
|
+
return {
|
|
101
|
+
imsg_version: version,
|
|
102
|
+
binary_path: this.binaryPath,
|
|
103
|
+
full_disk_access: fullDiskAccess,
|
|
104
|
+
automation: 'unknown',
|
|
105
|
+
bridge_available: false,
|
|
106
|
+
};
|
|
107
|
+
}
|
|
108
|
+
async listChats(limit = 25) {
|
|
109
|
+
const result = await this.rpc.request('chats.list', { limit });
|
|
110
|
+
return result.chats.map(summarizeChat);
|
|
111
|
+
}
|
|
112
|
+
async searchChats(query, limit = 25) {
|
|
113
|
+
const all = await this.listChats(Math.max(limit, 100));
|
|
114
|
+
const lower = query.toLowerCase();
|
|
115
|
+
return all
|
|
116
|
+
.filter((c) => c.name.toLowerCase().includes(lower) || (c.identifier ?? '').toLowerCase().includes(lower))
|
|
117
|
+
.slice(0, limit);
|
|
118
|
+
}
|
|
119
|
+
async getMessages(chatId, limit = 25, start) {
|
|
120
|
+
const result = await this.rpc.request('messages.history', {
|
|
121
|
+
chat_id: chatId,
|
|
122
|
+
limit,
|
|
123
|
+
...(start ? { start } : {}),
|
|
124
|
+
});
|
|
125
|
+
return result.messages.map(summarizeMessage).sort((a, b) => Date.parse(a.timestamp) - Date.parse(b.timestamp));
|
|
126
|
+
}
|
|
127
|
+
async sendMessage(target, text) {
|
|
128
|
+
const params = { text };
|
|
129
|
+
if (target.chatId !== undefined)
|
|
130
|
+
params.chat_id = target.chatId;
|
|
131
|
+
else if (target.chatGuid)
|
|
132
|
+
params.chat_guid = target.chatGuid;
|
|
133
|
+
else if (target.chatIdentifier)
|
|
134
|
+
params.chat_identifier = target.chatIdentifier;
|
|
135
|
+
else if (target.to)
|
|
136
|
+
params.to = target.to;
|
|
137
|
+
else
|
|
138
|
+
throw new IMessageError('A chat id, guid, or recipient is required to send.', 'chat_not_found');
|
|
139
|
+
if (this.region)
|
|
140
|
+
params.region = this.region;
|
|
141
|
+
const result = await this.rpc.request('send', params);
|
|
142
|
+
return {
|
|
143
|
+
id: result.id ?? 0,
|
|
144
|
+
guid: result.guid ?? '',
|
|
145
|
+
chat_id: target.chatId ?? 0,
|
|
146
|
+
from: '',
|
|
147
|
+
is_outgoing: true,
|
|
148
|
+
timestamp: new Date().toISOString(),
|
|
149
|
+
text,
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
async sendReaction(chatId, reaction, messageGuid) {
|
|
153
|
+
if (messageGuid) {
|
|
154
|
+
throw new IMessageError('Reacting to a specific message requires the imsg Private API bridge.', 'private_api_required', { suggestion: 'Enable the bridge with "imsg launch" (requires SIP disabled).' });
|
|
155
|
+
}
|
|
156
|
+
if (!STANDARD_REACTIONS.has(reaction)) {
|
|
157
|
+
throw new IMessageError(`Custom reactions require the imsg Private API bridge. Standard tapbacks: ${[...STANDARD_REACTIONS].join(', ')}.`, 'private_api_required', { suggestion: 'Enable the bridge with "imsg launch" (requires SIP disabled).' });
|
|
158
|
+
}
|
|
159
|
+
const result = await this.runner(this.binaryPath, [
|
|
160
|
+
'react',
|
|
161
|
+
'--chat-id',
|
|
162
|
+
String(chatId),
|
|
163
|
+
'--reaction',
|
|
164
|
+
reaction,
|
|
165
|
+
'--json',
|
|
166
|
+
]);
|
|
167
|
+
if (result.code !== 0) {
|
|
168
|
+
const detail = result.stderr.trim() || result.stdout.trim() || 'Reaction failed.';
|
|
169
|
+
throw classifyImsgFailure(detail, 'send_failed');
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
async watch(onMessage, options = {}) {
|
|
173
|
+
const params = { include_reactions: false };
|
|
174
|
+
if (options.chatId !== undefined)
|
|
175
|
+
params.chat_id = options.chatId;
|
|
176
|
+
if (options.sinceRowId !== undefined)
|
|
177
|
+
params.since_rowid = options.sinceRowId;
|
|
178
|
+
const subscription = await this.rpc.subscribe(params, (raw) => onMessage(summarizeMessage(raw)), options.onError);
|
|
179
|
+
return async () => {
|
|
180
|
+
await this.rpc.unsubscribe(subscription);
|
|
181
|
+
};
|
|
182
|
+
}
|
|
183
|
+
async getProfile() {
|
|
184
|
+
return this.getStatus();
|
|
185
|
+
}
|
|
186
|
+
async close() {
|
|
187
|
+
this.rpc.close();
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
//# sourceMappingURL=client.js.map
|