agent-messenger 2.10.2 → 2.11.1

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.
Files changed (330) hide show
  1. package/.claude-plugin/plugin.json +1 -1
  2. package/.env.template +4 -1
  3. package/README.md +77 -27
  4. package/bun.lock +26 -0
  5. package/dist/package.json +21 -1
  6. package/dist/src/platforms/channeltalk/commands/auth.d.ts +2 -1
  7. package/dist/src/platforms/channeltalk/commands/auth.d.ts.map +1 -1
  8. package/dist/src/platforms/channeltalk/commands/auth.js +5 -3
  9. package/dist/src/platforms/channeltalk/commands/auth.js.map +1 -1
  10. package/dist/src/platforms/channeltalk/token-extractor.d.ts +2 -1
  11. package/dist/src/platforms/channeltalk/token-extractor.d.ts.map +1 -1
  12. package/dist/src/platforms/channeltalk/token-extractor.js +22 -6
  13. package/dist/src/platforms/channeltalk/token-extractor.js.map +1 -1
  14. package/dist/src/platforms/channeltalkbot/cli.d.ts.map +1 -1
  15. package/dist/src/platforms/channeltalkbot/cli.js +11 -1
  16. package/dist/src/platforms/channeltalkbot/cli.js.map +1 -1
  17. package/dist/src/platforms/channeltalkbot/commands/auth.d.ts.map +1 -1
  18. package/dist/src/platforms/channeltalkbot/commands/auth.js +1 -5
  19. package/dist/src/platforms/channeltalkbot/commands/auth.js.map +1 -1
  20. package/dist/src/platforms/channeltalkbot/commands/bot.d.ts.map +1 -1
  21. package/dist/src/platforms/channeltalkbot/commands/bot.js +1 -6
  22. package/dist/src/platforms/channeltalkbot/commands/bot.js.map +1 -1
  23. package/dist/src/platforms/channeltalkbot/commands/chat.d.ts.map +1 -1
  24. package/dist/src/platforms/channeltalkbot/commands/chat.js +1 -6
  25. package/dist/src/platforms/channeltalkbot/commands/chat.js.map +1 -1
  26. package/dist/src/platforms/channeltalkbot/commands/group.d.ts.map +1 -1
  27. package/dist/src/platforms/channeltalkbot/commands/group.js +1 -6
  28. package/dist/src/platforms/channeltalkbot/commands/group.js.map +1 -1
  29. package/dist/src/platforms/channeltalkbot/commands/manager.d.ts.map +1 -1
  30. package/dist/src/platforms/channeltalkbot/commands/manager.js +1 -6
  31. package/dist/src/platforms/channeltalkbot/commands/manager.js.map +1 -1
  32. package/dist/src/platforms/channeltalkbot/commands/message.d.ts.map +1 -1
  33. package/dist/src/platforms/channeltalkbot/commands/message.js +1 -6
  34. package/dist/src/platforms/channeltalkbot/commands/message.js.map +1 -1
  35. package/dist/src/platforms/channeltalkbot/commands/whoami.d.ts.map +1 -1
  36. package/dist/src/platforms/channeltalkbot/commands/whoami.js +1 -6
  37. package/dist/src/platforms/channeltalkbot/commands/whoami.js.map +1 -1
  38. package/dist/src/platforms/channeltalkbot/credential-manager.d.ts +5 -0
  39. package/dist/src/platforms/channeltalkbot/credential-manager.d.ts.map +1 -1
  40. package/dist/src/platforms/channeltalkbot/credential-manager.js +34 -4
  41. package/dist/src/platforms/channeltalkbot/credential-manager.js.map +1 -1
  42. package/dist/src/platforms/discord/commands/auth.d.ts +1 -0
  43. package/dist/src/platforms/discord/commands/auth.d.ts.map +1 -1
  44. package/dist/src/platforms/discord/commands/auth.js +3 -1
  45. package/dist/src/platforms/discord/commands/auth.js.map +1 -1
  46. package/dist/src/platforms/discord/listener.d.ts +2 -0
  47. package/dist/src/platforms/discord/listener.d.ts.map +1 -1
  48. package/dist/src/platforms/discord/listener.js +51 -21
  49. package/dist/src/platforms/discord/listener.js.map +1 -1
  50. package/dist/src/platforms/discord/token-extractor.d.ts +2 -1
  51. package/dist/src/platforms/discord/token-extractor.d.ts.map +1 -1
  52. package/dist/src/platforms/discord/token-extractor.js +21 -6
  53. package/dist/src/platforms/discord/token-extractor.js.map +1 -1
  54. package/dist/src/platforms/discordbot/cli.d.ts.map +1 -1
  55. package/dist/src/platforms/discordbot/cli.js +12 -1
  56. package/dist/src/platforms/discordbot/cli.js.map +1 -1
  57. package/dist/src/platforms/discordbot/client.d.ts +3 -0
  58. package/dist/src/platforms/discordbot/client.d.ts.map +1 -1
  59. package/dist/src/platforms/discordbot/client.js +3 -0
  60. package/dist/src/platforms/discordbot/client.js.map +1 -1
  61. package/dist/src/platforms/discordbot/commands/auth.d.ts.map +1 -1
  62. package/dist/src/platforms/discordbot/commands/auth.js +1 -5
  63. package/dist/src/platforms/discordbot/commands/auth.js.map +1 -1
  64. package/dist/src/platforms/discordbot/commands/message.d.ts.map +1 -1
  65. package/dist/src/platforms/discordbot/commands/message.js +1 -6
  66. package/dist/src/platforms/discordbot/commands/message.js.map +1 -1
  67. package/dist/src/platforms/discordbot/commands/server.d.ts.map +1 -1
  68. package/dist/src/platforms/discordbot/commands/server.js +1 -4
  69. package/dist/src/platforms/discordbot/commands/server.js.map +1 -1
  70. package/dist/src/platforms/discordbot/commands/whoami.d.ts.map +1 -1
  71. package/dist/src/platforms/discordbot/commands/whoami.js +1 -6
  72. package/dist/src/platforms/discordbot/commands/whoami.js.map +1 -1
  73. package/dist/src/platforms/discordbot/index.d.ts +3 -1
  74. package/dist/src/platforms/discordbot/index.d.ts.map +1 -1
  75. package/dist/src/platforms/discordbot/index.js +2 -1
  76. package/dist/src/platforms/discordbot/index.js.map +1 -1
  77. package/dist/src/platforms/discordbot/listener.d.ts +43 -0
  78. package/dist/src/platforms/discordbot/listener.d.ts.map +1 -0
  79. package/dist/src/platforms/discordbot/listener.js +292 -0
  80. package/dist/src/platforms/discordbot/listener.js.map +1 -0
  81. package/dist/src/platforms/discordbot/types.d.ts +161 -0
  82. package/dist/src/platforms/discordbot/types.d.ts.map +1 -1
  83. package/dist/src/platforms/discordbot/types.js +34 -0
  84. package/dist/src/platforms/discordbot/types.js.map +1 -1
  85. package/dist/src/platforms/instagram/commands/auth.d.ts.map +1 -1
  86. package/dist/src/platforms/instagram/commands/auth.js +3 -1
  87. package/dist/src/platforms/instagram/commands/auth.js.map +1 -1
  88. package/dist/src/platforms/instagram/token-extractor.d.ts +2 -1
  89. package/dist/src/platforms/instagram/token-extractor.d.ts.map +1 -1
  90. package/dist/src/platforms/instagram/token-extractor.js +11 -2
  91. package/dist/src/platforms/instagram/token-extractor.js.map +1 -1
  92. package/dist/src/platforms/slack/commands/auth.d.ts.map +1 -1
  93. package/dist/src/platforms/slack/commands/auth.js +4 -2
  94. package/dist/src/platforms/slack/commands/auth.js.map +1 -1
  95. package/dist/src/platforms/slack/token-extractor.d.ts +4 -1
  96. package/dist/src/platforms/slack/token-extractor.d.ts.map +1 -1
  97. package/dist/src/platforms/slack/token-extractor.js +64 -15
  98. package/dist/src/platforms/slack/token-extractor.js.map +1 -1
  99. package/dist/src/platforms/slackbot/cli.d.ts.map +1 -1
  100. package/dist/src/platforms/slackbot/cli.js +15 -3
  101. package/dist/src/platforms/slackbot/cli.js.map +1 -1
  102. package/dist/src/platforms/slackbot/client.d.ts +22 -1
  103. package/dist/src/platforms/slackbot/client.d.ts.map +1 -1
  104. package/dist/src/platforms/slackbot/client.js +104 -1
  105. package/dist/src/platforms/slackbot/client.js.map +1 -1
  106. package/dist/src/platforms/slackbot/commands/auth.d.ts.map +1 -1
  107. package/dist/src/platforms/slackbot/commands/auth.js +1 -5
  108. package/dist/src/platforms/slackbot/commands/auth.js.map +1 -1
  109. package/dist/src/platforms/slackbot/commands/file.d.ts +3 -0
  110. package/dist/src/platforms/slackbot/commands/file.d.ts.map +1 -0
  111. package/dist/src/platforms/slackbot/commands/file.js +164 -0
  112. package/dist/src/platforms/slackbot/commands/file.js.map +1 -0
  113. package/dist/src/platforms/slackbot/commands/index.d.ts +1 -0
  114. package/dist/src/platforms/slackbot/commands/index.d.ts.map +1 -1
  115. package/dist/src/platforms/slackbot/commands/index.js +1 -0
  116. package/dist/src/platforms/slackbot/commands/index.js.map +1 -1
  117. package/dist/src/platforms/slackbot/commands/message.d.ts.map +1 -1
  118. package/dist/src/platforms/slackbot/commands/message.js +19 -0
  119. package/dist/src/platforms/slackbot/commands/message.js.map +1 -1
  120. package/dist/src/platforms/slackbot/commands/whoami.d.ts.map +1 -1
  121. package/dist/src/platforms/slackbot/commands/whoami.js +1 -6
  122. package/dist/src/platforms/slackbot/commands/whoami.js.map +1 -1
  123. package/dist/src/platforms/slackbot/credential-manager.d.ts +1 -0
  124. package/dist/src/platforms/slackbot/credential-manager.d.ts.map +1 -1
  125. package/dist/src/platforms/slackbot/credential-manager.js +30 -2
  126. package/dist/src/platforms/slackbot/credential-manager.js.map +1 -1
  127. package/dist/src/platforms/slackbot/index.d.ts +4 -1
  128. package/dist/src/platforms/slackbot/index.d.ts.map +1 -1
  129. package/dist/src/platforms/slackbot/index.js +1 -0
  130. package/dist/src/platforms/slackbot/index.js.map +1 -1
  131. package/dist/src/platforms/slackbot/listener.d.ts +44 -0
  132. package/dist/src/platforms/slackbot/listener.d.ts.map +1 -0
  133. package/dist/src/platforms/slackbot/listener.js +313 -0
  134. package/dist/src/platforms/slackbot/listener.js.map +1 -0
  135. package/dist/src/platforms/slackbot/types.d.ts +196 -1
  136. package/dist/src/platforms/slackbot/types.d.ts.map +1 -1
  137. package/dist/src/platforms/slackbot/types.js +4 -1
  138. package/dist/src/platforms/slackbot/types.js.map +1 -1
  139. package/dist/src/platforms/teams/commands/auth.d.ts +1 -0
  140. package/dist/src/platforms/teams/commands/auth.d.ts.map +1 -1
  141. package/dist/src/platforms/teams/commands/auth.js +37 -6
  142. package/dist/src/platforms/teams/commands/auth.js.map +1 -1
  143. package/dist/src/platforms/teams/ensure-auth.js +31 -9
  144. package/dist/src/platforms/teams/ensure-auth.js.map +1 -1
  145. package/dist/src/platforms/teams/token-extractor.d.ts +4 -1
  146. package/dist/src/platforms/teams/token-extractor.d.ts.map +1 -1
  147. package/dist/src/platforms/teams/token-extractor.js +71 -29
  148. package/dist/src/platforms/teams/token-extractor.js.map +1 -1
  149. package/dist/src/platforms/webex/commands/auth.d.ts +1 -0
  150. package/dist/src/platforms/webex/commands/auth.d.ts.map +1 -1
  151. package/dist/src/platforms/webex/commands/auth.js +3 -1
  152. package/dist/src/platforms/webex/commands/auth.js.map +1 -1
  153. package/dist/src/platforms/webex/token-extractor.d.ts +3 -1
  154. package/dist/src/platforms/webex/token-extractor.d.ts.map +1 -1
  155. package/dist/src/platforms/webex/token-extractor.js +16 -2
  156. package/dist/src/platforms/webex/token-extractor.js.map +1 -1
  157. package/dist/src/platforms/wechatbot/cli.d.ts.map +1 -1
  158. package/dist/src/platforms/wechatbot/cli.js +11 -1
  159. package/dist/src/platforms/wechatbot/cli.js.map +1 -1
  160. package/dist/src/platforms/wechatbot/commands/auth.d.ts.map +1 -1
  161. package/dist/src/platforms/wechatbot/commands/auth.js +1 -5
  162. package/dist/src/platforms/wechatbot/commands/auth.js.map +1 -1
  163. package/dist/src/platforms/wechatbot/commands/message.d.ts.map +1 -1
  164. package/dist/src/platforms/wechatbot/commands/message.js +1 -6
  165. package/dist/src/platforms/wechatbot/commands/message.js.map +1 -1
  166. package/dist/src/platforms/wechatbot/commands/template.d.ts.map +1 -1
  167. package/dist/src/platforms/wechatbot/commands/template.js +1 -6
  168. package/dist/src/platforms/wechatbot/commands/template.js.map +1 -1
  169. package/dist/src/platforms/wechatbot/commands/user.d.ts.map +1 -1
  170. package/dist/src/platforms/wechatbot/commands/user.js +1 -6
  171. package/dist/src/platforms/wechatbot/commands/user.js.map +1 -1
  172. package/dist/src/platforms/wechatbot/commands/whoami.d.ts.map +1 -1
  173. package/dist/src/platforms/wechatbot/commands/whoami.js +1 -6
  174. package/dist/src/platforms/wechatbot/commands/whoami.js.map +1 -1
  175. package/dist/src/platforms/whatsappbot/cli.d.ts.map +1 -1
  176. package/dist/src/platforms/whatsappbot/cli.js +11 -1
  177. package/dist/src/platforms/whatsappbot/cli.js.map +1 -1
  178. package/dist/src/platforms/whatsappbot/commands/auth.d.ts.map +1 -1
  179. package/dist/src/platforms/whatsappbot/commands/auth.js +1 -5
  180. package/dist/src/platforms/whatsappbot/commands/auth.js.map +1 -1
  181. package/dist/src/platforms/whatsappbot/commands/message.d.ts.map +1 -1
  182. package/dist/src/platforms/whatsappbot/commands/message.js +1 -6
  183. package/dist/src/platforms/whatsappbot/commands/message.js.map +1 -1
  184. package/dist/src/platforms/whatsappbot/commands/template.d.ts.map +1 -1
  185. package/dist/src/platforms/whatsappbot/commands/template.js +1 -6
  186. package/dist/src/platforms/whatsappbot/commands/template.js.map +1 -1
  187. package/dist/src/platforms/whatsappbot/commands/whoami.d.ts.map +1 -1
  188. package/dist/src/platforms/whatsappbot/commands/whoami.js +1 -6
  189. package/dist/src/platforms/whatsappbot/commands/whoami.js.map +1 -1
  190. package/dist/src/shared/chromium/browsers.d.ts +8 -0
  191. package/dist/src/shared/chromium/browsers.d.ts.map +1 -1
  192. package/dist/src/shared/chromium/browsers.js +58 -3
  193. package/dist/src/shared/chromium/browsers.js.map +1 -1
  194. package/dist/src/shared/chromium/cli-options.d.ts +5 -0
  195. package/dist/src/shared/chromium/cli-options.d.ts.map +1 -0
  196. package/dist/src/shared/chromium/cli-options.js +8 -0
  197. package/dist/src/shared/chromium/cli-options.js.map +1 -0
  198. package/dist/src/shared/chromium/index.d.ts +3 -1
  199. package/dist/src/shared/chromium/index.d.ts.map +1 -1
  200. package/dist/src/shared/chromium/index.js +2 -1
  201. package/dist/src/shared/chromium/index.js.map +1 -1
  202. package/dist/src/shared/utils/cli-output.d.ts +7 -0
  203. package/dist/src/shared/utils/cli-output.d.ts.map +1 -0
  204. package/dist/src/shared/utils/cli-output.js +7 -0
  205. package/dist/src/shared/utils/cli-output.js.map +1 -0
  206. package/dist/src/tui/app.d.ts.map +1 -1
  207. package/dist/src/tui/app.js +73 -20
  208. package/dist/src/tui/app.js.map +1 -1
  209. package/docs/content/docs/cli/channeltalk.mdx +4 -0
  210. package/docs/content/docs/cli/discord.mdx +5 -0
  211. package/docs/content/docs/cli/instagram.mdx +3 -0
  212. package/docs/content/docs/cli/slack.mdx +5 -0
  213. package/docs/content/docs/cli/slackbot.mdx +60 -22
  214. package/docs/content/docs/cli/teams.mdx +5 -0
  215. package/docs/content/docs/cli/webex.mdx +3 -0
  216. package/docs/content/docs/sdk/channeltalkbot.mdx +38 -1
  217. package/docs/content/docs/sdk/discordbot.mdx +501 -0
  218. package/docs/content/docs/sdk/meta.json +2 -0
  219. package/docs/content/docs/sdk/slackbot.mdx +576 -0
  220. package/e2e/README.md +1 -1
  221. package/e2e/config.ts +9 -4
  222. package/examples/discordbot-listen.ts +65 -0
  223. package/examples/slackbot-listen.ts +65 -0
  224. package/package.json +21 -1
  225. package/skills/agent-channeltalk/SKILL.md +5 -1
  226. package/skills/agent-channeltalk/references/authentication.md +5 -1
  227. package/skills/agent-channeltalkbot/SKILL.md +17 -3
  228. package/skills/agent-channeltalkbot/references/authentication.md +7 -5
  229. package/skills/agent-discord/SKILL.md +5 -1
  230. package/skills/agent-discord/references/authentication.md +7 -1
  231. package/skills/agent-discordbot/SKILL.md +13 -2
  232. package/skills/agent-discordbot/references/common-patterns.md +1 -1
  233. package/skills/agent-instagram/SKILL.md +7 -1
  234. package/skills/agent-instagram/references/authentication.md +6 -0
  235. package/skills/agent-kakaotalk/SKILL.md +1 -1
  236. package/skills/agent-line/SKILL.md +1 -1
  237. package/skills/agent-slack/SKILL.md +5 -1
  238. package/skills/agent-slack/references/authentication.md +7 -1
  239. package/skills/agent-slackbot/SKILL.md +56 -4
  240. package/skills/agent-slackbot/references/authentication.md +4 -0
  241. package/skills/agent-teams/SKILL.md +5 -1
  242. package/skills/agent-teams/references/authentication.md +7 -1
  243. package/skills/agent-telegram/SKILL.md +1 -1
  244. package/skills/agent-webex/SKILL.md +7 -1
  245. package/skills/agent-webex/references/authentication.md +6 -0
  246. package/skills/agent-wechatbot/SKILL.md +16 -1
  247. package/skills/agent-wechatbot/references/authentication.md +219 -0
  248. package/skills/agent-wechatbot/references/common-patterns.md +358 -0
  249. package/skills/agent-wechatbot/templates/account-summary.sh +122 -0
  250. package/skills/agent-wechatbot/templates/post-message.sh +122 -0
  251. package/skills/agent-wechatbot/templates/send-template.sh +152 -0
  252. package/skills/agent-whatsapp/SKILL.md +1 -1
  253. package/skills/agent-whatsappbot/SKILL.md +30 -1
  254. package/src/platforms/channeltalk/commands/auth.test.ts +15 -3
  255. package/src/platforms/channeltalk/commands/auth.ts +15 -5
  256. package/src/platforms/channeltalk/token-extractor.ts +24 -5
  257. package/src/platforms/channeltalkbot/cli.ts +9 -0
  258. package/src/platforms/channeltalkbot/commands/auth.ts +1 -5
  259. package/src/platforms/channeltalkbot/commands/bot.ts +1 -6
  260. package/src/platforms/channeltalkbot/commands/chat.ts +1 -6
  261. package/src/platforms/channeltalkbot/commands/group.ts +1 -6
  262. package/src/platforms/channeltalkbot/commands/manager.ts +1 -6
  263. package/src/platforms/channeltalkbot/commands/message.ts +1 -6
  264. package/src/platforms/channeltalkbot/commands/whoami.test.ts +2 -0
  265. package/src/platforms/channeltalkbot/commands/whoami.ts +1 -6
  266. package/src/platforms/channeltalkbot/credential-manager.test.ts +96 -2
  267. package/src/platforms/channeltalkbot/credential-manager.ts +37 -4
  268. package/src/platforms/discord/commands/auth.ts +13 -2
  269. package/src/platforms/discord/listener.test.ts +59 -1
  270. package/src/platforms/discord/listener.ts +43 -19
  271. package/src/platforms/discord/token-extractor.ts +30 -6
  272. package/src/platforms/discordbot/cli.ts +10 -0
  273. package/src/platforms/discordbot/client.ts +4 -0
  274. package/src/platforms/discordbot/commands/auth.ts +1 -5
  275. package/src/platforms/discordbot/commands/message.ts +1 -6
  276. package/src/platforms/discordbot/commands/server.ts +1 -5
  277. package/src/platforms/discordbot/commands/whoami.ts +1 -6
  278. package/src/platforms/discordbot/index.test.ts +82 -0
  279. package/src/platforms/discordbot/index.ts +27 -9
  280. package/src/platforms/discordbot/listener.test.ts +1002 -0
  281. package/src/platforms/discordbot/listener.ts +321 -0
  282. package/src/platforms/discordbot/types.ts +163 -0
  283. package/src/platforms/instagram/commands/auth.ts +9 -1
  284. package/src/platforms/instagram/token-extractor.ts +13 -1
  285. package/src/platforms/slack/commands/auth.ts +11 -2
  286. package/src/platforms/slack/token-extractor.test.ts +96 -0
  287. package/src/platforms/slack/token-extractor.ts +76 -13
  288. package/src/platforms/slackbot/cli.ts +13 -1
  289. package/src/platforms/slackbot/client.test.ts +274 -0
  290. package/src/platforms/slackbot/client.ts +130 -2
  291. package/src/platforms/slackbot/commands/auth.ts +1 -5
  292. package/src/platforms/slackbot/commands/file.test.ts +201 -0
  293. package/src/platforms/slackbot/commands/file.ts +212 -0
  294. package/src/platforms/slackbot/commands/index.ts +1 -0
  295. package/src/platforms/slackbot/commands/message.ts +22 -0
  296. package/src/platforms/slackbot/commands/whoami.ts +1 -6
  297. package/src/platforms/slackbot/credential-manager.test.ts +62 -2
  298. package/src/platforms/slackbot/credential-manager.ts +32 -2
  299. package/src/platforms/slackbot/index.test.ts +59 -0
  300. package/src/platforms/slackbot/index.ts +31 -7
  301. package/src/platforms/slackbot/listener.test.ts +1012 -0
  302. package/src/platforms/slackbot/listener.ts +362 -0
  303. package/src/platforms/slackbot/types.ts +224 -1
  304. package/src/platforms/teams/commands/auth.test.ts +1 -1
  305. package/src/platforms/teams/commands/auth.ts +66 -7
  306. package/src/platforms/teams/ensure-auth.test.ts +56 -5
  307. package/src/platforms/teams/ensure-auth.ts +39 -11
  308. package/src/platforms/teams/token-extractor.test.ts +146 -24
  309. package/src/platforms/teams/token-extractor.ts +87 -29
  310. package/src/platforms/webex/commands/auth.ts +13 -2
  311. package/src/platforms/webex/token-extractor.ts +25 -3
  312. package/src/platforms/wechatbot/cli.ts +9 -0
  313. package/src/platforms/wechatbot/commands/auth.ts +1 -5
  314. package/src/platforms/wechatbot/commands/message.ts +1 -6
  315. package/src/platforms/wechatbot/commands/template.ts +1 -6
  316. package/src/platforms/wechatbot/commands/user.ts +1 -6
  317. package/src/platforms/wechatbot/commands/whoami.ts +1 -6
  318. package/src/platforms/whatsappbot/cli.ts +9 -0
  319. package/src/platforms/whatsappbot/commands/auth.ts +1 -5
  320. package/src/platforms/whatsappbot/commands/message.ts +1 -6
  321. package/src/platforms/whatsappbot/commands/template.ts +1 -6
  322. package/src/platforms/whatsappbot/commands/whoami.ts +1 -6
  323. package/src/shared/chromium/browsers.test.ts +80 -0
  324. package/src/shared/chromium/browsers.ts +72 -3
  325. package/src/shared/chromium/cli-options.test.ts +22 -0
  326. package/src/shared/chromium/cli-options.ts +12 -0
  327. package/src/shared/chromium/index.ts +3 -0
  328. package/src/shared/utils/cli-output.test.ts +57 -0
  329. package/src/shared/utils/cli-output.ts +8 -0
  330. package/src/tui/app.ts +129 -20
@@ -1,6 +1,6 @@
1
- import { existsSync, readdirSync } from 'node:fs'
1
+ import { existsSync, readdirSync, readFileSync } from 'node:fs'
2
2
  import { homedir } from 'node:os'
3
- import { join } from 'node:path'
3
+ import { dirname, isAbsolute, join, resolve } from 'node:path'
4
4
 
5
5
  import type { BrowserConfig, KeychainVariant } from './types'
6
6
 
@@ -39,6 +39,17 @@ export const BROWSER_KEYCHAIN_VARIANTS: KeychainVariant[] = [
39
39
  { service: 'Chromium Safe Storage', account: 'Chromium' },
40
40
  ]
41
41
 
42
+ interface AgentBrowserProfileDiscoveryOptions {
43
+ cwd?: string
44
+ env?: NodeJS.ProcessEnv
45
+ homeDir?: string
46
+ customProfileDirs?: string[]
47
+ }
48
+
49
+ type AgentBrowserConfig = {
50
+ profile?: unknown
51
+ }
52
+
42
53
  export function getBrowserBasePath(browser: BrowserConfig, platform: NodeJS.Platform): string | null {
43
54
  let relative: string
44
55
  switch (platform) {
@@ -70,10 +81,41 @@ export function discoverBrowserProfileDirs(browserBase: string): string[] {
70
81
  if (!/^Profile \d+$/i.test(entry.name)) continue
71
82
  dirs.push(join(browserBase, entry.name))
72
83
  }
73
- } catch {}
84
+ } catch {
85
+ return dirs
86
+ }
74
87
  return dirs
75
88
  }
76
89
 
90
+ export function getAgentBrowserProfileDirs(options: AgentBrowserProfileDiscoveryOptions = {}): string[] {
91
+ const cwd = options.cwd ?? process.cwd()
92
+ const env = options.env ?? process.env
93
+ const homeDir = options.homeDir ?? homedir()
94
+ if (env.AGENT_MESSENGER_DISABLE_AGENT_BROWSER_PROFILE_DISCOVERY === '1') return []
95
+
96
+ const profileDirs: string[] = []
97
+
98
+ for (const profileDir of options.customProfileDirs ?? []) {
99
+ addAgentBrowserProfileDir(profileDirs, profileDir, cwd)
100
+ }
101
+
102
+ addAgentBrowserProfileDir(profileDirs, env.AGENT_BROWSER_PROFILE, cwd)
103
+
104
+ const configPaths = [
105
+ join(homeDir, '.agent-browser', 'config.json'),
106
+ join(cwd, 'agent-browser.json'),
107
+ env.AGENT_BROWSER_CONFIG,
108
+ ]
109
+
110
+ for (const configPath of configPaths) {
111
+ if (!configPath) continue
112
+ const config = readAgentBrowserConfig(configPath)
113
+ addAgentBrowserProfileDir(profileDirs, config?.profile, dirname(configPath))
114
+ }
115
+
116
+ return dedupePaths(profileDirs.flatMap((profileDir) => [profileDir, ...discoverBrowserProfileDirs(profileDir)]))
117
+ }
118
+
77
119
  export function findLocalStatePath(cookieOrProfilePath: string): string | null {
78
120
  const parts = cookieOrProfilePath.split(/[/\\]/)
79
121
  for (let levels = 2; levels <= 4; levels++) {
@@ -84,3 +126,30 @@ export function findLocalStatePath(cookieOrProfilePath: string): string | null {
84
126
  }
85
127
  return null
86
128
  }
129
+
130
+ function readAgentBrowserConfig(configPath: string): AgentBrowserConfig | null {
131
+ if (!existsSync(configPath)) return null
132
+ try {
133
+ const parsed = JSON.parse(readFileSync(configPath, 'utf8')) as unknown
134
+ if (!parsed || typeof parsed !== 'object') return null
135
+ return parsed as AgentBrowserConfig
136
+ } catch {
137
+ return null
138
+ }
139
+ }
140
+
141
+ function addAgentBrowserProfileDir(dirs: string[], profile: unknown, baseDir: string): void {
142
+ if (typeof profile !== 'string' || profile.length === 0) return
143
+ dirs.push(isAbsolute(profile) ? profile : resolve(baseDir, profile))
144
+ }
145
+
146
+ function dedupePaths(paths: string[]): string[] {
147
+ const seen = new Set<string>()
148
+ const result: string[] = []
149
+ for (const path of paths) {
150
+ if (seen.has(path)) continue
151
+ seen.add(path)
152
+ result.push(path)
153
+ }
154
+ return result
155
+ }
@@ -0,0 +1,22 @@
1
+ import { describe, expect, it } from 'bun:test'
2
+
3
+ import { collectBrowserProfileOption } from './cli-options'
4
+
5
+ describe('collectBrowserProfileOption', () => {
6
+ it('collects repeated browser profile options', () => {
7
+ // when
8
+ const first = collectBrowserProfileOption('/tmp/profile-a')
9
+ const second = collectBrowserProfileOption('/tmp/profile-b', first)
10
+
11
+ // then
12
+ expect(second).toEqual(['/tmp/profile-a', '/tmp/profile-b'])
13
+ })
14
+
15
+ it('splits comma-separated browser profile options', () => {
16
+ // when
17
+ const profiles = collectBrowserProfileOption('/tmp/profile-a, /tmp/profile-b,,')
18
+
19
+ // then
20
+ expect(profiles).toEqual(['/tmp/profile-a', '/tmp/profile-b'])
21
+ })
22
+ })
@@ -0,0 +1,12 @@
1
+ export interface BrowserProfileOption {
2
+ browserProfile?: string[]
3
+ }
4
+
5
+ export function collectBrowserProfileOption(value: string, previous: string[] = []): string[] {
6
+ const paths = value
7
+ .split(',')
8
+ .map((path) => path.trim())
9
+ .filter((path) => path.length > 0)
10
+
11
+ return [...previous, ...paths]
12
+ }
@@ -4,8 +4,11 @@ export {
4
4
  CHROMIUM_BROWSERS,
5
5
  discoverBrowserProfileDirs,
6
6
  findLocalStatePath,
7
+ getAgentBrowserProfileDirs,
7
8
  getBrowserBasePath,
8
9
  } from './browsers'
9
10
  export { ChromiumCookieDecryptor } from './decryptor'
10
11
  export type { ChromiumDecryptorOptions } from './decryptor'
11
12
  export { ChromiumCookieReader } from './cookie-reader'
13
+ export { collectBrowserProfileOption } from './cli-options'
14
+ export type { BrowserProfileOption } from './cli-options'
@@ -0,0 +1,57 @@
1
+ import { afterEach, beforeEach, describe, expect, it, mock } from 'bun:test'
2
+
3
+ import { cliOutput } from './cli-output'
4
+
5
+ describe('cliOutput', () => {
6
+ let logSpy: ReturnType<typeof mock>
7
+ let exitSpy: ReturnType<typeof mock>
8
+ let originalLog: typeof console.log
9
+ let originalExit: typeof process.exit
10
+
11
+ beforeEach(() => {
12
+ originalLog = console.log
13
+ originalExit = process.exit
14
+ logSpy = mock(() => {})
15
+ exitSpy = mock(((_code?: number) => undefined) as never)
16
+ console.log = logSpy as unknown as typeof console.log
17
+ process.exit = exitSpy as unknown as typeof process.exit
18
+ })
19
+
20
+ afterEach(() => {
21
+ console.log = originalLog
22
+ process.exit = originalExit
23
+ })
24
+
25
+ it('prints compact JSON for success results', () => {
26
+ cliOutput({ ok: true, value: 42 })
27
+
28
+ expect(logSpy).toHaveBeenCalledWith('{"ok":true,"value":42}')
29
+ expect(exitSpy).not.toHaveBeenCalled()
30
+ })
31
+
32
+ it('prints pretty JSON when pretty=true', () => {
33
+ cliOutput({ ok: true }, true)
34
+
35
+ expect(logSpy).toHaveBeenCalledWith('{\n "ok": true\n}')
36
+ })
37
+
38
+ it('exits 1 when result.error is set', () => {
39
+ cliOutput({ error: 'Something went wrong' })
40
+
41
+ expect(logSpy).toHaveBeenCalledWith('{"error":"Something went wrong"}')
42
+ expect(exitSpy).toHaveBeenCalledWith(1)
43
+ })
44
+
45
+ it('does not exit when exitOnError=false even with error set', () => {
46
+ cliOutput({ error: 'Soft fail' }, false, false)
47
+
48
+ expect(logSpy).toHaveBeenCalledWith('{"error":"Soft fail"}')
49
+ expect(exitSpy).not.toHaveBeenCalled()
50
+ })
51
+
52
+ it('does not exit when error is undefined', () => {
53
+ cliOutput({ error: undefined, success: true })
54
+
55
+ expect(exitSpy).not.toHaveBeenCalled()
56
+ })
57
+ })
@@ -0,0 +1,8 @@
1
+ import { formatOutput } from './output'
2
+
3
+ export type CliResult = { error?: string } & Record<string, unknown>
4
+
5
+ export function cliOutput<T extends { error?: string }>(result: T, pretty?: boolean, exitOnError = true): void {
6
+ console.log(formatOutput(result, pretty))
7
+ if (result.error && exitOnError) process.exit(1)
8
+ }
package/src/tui/app.ts CHANGED
@@ -1,20 +1,89 @@
1
1
  import blessed from 'blessed'
2
2
 
3
- import { ChannelTalkAdapter } from './adapters/channeltalk-adapter'
4
- import { DiscordAdapter } from './adapters/discord-adapter'
5
- import { InstagramAdapter } from './adapters/instagram-adapter'
6
- import { KakaoTalkAdapter } from './adapters/kakaotalk-adapter'
7
- import { LineAdapter } from './adapters/line-adapter'
8
- import { SlackAdapter } from './adapters/slack-adapter'
9
- import { TeamsAdapter } from './adapters/teams-adapter'
10
- import { TelegramAdapter } from './adapters/telegram-adapter'
11
3
  import type { AuthIO, PlatformAdapter, UnifiedChannel, UnifiedMessage, Workspace } from './adapters/types'
12
- import { WebexAdapter } from './adapters/webex-adapter'
13
- import { WhatsAppAdapter } from './adapters/whatsapp-adapter'
14
4
  import { formatTimestamp } from './utils'
15
5
  import { ChannelPicker } from './views/channel-picker'
16
6
  import { WorkspacePicker } from './views/workspace-picker'
17
7
 
8
+ type PlatformAdapterFactory = () => Promise<PlatformAdapter>
9
+
10
+ class LazyPlatformAdapter implements PlatformAdapter {
11
+ readonly name: string
12
+ private adapter: PlatformAdapter | null = null
13
+ private loadPromise: Promise<PlatformAdapter> | null = null
14
+
15
+ constructor(
16
+ name: string,
17
+ private readonly fallbackAuthHint: string,
18
+ private readonly factory: PlatformAdapterFactory,
19
+ ) {
20
+ this.name = name
21
+ }
22
+
23
+ private async load(): Promise<PlatformAdapter> {
24
+ if (this.adapter) return this.adapter
25
+ this.loadPromise ??= this.factory()
26
+ .then((adapter) => {
27
+ this.adapter = adapter
28
+ return adapter
29
+ })
30
+ .catch((error: unknown) => {
31
+ this.loadPromise = null
32
+ throw error
33
+ })
34
+ return this.loadPromise
35
+ }
36
+
37
+ async login(): Promise<void> {
38
+ await (await this.load()).login()
39
+ }
40
+
41
+ async getChannels(): Promise<UnifiedChannel[]> {
42
+ return (await this.load()).getChannels()
43
+ }
44
+
45
+ async getMessages(channelId: string, limit?: number): Promise<UnifiedMessage[]> {
46
+ return (await this.load()).getMessages(channelId, limit)
47
+ }
48
+
49
+ async sendMessage(channelId: string, text: string): Promise<void> {
50
+ await (await this.load()).sendMessage(channelId, text)
51
+ }
52
+
53
+ async startListening(onMessage: (msg: UnifiedMessage) => void): Promise<void> {
54
+ const adapter = await this.load()
55
+ await adapter.startListening?.(onMessage)
56
+ }
57
+
58
+ stopListening(): void {
59
+ this.adapter?.stopListening?.()
60
+ }
61
+
62
+ async getWorkspaces(): Promise<Workspace[]> {
63
+ return (await this.load()).getWorkspaces?.() ?? []
64
+ }
65
+
66
+ async switchWorkspace(workspaceId: string): Promise<void> {
67
+ await (await this.load()).switchWorkspace?.(workspaceId)
68
+ }
69
+
70
+ getCurrentWorkspace(): Workspace | null {
71
+ return this.adapter?.getCurrentWorkspace?.() ?? null
72
+ }
73
+
74
+ getAuthHint() {
75
+ return this.adapter?.getAuthHint() ?? { command: this.fallbackAuthHint, description: `Authenticate ${this.name}` }
76
+ }
77
+
78
+ async authenticate(io: AuthIO): Promise<void> {
79
+ await (await this.load()).authenticate(io)
80
+ }
81
+ }
82
+
83
+ function lazyAdapter(name: string, fallbackAuthHint: string, factory: PlatformAdapterFactory): PlatformAdapter {
84
+ return new LazyPlatformAdapter(name, fallbackAuthHint, factory)
85
+ }
86
+
18
87
  type AppMode = 'selection' | 'read' | 'write' | 'auth'
19
88
  type NavLevel = 'platform' | 'workspace' | 'channel'
20
89
 
@@ -36,7 +105,11 @@ export async function createApp(): Promise<void> {
36
105
 
37
106
  const platformStates: PlatformState[] = [
38
107
  {
39
- adapter: new SlackAdapter(),
108
+ adapter: lazyAdapter(
109
+ 'Slack',
110
+ 'agent-slack auth extract',
111
+ async () => new (await import('./adapters/slack-adapter')).SlackAdapter(),
112
+ ),
40
113
  label: 'Slack',
41
114
  enabled: false,
42
115
  channels: null,
@@ -45,7 +118,11 @@ export async function createApp(): Promise<void> {
45
118
  lastChannelId: null,
46
119
  },
47
120
  {
48
- adapter: new DiscordAdapter(),
121
+ adapter: lazyAdapter(
122
+ 'Discord',
123
+ 'agent-discord auth extract',
124
+ async () => new (await import('./adapters/discord-adapter')).DiscordAdapter(),
125
+ ),
49
126
  label: 'Discord',
50
127
  enabled: false,
51
128
  channels: null,
@@ -54,7 +131,11 @@ export async function createApp(): Promise<void> {
54
131
  lastChannelId: null,
55
132
  },
56
133
  {
57
- adapter: new TeamsAdapter(),
134
+ adapter: lazyAdapter(
135
+ 'Teams',
136
+ 'agent-teams auth extract',
137
+ async () => new (await import('./adapters/teams-adapter')).TeamsAdapter(),
138
+ ),
58
139
  label: 'Teams',
59
140
  enabled: false,
60
141
  channels: null,
@@ -63,7 +144,11 @@ export async function createApp(): Promise<void> {
63
144
  lastChannelId: null,
64
145
  },
65
146
  {
66
- adapter: new WebexAdapter(),
147
+ adapter: lazyAdapter(
148
+ 'Webex',
149
+ 'agent-webex auth extract',
150
+ async () => new (await import('./adapters/webex-adapter')).WebexAdapter(),
151
+ ),
67
152
  label: 'Webex',
68
153
  enabled: false,
69
154
  channels: null,
@@ -72,7 +157,11 @@ export async function createApp(): Promise<void> {
72
157
  lastChannelId: null,
73
158
  },
74
159
  {
75
- adapter: new TelegramAdapter(),
160
+ adapter: lazyAdapter(
161
+ 'Telegram',
162
+ 'agent-telegram auth login',
163
+ async () => new (await import('./adapters/telegram-adapter')).TelegramAdapter(),
164
+ ),
76
165
  label: 'Telegram',
77
166
  enabled: false,
78
167
  channels: null,
@@ -81,7 +170,11 @@ export async function createApp(): Promise<void> {
81
170
  lastChannelId: null,
82
171
  },
83
172
  {
84
- adapter: new WhatsAppAdapter(),
173
+ adapter: lazyAdapter(
174
+ 'WhatsApp',
175
+ 'agent-whatsapp auth login',
176
+ async () => new (await import('./adapters/whatsapp-adapter')).WhatsAppAdapter(),
177
+ ),
85
178
  label: 'WhatsApp',
86
179
  enabled: false,
87
180
  channels: null,
@@ -90,7 +183,11 @@ export async function createApp(): Promise<void> {
90
183
  lastChannelId: null,
91
184
  },
92
185
  {
93
- adapter: new LineAdapter(),
186
+ adapter: lazyAdapter(
187
+ 'LINE',
188
+ 'agent-line auth login',
189
+ async () => new (await import('./adapters/line-adapter')).LineAdapter(),
190
+ ),
94
191
  label: 'LINE',
95
192
  enabled: false,
96
193
  channels: null,
@@ -99,7 +196,11 @@ export async function createApp(): Promise<void> {
99
196
  lastChannelId: null,
100
197
  },
101
198
  {
102
- adapter: new InstagramAdapter(),
199
+ adapter: lazyAdapter(
200
+ 'Instagram',
201
+ 'agent-instagram auth login',
202
+ async () => new (await import('./adapters/instagram-adapter')).InstagramAdapter(),
203
+ ),
103
204
  label: 'Instagram',
104
205
  enabled: false,
105
206
  channels: null,
@@ -108,7 +209,11 @@ export async function createApp(): Promise<void> {
108
209
  lastChannelId: null,
109
210
  },
110
211
  {
111
- adapter: new KakaoTalkAdapter(),
212
+ adapter: lazyAdapter(
213
+ 'KakaoTalk',
214
+ 'agent-kakaotalk auth extract',
215
+ async () => new (await import('./adapters/kakaotalk-adapter')).KakaoTalkAdapter(),
216
+ ),
112
217
  label: 'KakaoTalk',
113
218
  enabled: false,
114
219
  channels: null,
@@ -117,7 +222,11 @@ export async function createApp(): Promise<void> {
117
222
  lastChannelId: null,
118
223
  },
119
224
  {
120
- adapter: new ChannelTalkAdapter(),
225
+ adapter: lazyAdapter(
226
+ 'Channel Talk',
227
+ 'agent-channeltalk auth extract',
228
+ async () => new (await import('./adapters/channeltalk-adapter')).ChannelTalkAdapter(),
229
+ ),
121
230
  label: 'Channel Talk',
122
231
  enabled: false,
123
232
  channels: null,