@larksuite/openclaw-lark 2026.3.9

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 (689) hide show
  1. package/LICENSE +10 -0
  2. package/README.md +283 -0
  3. package/index.d.ts +37 -0
  4. package/index.d.ts.map +1 -0
  5. package/index.js +119 -0
  6. package/index.js.map +1 -0
  7. package/openclaw.plugin.json +10 -0
  8. package/package.json +47 -0
  9. package/skills/feishu-bitable/SKILL.md +248 -0
  10. package/skills/feishu-bitable/references/examples.md +813 -0
  11. package/skills/feishu-bitable/references/field-properties.md +763 -0
  12. package/skills/feishu-bitable/references/record-values.md +911 -0
  13. package/skills/feishu-calendar/SKILL.md +244 -0
  14. package/skills/feishu-channel-rules/SKILL.md +18 -0
  15. package/skills/feishu-channel-rules/references/markdown-syntax.md +138 -0
  16. package/skills/feishu-create-doc/SKILL.md +719 -0
  17. package/skills/feishu-fetch-doc/SKILL.md +93 -0
  18. package/skills/feishu-im-read/SKILL.md +163 -0
  19. package/skills/feishu-task/SKILL.md +293 -0
  20. package/skills/feishu-troubleshoot/SKILL.md +70 -0
  21. package/skills/feishu-update-doc/SKILL.md +285 -0
  22. package/src/card/builder.d.ts +100 -0
  23. package/src/card/builder.d.ts.map +1 -0
  24. package/src/card/builder.js +381 -0
  25. package/src/card/builder.js.map +1 -0
  26. package/src/card/cardkit.d.ts +91 -0
  27. package/src/card/cardkit.d.ts.map +1 -0
  28. package/src/card/cardkit.js +182 -0
  29. package/src/card/cardkit.js.map +1 -0
  30. package/src/card/flush-controller.d.ts +46 -0
  31. package/src/card/flush-controller.d.ts.map +1 -0
  32. package/src/card/flush-controller.js +135 -0
  33. package/src/card/flush-controller.js.map +1 -0
  34. package/src/card/markdown-style.d.ts +17 -0
  35. package/src/card/markdown-style.d.ts.map +1 -0
  36. package/src/card/markdown-style.js +98 -0
  37. package/src/card/markdown-style.js.map +1 -0
  38. package/src/card/reply-dispatcher-types.d.ts +121 -0
  39. package/src/card/reply-dispatcher-types.d.ts.map +1 -0
  40. package/src/card/reply-dispatcher-types.js +58 -0
  41. package/src/card/reply-dispatcher-types.js.map +1 -0
  42. package/src/card/reply-dispatcher.d.ts +16 -0
  43. package/src/card/reply-dispatcher.d.ts.map +1 -0
  44. package/src/card/reply-dispatcher.js +293 -0
  45. package/src/card/reply-dispatcher.js.map +1 -0
  46. package/src/card/reply-mode.d.ts +39 -0
  47. package/src/card/reply-mode.d.ts.map +1 -0
  48. package/src/card/reply-mode.js +66 -0
  49. package/src/card/reply-mode.js.map +1 -0
  50. package/src/card/streaming-card-controller.d.ts +88 -0
  51. package/src/card/streaming-card-controller.d.ts.map +1 -0
  52. package/src/card/streaming-card-controller.js +717 -0
  53. package/src/card/streaming-card-controller.js.map +1 -0
  54. package/src/card/unavailable-guard.d.ts +36 -0
  55. package/src/card/unavailable-guard.d.ts.map +1 -0
  56. package/src/card/unavailable-guard.js +84 -0
  57. package/src/card/unavailable-guard.js.map +1 -0
  58. package/src/channel/abort-detect.d.ts +35 -0
  59. package/src/channel/abort-detect.d.ts.map +1 -0
  60. package/src/channel/abort-detect.js +125 -0
  61. package/src/channel/abort-detect.js.map +1 -0
  62. package/src/channel/chat-queue.d.ts +42 -0
  63. package/src/channel/chat-queue.d.ts.map +1 -0
  64. package/src/channel/chat-queue.js +59 -0
  65. package/src/channel/chat-queue.js.map +1 -0
  66. package/src/channel/config-adapter.d.ts +24 -0
  67. package/src/channel/config-adapter.d.ts.map +1 -0
  68. package/src/channel/config-adapter.js +102 -0
  69. package/src/channel/config-adapter.js.map +1 -0
  70. package/src/channel/directory.d.ts +58 -0
  71. package/src/channel/directory.d.ts.map +1 -0
  72. package/src/channel/directory.js +192 -0
  73. package/src/channel/directory.js.map +1 -0
  74. package/src/channel/event-handlers.d.ts +16 -0
  75. package/src/channel/event-handlers.d.ts.map +1 -0
  76. package/src/channel/event-handlers.js +222 -0
  77. package/src/channel/event-handlers.js.map +1 -0
  78. package/src/channel/monitor.d.ts +18 -0
  79. package/src/channel/monitor.d.ts.map +1 -0
  80. package/src/channel/monitor.js +128 -0
  81. package/src/channel/monitor.js.map +1 -0
  82. package/src/channel/onboarding-config.d.ts +18 -0
  83. package/src/channel/onboarding-config.d.ts.map +1 -0
  84. package/src/channel/onboarding-config.js +89 -0
  85. package/src/channel/onboarding-config.js.map +1 -0
  86. package/src/channel/onboarding-migrate.d.ts +26 -0
  87. package/src/channel/onboarding-migrate.d.ts.map +1 -0
  88. package/src/channel/onboarding-migrate.js +68 -0
  89. package/src/channel/onboarding-migrate.js.map +1 -0
  90. package/src/channel/onboarding.d.ts +13 -0
  91. package/src/channel/onboarding.d.ts.map +1 -0
  92. package/src/channel/onboarding.js +297 -0
  93. package/src/channel/onboarding.js.map +1 -0
  94. package/src/channel/plugin.d.ts +14 -0
  95. package/src/channel/plugin.d.ts.map +1 -0
  96. package/src/channel/plugin.js +279 -0
  97. package/src/channel/plugin.js.map +1 -0
  98. package/src/channel/probe.d.ts +15 -0
  99. package/src/channel/probe.d.ts.map +1 -0
  100. package/src/channel/probe.js +22 -0
  101. package/src/channel/probe.js.map +1 -0
  102. package/src/channel/types.d.ts +37 -0
  103. package/src/channel/types.d.ts.map +1 -0
  104. package/src/channel/types.js +8 -0
  105. package/src/channel/types.js.map +1 -0
  106. package/src/commands/auth.d.ts +16 -0
  107. package/src/commands/auth.d.ts.map +1 -0
  108. package/src/commands/auth.js +85 -0
  109. package/src/commands/auth.js.map +1 -0
  110. package/src/commands/diagnose.d.ts +70 -0
  111. package/src/commands/diagnose.d.ts.map +1 -0
  112. package/src/commands/diagnose.js +808 -0
  113. package/src/commands/diagnose.js.map +1 -0
  114. package/src/commands/doctor.d.ts +18 -0
  115. package/src/commands/doctor.d.ts.map +1 -0
  116. package/src/commands/doctor.js +439 -0
  117. package/src/commands/doctor.js.map +1 -0
  118. package/src/commands/index.d.ts +9 -0
  119. package/src/commands/index.d.ts.map +1 -0
  120. package/src/commands/index.js +208 -0
  121. package/src/commands/index.js.map +1 -0
  122. package/src/core/accounts.d.ts +38 -0
  123. package/src/core/accounts.d.ts.map +1 -0
  124. package/src/core/accounts.js +179 -0
  125. package/src/core/accounts.js.map +1 -0
  126. package/src/core/agent-config.d.ts +101 -0
  127. package/src/core/agent-config.d.ts.map +1 -0
  128. package/src/core/agent-config.js +140 -0
  129. package/src/core/agent-config.js.map +1 -0
  130. package/src/core/api-error.d.ts +49 -0
  131. package/src/core/api-error.d.ts.map +1 -0
  132. package/src/core/api-error.js +113 -0
  133. package/src/core/api-error.js.map +1 -0
  134. package/src/core/app-owner-fallback.d.ts +22 -0
  135. package/src/core/app-owner-fallback.d.ts.map +1 -0
  136. package/src/core/app-owner-fallback.js +39 -0
  137. package/src/core/app-owner-fallback.js.map +1 -0
  138. package/src/core/app-scope-checker.d.ts +88 -0
  139. package/src/core/app-scope-checker.d.ts.map +1 -0
  140. package/src/core/app-scope-checker.js +191 -0
  141. package/src/core/app-scope-checker.js.map +1 -0
  142. package/src/core/auth-errors.d.ts +143 -0
  143. package/src/core/auth-errors.d.ts.map +1 -0
  144. package/src/core/auth-errors.js +156 -0
  145. package/src/core/auth-errors.js.map +1 -0
  146. package/src/core/chat-info-cache.d.ts +58 -0
  147. package/src/core/chat-info-cache.d.ts.map +1 -0
  148. package/src/core/chat-info-cache.js +153 -0
  149. package/src/core/chat-info-cache.js.map +1 -0
  150. package/src/core/config-schema.d.ts +449 -0
  151. package/src/core/config-schema.d.ts.map +1 -0
  152. package/src/core/config-schema.js +201 -0
  153. package/src/core/config-schema.js.map +1 -0
  154. package/src/core/device-flow.d.ts +78 -0
  155. package/src/core/device-flow.d.ts.map +1 -0
  156. package/src/core/device-flow.js +213 -0
  157. package/src/core/device-flow.js.map +1 -0
  158. package/src/core/feishu-fetch.d.ts +19 -0
  159. package/src/core/feishu-fetch.d.ts.map +1 -0
  160. package/src/core/feishu-fetch.js +26 -0
  161. package/src/core/feishu-fetch.js.map +1 -0
  162. package/src/core/footer-config.d.ts +25 -0
  163. package/src/core/footer-config.d.ts.map +1 -0
  164. package/src/core/footer-config.js +40 -0
  165. package/src/core/footer-config.js.map +1 -0
  166. package/src/core/lark-client.d.ts +109 -0
  167. package/src/core/lark-client.d.ts.map +1 -0
  168. package/src/core/lark-client.js +354 -0
  169. package/src/core/lark-client.js.map +1 -0
  170. package/src/core/lark-logger.d.ts +24 -0
  171. package/src/core/lark-logger.d.ts.map +1 -0
  172. package/src/core/lark-logger.js +155 -0
  173. package/src/core/lark-logger.js.map +1 -0
  174. package/src/core/lark-ticket.d.ts +30 -0
  175. package/src/core/lark-ticket.d.ts.map +1 -0
  176. package/src/core/lark-ticket.js +36 -0
  177. package/src/core/lark-ticket.js.map +1 -0
  178. package/src/core/message-unavailable.d.ts +54 -0
  179. package/src/core/message-unavailable.d.ts.map +1 -0
  180. package/src/core/message-unavailable.js +131 -0
  181. package/src/core/message-unavailable.js.map +1 -0
  182. package/src/core/owner-policy.d.ts +32 -0
  183. package/src/core/owner-policy.d.ts.map +1 -0
  184. package/src/core/owner-policy.js +53 -0
  185. package/src/core/owner-policy.js.map +1 -0
  186. package/src/core/permission-url.d.ts +23 -0
  187. package/src/core/permission-url.d.ts.map +1 -0
  188. package/src/core/permission-url.js +73 -0
  189. package/src/core/permission-url.js.map +1 -0
  190. package/src/core/raw-request.d.ts +28 -0
  191. package/src/core/raw-request.d.ts.map +1 -0
  192. package/src/core/raw-request.js +63 -0
  193. package/src/core/raw-request.js.map +1 -0
  194. package/src/core/scope-manager.d.ts +169 -0
  195. package/src/core/scope-manager.d.ts.map +1 -0
  196. package/src/core/scope-manager.js +214 -0
  197. package/src/core/scope-manager.js.map +1 -0
  198. package/src/core/security-check.d.ts +73 -0
  199. package/src/core/security-check.d.ts.map +1 -0
  200. package/src/core/security-check.js +175 -0
  201. package/src/core/security-check.js.map +1 -0
  202. package/src/core/shutdown-hooks.d.ts +23 -0
  203. package/src/core/shutdown-hooks.d.ts.map +1 -0
  204. package/src/core/shutdown-hooks.js +57 -0
  205. package/src/core/shutdown-hooks.js.map +1 -0
  206. package/src/core/targets.d.ts +50 -0
  207. package/src/core/targets.d.ts.map +1 -0
  208. package/src/core/targets.js +128 -0
  209. package/src/core/targets.js.map +1 -0
  210. package/src/core/token-store.d.ts +55 -0
  211. package/src/core/token-store.d.ts.map +1 -0
  212. package/src/core/token-store.js +315 -0
  213. package/src/core/token-store.js.map +1 -0
  214. package/src/core/tool-client.d.ts +177 -0
  215. package/src/core/tool-client.d.ts.map +1 -0
  216. package/src/core/tool-client.js +381 -0
  217. package/src/core/tool-client.js.map +1 -0
  218. package/src/core/tool-scopes.d.ts +154 -0
  219. package/src/core/tool-scopes.d.ts.map +1 -0
  220. package/src/core/tool-scopes.js +326 -0
  221. package/src/core/tool-scopes.js.map +1 -0
  222. package/src/core/tools-config.d.ts +35 -0
  223. package/src/core/tools-config.d.ts.map +1 -0
  224. package/src/core/tools-config.js +88 -0
  225. package/src/core/tools-config.js.map +1 -0
  226. package/src/core/types.d.ts +88 -0
  227. package/src/core/types.d.ts.map +1 -0
  228. package/src/core/types.js +12 -0
  229. package/src/core/types.js.map +1 -0
  230. package/src/core/uat-client.d.ts +47 -0
  231. package/src/core/uat-client.d.ts.map +1 -0
  232. package/src/core/uat-client.js +173 -0
  233. package/src/core/uat-client.js.map +1 -0
  234. package/src/core/version.d.ts +26 -0
  235. package/src/core/version.d.ts.map +1 -0
  236. package/src/core/version.js +50 -0
  237. package/src/core/version.js.map +1 -0
  238. package/src/messaging/converters/audio.d.ts +9 -0
  239. package/src/messaging/converters/audio.d.ts.map +1 -0
  240. package/src/messaging/converters/audio.js +22 -0
  241. package/src/messaging/converters/audio.js.map +1 -0
  242. package/src/messaging/converters/calendar.d.ts +14 -0
  243. package/src/messaging/converters/calendar.d.ts.map +1 -0
  244. package/src/messaging/converters/calendar.js +51 -0
  245. package/src/messaging/converters/calendar.js.map +1 -0
  246. package/src/messaging/converters/content-converter.d.ts +42 -0
  247. package/src/messaging/converters/content-converter.d.ts.map +1 -0
  248. package/src/messaging/converters/content-converter.js +107 -0
  249. package/src/messaging/converters/content-converter.js.map +1 -0
  250. package/src/messaging/converters/file.d.ts +9 -0
  251. package/src/messaging/converters/file.d.ts.map +1 -0
  252. package/src/messaging/converters/file.js +21 -0
  253. package/src/messaging/converters/file.js.map +1 -0
  254. package/src/messaging/converters/folder.d.ts +9 -0
  255. package/src/messaging/converters/folder.d.ts.map +1 -0
  256. package/src/messaging/converters/folder.js +21 -0
  257. package/src/messaging/converters/folder.js.map +1 -0
  258. package/src/messaging/converters/hongbao.d.ts +9 -0
  259. package/src/messaging/converters/hongbao.d.ts.map +1 -0
  260. package/src/messaging/converters/hongbao.js +17 -0
  261. package/src/messaging/converters/hongbao.js.map +1 -0
  262. package/src/messaging/converters/image.d.ts +9 -0
  263. package/src/messaging/converters/image.d.ts.map +1 -0
  264. package/src/messaging/converters/image.js +19 -0
  265. package/src/messaging/converters/image.js.map +1 -0
  266. package/src/messaging/converters/index.d.ts +9 -0
  267. package/src/messaging/converters/index.d.ts.map +1 -0
  268. package/src/messaging/converters/index.js +51 -0
  269. package/src/messaging/converters/index.js.map +1 -0
  270. package/src/messaging/converters/interactive/card-converter.d.ts +77 -0
  271. package/src/messaging/converters/interactive/card-converter.d.ts.map +1 -0
  272. package/src/messaging/converters/interactive/card-converter.js +1174 -0
  273. package/src/messaging/converters/interactive/card-converter.js.map +1 -0
  274. package/src/messaging/converters/interactive/card-utils.d.ts +10 -0
  275. package/src/messaging/converters/interactive/card-utils.d.ts.map +1 -0
  276. package/src/messaging/converters/interactive/card-utils.js +43 -0
  277. package/src/messaging/converters/interactive/card-utils.js.map +1 -0
  278. package/src/messaging/converters/interactive/index.d.ts +9 -0
  279. package/src/messaging/converters/interactive/index.d.ts.map +1 -0
  280. package/src/messaging/converters/interactive/index.js +22 -0
  281. package/src/messaging/converters/interactive/index.js.map +1 -0
  282. package/src/messaging/converters/interactive/legacy.d.ts +12 -0
  283. package/src/messaging/converters/interactive/legacy.d.ts.map +1 -0
  284. package/src/messaging/converters/interactive/legacy.js +58 -0
  285. package/src/messaging/converters/interactive/legacy.js.map +1 -0
  286. package/src/messaging/converters/interactive/types.d.ts +24 -0
  287. package/src/messaging/converters/interactive/types.d.ts.map +1 -0
  288. package/src/messaging/converters/interactive/types.js +25 -0
  289. package/src/messaging/converters/interactive/types.js.map +1 -0
  290. package/src/messaging/converters/location.d.ts +9 -0
  291. package/src/messaging/converters/location.d.ts.map +1 -0
  292. package/src/messaging/converters/location.js +20 -0
  293. package/src/messaging/converters/location.js.map +1 -0
  294. package/src/messaging/converters/merge-forward.d.ts +33 -0
  295. package/src/messaging/converters/merge-forward.d.ts.map +1 -0
  296. package/src/messaging/converters/merge-forward.js +226 -0
  297. package/src/messaging/converters/merge-forward.js.map +1 -0
  298. package/src/messaging/converters/post.d.ts +12 -0
  299. package/src/messaging/converters/post.d.ts.map +1 -0
  300. package/src/messaging/converters/post.js +136 -0
  301. package/src/messaging/converters/post.js.map +1 -0
  302. package/src/messaging/converters/share.d.ts +10 -0
  303. package/src/messaging/converters/share.d.ts.map +1 -0
  304. package/src/messaging/converters/share.js +24 -0
  305. package/src/messaging/converters/share.js.map +1 -0
  306. package/src/messaging/converters/sticker.d.ts +9 -0
  307. package/src/messaging/converters/sticker.d.ts.map +1 -0
  308. package/src/messaging/converters/sticker.js +19 -0
  309. package/src/messaging/converters/sticker.js.map +1 -0
  310. package/src/messaging/converters/system.d.ts +13 -0
  311. package/src/messaging/converters/system.d.ts.map +1 -0
  312. package/src/messaging/converters/system.js +33 -0
  313. package/src/messaging/converters/system.js.map +1 -0
  314. package/src/messaging/converters/text.d.ts +9 -0
  315. package/src/messaging/converters/text.d.ts.map +1 -0
  316. package/src/messaging/converters/text.js +15 -0
  317. package/src/messaging/converters/text.js.map +1 -0
  318. package/src/messaging/converters/todo.d.ts +9 -0
  319. package/src/messaging/converters/todo.d.ts.map +1 -0
  320. package/src/messaging/converters/todo.js +42 -0
  321. package/src/messaging/converters/todo.js.map +1 -0
  322. package/src/messaging/converters/types.d.ts +108 -0
  323. package/src/messaging/converters/types.d.ts.map +1 -0
  324. package/src/messaging/converters/types.js +8 -0
  325. package/src/messaging/converters/types.js.map +1 -0
  326. package/src/messaging/converters/unknown.d.ts +9 -0
  327. package/src/messaging/converters/unknown.d.ts.map +1 -0
  328. package/src/messaging/converters/unknown.js +17 -0
  329. package/src/messaging/converters/unknown.js.map +1 -0
  330. package/src/messaging/converters/utils.d.ts +23 -0
  331. package/src/messaging/converters/utils.d.ts.map +1 -0
  332. package/src/messaging/converters/utils.js +52 -0
  333. package/src/messaging/converters/utils.js.map +1 -0
  334. package/src/messaging/converters/video-chat.d.ts +9 -0
  335. package/src/messaging/converters/video-chat.d.ts.map +1 -0
  336. package/src/messaging/converters/video-chat.js +24 -0
  337. package/src/messaging/converters/video-chat.js.map +1 -0
  338. package/src/messaging/converters/video.d.ts +9 -0
  339. package/src/messaging/converters/video.d.ts.map +1 -0
  340. package/src/messaging/converters/video.js +33 -0
  341. package/src/messaging/converters/video.js.map +1 -0
  342. package/src/messaging/converters/vote.d.ts +9 -0
  343. package/src/messaging/converters/vote.d.ts.map +1 -0
  344. package/src/messaging/converters/vote.js +25 -0
  345. package/src/messaging/converters/vote.js.map +1 -0
  346. package/src/messaging/inbound/dedup.d.ts +60 -0
  347. package/src/messaging/inbound/dedup.d.ts.map +1 -0
  348. package/src/messaging/inbound/dedup.js +117 -0
  349. package/src/messaging/inbound/dedup.js.map +1 -0
  350. package/src/messaging/inbound/dispatch-builders.d.ts +84 -0
  351. package/src/messaging/inbound/dispatch-builders.d.ts.map +1 -0
  352. package/src/messaging/inbound/dispatch-builders.js +153 -0
  353. package/src/messaging/inbound/dispatch-builders.js.map +1 -0
  354. package/src/messaging/inbound/dispatch-commands.d.ts +28 -0
  355. package/src/messaging/inbound/dispatch-commands.d.ts.map +1 -0
  356. package/src/messaging/inbound/dispatch-commands.js +113 -0
  357. package/src/messaging/inbound/dispatch-commands.js.map +1 -0
  358. package/src/messaging/inbound/dispatch-context.d.ts +68 -0
  359. package/src/messaging/inbound/dispatch-context.d.ts.map +1 -0
  360. package/src/messaging/inbound/dispatch-context.js +137 -0
  361. package/src/messaging/inbound/dispatch-context.js.map +1 -0
  362. package/src/messaging/inbound/dispatch.d.ts +48 -0
  363. package/src/messaging/inbound/dispatch.d.ts.map +1 -0
  364. package/src/messaging/inbound/dispatch.js +193 -0
  365. package/src/messaging/inbound/dispatch.js.map +1 -0
  366. package/src/messaging/inbound/enrich.d.ts +103 -0
  367. package/src/messaging/inbound/enrich.d.ts.map +1 -0
  368. package/src/messaging/inbound/enrich.js +228 -0
  369. package/src/messaging/inbound/enrich.js.map +1 -0
  370. package/src/messaging/inbound/gate-effects.d.ts +24 -0
  371. package/src/messaging/inbound/gate-effects.d.ts.map +1 -0
  372. package/src/messaging/inbound/gate-effects.js +44 -0
  373. package/src/messaging/inbound/gate-effects.js.map +1 -0
  374. package/src/messaging/inbound/gate.d.ts +61 -0
  375. package/src/messaging/inbound/gate.d.ts.map +1 -0
  376. package/src/messaging/inbound/gate.js +234 -0
  377. package/src/messaging/inbound/gate.js.map +1 -0
  378. package/src/messaging/inbound/handler.d.ts +36 -0
  379. package/src/messaging/inbound/handler.d.ts.map +1 -0
  380. package/src/messaging/inbound/handler.js +174 -0
  381. package/src/messaging/inbound/handler.js.map +1 -0
  382. package/src/messaging/inbound/media-resolver.d.ts +33 -0
  383. package/src/messaging/inbound/media-resolver.d.ts.map +1 -0
  384. package/src/messaging/inbound/media-resolver.js +88 -0
  385. package/src/messaging/inbound/media-resolver.js.map +1 -0
  386. package/src/messaging/inbound/mention.d.ts +40 -0
  387. package/src/messaging/inbound/mention.d.ts.map +1 -0
  388. package/src/messaging/inbound/mention.js +82 -0
  389. package/src/messaging/inbound/mention.js.map +1 -0
  390. package/src/messaging/inbound/parse-io.d.ts +51 -0
  391. package/src/messaging/inbound/parse-io.d.ts.map +1 -0
  392. package/src/messaging/inbound/parse-io.js +82 -0
  393. package/src/messaging/inbound/parse-io.js.map +1 -0
  394. package/src/messaging/inbound/parse.d.ts +29 -0
  395. package/src/messaging/inbound/parse.d.ts.map +1 -0
  396. package/src/messaging/inbound/parse.js +107 -0
  397. package/src/messaging/inbound/parse.js.map +1 -0
  398. package/src/messaging/inbound/permission.d.ts +18 -0
  399. package/src/messaging/inbound/permission.d.ts.map +1 -0
  400. package/src/messaging/inbound/permission.js +41 -0
  401. package/src/messaging/inbound/permission.js.map +1 -0
  402. package/src/messaging/inbound/policy.d.ts +95 -0
  403. package/src/messaging/inbound/policy.d.ts.map +1 -0
  404. package/src/messaging/inbound/policy.js +161 -0
  405. package/src/messaging/inbound/policy.js.map +1 -0
  406. package/src/messaging/inbound/reaction-handler.d.ts +62 -0
  407. package/src/messaging/inbound/reaction-handler.d.ts.map +1 -0
  408. package/src/messaging/inbound/reaction-handler.js +221 -0
  409. package/src/messaging/inbound/reaction-handler.js.map +1 -0
  410. package/src/messaging/inbound/user-name-cache.d.ts +83 -0
  411. package/src/messaging/inbound/user-name-cache.d.ts.map +1 -0
  412. package/src/messaging/inbound/user-name-cache.js +242 -0
  413. package/src/messaging/inbound/user-name-cache.js.map +1 -0
  414. package/src/messaging/outbound/actions.d.ts +17 -0
  415. package/src/messaging/outbound/actions.d.ts.map +1 -0
  416. package/src/messaging/outbound/actions.js +310 -0
  417. package/src/messaging/outbound/actions.js.map +1 -0
  418. package/src/messaging/outbound/chat-manage.d.ts +65 -0
  419. package/src/messaging/outbound/chat-manage.d.ts.map +1 -0
  420. package/src/messaging/outbound/chat-manage.js +112 -0
  421. package/src/messaging/outbound/chat-manage.js.map +1 -0
  422. package/src/messaging/outbound/deliver.d.ts +156 -0
  423. package/src/messaging/outbound/deliver.d.ts.map +1 -0
  424. package/src/messaging/outbound/deliver.js +299 -0
  425. package/src/messaging/outbound/deliver.js.map +1 -0
  426. package/src/messaging/outbound/fetch.d.ts +13 -0
  427. package/src/messaging/outbound/fetch.d.ts.map +1 -0
  428. package/src/messaging/outbound/fetch.js +13 -0
  429. package/src/messaging/outbound/fetch.js.map +1 -0
  430. package/src/messaging/outbound/forward.d.ts +27 -0
  431. package/src/messaging/outbound/forward.d.ts.map +1 -0
  432. package/src/messaging/outbound/forward.js +49 -0
  433. package/src/messaging/outbound/forward.js.map +1 -0
  434. package/src/messaging/outbound/media-url-utils.d.ts +30 -0
  435. package/src/messaging/outbound/media-url-utils.d.ts.map +1 -0
  436. package/src/messaging/outbound/media-url-utils.js +131 -0
  437. package/src/messaging/outbound/media-url-utils.js.map +1 -0
  438. package/src/messaging/outbound/media.d.ts +256 -0
  439. package/src/messaging/outbound/media.d.ts.map +1 -0
  440. package/src/messaging/outbound/media.js +749 -0
  441. package/src/messaging/outbound/media.js.map +1 -0
  442. package/src/messaging/outbound/outbound.d.ts +90 -0
  443. package/src/messaging/outbound/outbound.d.ts.map +1 -0
  444. package/src/messaging/outbound/outbound.js +112 -0
  445. package/src/messaging/outbound/outbound.js.map +1 -0
  446. package/src/messaging/outbound/reactions.d.ts +125 -0
  447. package/src/messaging/outbound/reactions.d.ts.map +1 -0
  448. package/src/messaging/outbound/reactions.js +379 -0
  449. package/src/messaging/outbound/reactions.js.map +1 -0
  450. package/src/messaging/outbound/send.d.ts +136 -0
  451. package/src/messaging/outbound/send.d.ts.map +1 -0
  452. package/src/messaging/outbound/send.js +289 -0
  453. package/src/messaging/outbound/send.js.map +1 -0
  454. package/src/messaging/outbound/typing.d.ts +61 -0
  455. package/src/messaging/outbound/typing.d.ts.map +1 -0
  456. package/src/messaging/outbound/typing.js +136 -0
  457. package/src/messaging/outbound/typing.js.map +1 -0
  458. package/src/messaging/shared/message-lookup.d.ts +55 -0
  459. package/src/messaging/shared/message-lookup.d.ts.map +1 -0
  460. package/src/messaging/shared/message-lookup.js +118 -0
  461. package/src/messaging/shared/message-lookup.js.map +1 -0
  462. package/src/messaging/types.d.ts +177 -0
  463. package/src/messaging/types.d.ts.map +1 -0
  464. package/src/messaging/types.js +11 -0
  465. package/src/messaging/types.js.map +1 -0
  466. package/src/tools/auto-auth.d.ts +57 -0
  467. package/src/tools/auto-auth.d.ts.map +1 -0
  468. package/src/tools/auto-auth.js +925 -0
  469. package/src/tools/auto-auth.js.map +1 -0
  470. package/src/tools/helpers.d.ts +220 -0
  471. package/src/tools/helpers.d.ts.map +1 -0
  472. package/src/tools/helpers.js +298 -0
  473. package/src/tools/helpers.js.map +1 -0
  474. package/src/tools/mcp/doc/create.d.ts +13 -0
  475. package/src/tools/mcp/doc/create.d.ts.map +1 -0
  476. package/src/tools/mcp/doc/create.js +45 -0
  477. package/src/tools/mcp/doc/create.js.map +1 -0
  478. package/src/tools/mcp/doc/fetch.d.ts +13 -0
  479. package/src/tools/mcp/doc/fetch.d.ts.map +1 -0
  480. package/src/tools/mcp/doc/fetch.js +37 -0
  481. package/src/tools/mcp/doc/fetch.js.map +1 -0
  482. package/src/tools/mcp/doc/index.d.ts +13 -0
  483. package/src/tools/mcp/doc/index.d.ts.map +1 -0
  484. package/src/tools/mcp/doc/index.js +42 -0
  485. package/src/tools/mcp/doc/index.js.map +1 -0
  486. package/src/tools/mcp/doc/update.d.ts +13 -0
  487. package/src/tools/mcp/doc/update.d.ts.map +1 -0
  488. package/src/tools/mcp/doc/update.js +62 -0
  489. package/src/tools/mcp/doc/update.js.map +1 -0
  490. package/src/tools/mcp/shared.d.ts +58 -0
  491. package/src/tools/mcp/shared.d.ts.map +1 -0
  492. package/src/tools/mcp/shared.js +224 -0
  493. package/src/tools/mcp/shared.js.map +1 -0
  494. package/src/tools/oapi/bitable/app-table-field.d.ts +17 -0
  495. package/src/tools/oapi/bitable/app-table-field.d.ts.map +1 -0
  496. package/src/tools/oapi/bitable/app-table-field.js +224 -0
  497. package/src/tools/oapi/bitable/app-table-field.js.map +1 -0
  498. package/src/tools/oapi/bitable/app-table-record.d.ts +21 -0
  499. package/src/tools/oapi/bitable/app-table-record.d.ts.map +1 -0
  500. package/src/tools/oapi/bitable/app-table-record.js +449 -0
  501. package/src/tools/oapi/bitable/app-table-record.js.map +1 -0
  502. package/src/tools/oapi/bitable/app-table-view.d.ts +18 -0
  503. package/src/tools/oapi/bitable/app-table-view.d.ts.map +1 -0
  504. package/src/tools/oapi/bitable/app-table-view.js +197 -0
  505. package/src/tools/oapi/bitable/app-table-view.js.map +1 -0
  506. package/src/tools/oapi/bitable/app-table.d.ts +20 -0
  507. package/src/tools/oapi/bitable/app-table.d.ts.map +1 -0
  508. package/src/tools/oapi/bitable/app-table.js +249 -0
  509. package/src/tools/oapi/bitable/app-table.js.map +1 -0
  510. package/src/tools/oapi/bitable/app.d.ts +19 -0
  511. package/src/tools/oapi/bitable/app.d.ts.map +1 -0
  512. package/src/tools/oapi/bitable/app.js +188 -0
  513. package/src/tools/oapi/bitable/app.js.map +1 -0
  514. package/src/tools/oapi/bitable/index.d.ts +10 -0
  515. package/src/tools/oapi/bitable/index.d.ts.map +1 -0
  516. package/src/tools/oapi/bitable/index.js +10 -0
  517. package/src/tools/oapi/bitable/index.js.map +1 -0
  518. package/src/tools/oapi/calendar/calendar.d.ts +16 -0
  519. package/src/tools/oapi/calendar/calendar.d.ts.map +1 -0
  520. package/src/tools/oapi/calendar/calendar.js +124 -0
  521. package/src/tools/oapi/calendar/calendar.js.map +1 -0
  522. package/src/tools/oapi/calendar/event-attendee.d.ts +17 -0
  523. package/src/tools/oapi/calendar/event-attendee.d.ts.map +1 -0
  524. package/src/tools/oapi/calendar/event-attendee.js +275 -0
  525. package/src/tools/oapi/calendar/event-attendee.js.map +1 -0
  526. package/src/tools/oapi/calendar/event.d.ts +17 -0
  527. package/src/tools/oapi/calendar/event.d.ts.map +1 -0
  528. package/src/tools/oapi/calendar/event.js +721 -0
  529. package/src/tools/oapi/calendar/event.js.map +1 -0
  530. package/src/tools/oapi/calendar/freebusy.d.ts +14 -0
  531. package/src/tools/oapi/calendar/freebusy.d.ts.map +1 -0
  532. package/src/tools/oapi/calendar/freebusy.js +113 -0
  533. package/src/tools/oapi/calendar/freebusy.js.map +1 -0
  534. package/src/tools/oapi/calendar/index.d.ts +9 -0
  535. package/src/tools/oapi/calendar/index.d.ts.map +1 -0
  536. package/src/tools/oapi/calendar/index.js +9 -0
  537. package/src/tools/oapi/calendar/index.js.map +1 -0
  538. package/src/tools/oapi/chat/chat.d.ts +17 -0
  539. package/src/tools/oapi/chat/chat.d.ts.map +1 -0
  540. package/src/tools/oapi/chat/chat.js +126 -0
  541. package/src/tools/oapi/chat/chat.js.map +1 -0
  542. package/src/tools/oapi/chat/index.d.ts +11 -0
  543. package/src/tools/oapi/chat/index.d.ts.map +1 -0
  544. package/src/tools/oapi/chat/index.js +16 -0
  545. package/src/tools/oapi/chat/index.js.map +1 -0
  546. package/src/tools/oapi/chat/members.d.ts +12 -0
  547. package/src/tools/oapi/chat/members.d.ts.map +1 -0
  548. package/src/tools/oapi/chat/members.js +83 -0
  549. package/src/tools/oapi/chat/members.js.map +1 -0
  550. package/src/tools/oapi/common/get-user.d.ts +13 -0
  551. package/src/tools/oapi/common/get-user.d.ts.map +1 -0
  552. package/src/tools/oapi/common/get-user.js +108 -0
  553. package/src/tools/oapi/common/get-user.js.map +1 -0
  554. package/src/tools/oapi/common/index.d.ts +7 -0
  555. package/src/tools/oapi/common/index.d.ts.map +1 -0
  556. package/src/tools/oapi/common/index.js +7 -0
  557. package/src/tools/oapi/common/index.js.map +1 -0
  558. package/src/tools/oapi/common/search-user.d.ts +12 -0
  559. package/src/tools/oapi/common/search-user.d.ts.map +1 -0
  560. package/src/tools/oapi/common/search-user.js +75 -0
  561. package/src/tools/oapi/common/search-user.js.map +1 -0
  562. package/src/tools/oapi/drive/doc-comments.d.ts +16 -0
  563. package/src/tools/oapi/drive/doc-comments.d.ts.map +1 -0
  564. package/src/tools/oapi/drive/doc-comments.js +288 -0
  565. package/src/tools/oapi/drive/doc-comments.js.map +1 -0
  566. package/src/tools/oapi/drive/doc-media.d.ts +20 -0
  567. package/src/tools/oapi/drive/doc-media.d.ts.map +1 -0
  568. package/src/tools/oapi/drive/doc-media.js +337 -0
  569. package/src/tools/oapi/drive/doc-media.js.map +1 -0
  570. package/src/tools/oapi/drive/file.d.ts +20 -0
  571. package/src/tools/oapi/drive/file.d.ts.map +1 -0
  572. package/src/tools/oapi/drive/file.js +485 -0
  573. package/src/tools/oapi/drive/file.js.map +1 -0
  574. package/src/tools/oapi/drive/index.d.ts +13 -0
  575. package/src/tools/oapi/drive/index.d.ts.map +1 -0
  576. package/src/tools/oapi/drive/index.js +37 -0
  577. package/src/tools/oapi/drive/index.js.map +1 -0
  578. package/src/tools/oapi/helpers.d.ts +174 -0
  579. package/src/tools/oapi/helpers.d.ts.map +1 -0
  580. package/src/tools/oapi/helpers.js +341 -0
  581. package/src/tools/oapi/helpers.js.map +1 -0
  582. package/src/tools/oapi/im/format-messages.d.ts +51 -0
  583. package/src/tools/oapi/im/format-messages.d.ts.map +1 -0
  584. package/src/tools/oapi/im/format-messages.js +166 -0
  585. package/src/tools/oapi/im/format-messages.js.map +1 -0
  586. package/src/tools/oapi/im/index.d.ts +11 -0
  587. package/src/tools/oapi/im/index.d.ts.map +1 -0
  588. package/src/tools/oapi/im/index.js +18 -0
  589. package/src/tools/oapi/im/index.js.map +1 -0
  590. package/src/tools/oapi/im/message-read.d.ts +14 -0
  591. package/src/tools/oapi/im/message-read.d.ts.map +1 -0
  592. package/src/tools/oapi/im/message-read.js +412 -0
  593. package/src/tools/oapi/im/message-read.js.map +1 -0
  594. package/src/tools/oapi/im/message.d.ts +17 -0
  595. package/src/tools/oapi/im/message.d.ts.map +1 -0
  596. package/src/tools/oapi/im/message.js +171 -0
  597. package/src/tools/oapi/im/message.js.map +1 -0
  598. package/src/tools/oapi/im/resource.d.ts +14 -0
  599. package/src/tools/oapi/im/resource.d.ts.map +1 -0
  600. package/src/tools/oapi/im/resource.js +152 -0
  601. package/src/tools/oapi/im/resource.js.map +1 -0
  602. package/src/tools/oapi/im/time-utils.d.ts +47 -0
  603. package/src/tools/oapi/im/time-utils.d.ts.map +1 -0
  604. package/src/tools/oapi/im/time-utils.js +202 -0
  605. package/src/tools/oapi/im/time-utils.js.map +1 -0
  606. package/src/tools/oapi/im/user-name-uat.d.ts +24 -0
  607. package/src/tools/oapi/im/user-name-uat.d.ts.map +1 -0
  608. package/src/tools/oapi/im/user-name-uat.js +128 -0
  609. package/src/tools/oapi/im/user-name-uat.js.map +1 -0
  610. package/src/tools/oapi/index.d.ts +12 -0
  611. package/src/tools/oapi/index.d.ts.map +1 -0
  612. package/src/tools/oapi/index.js +59 -0
  613. package/src/tools/oapi/index.js.map +1 -0
  614. package/src/tools/oapi/sdk-types.d.ts +97 -0
  615. package/src/tools/oapi/sdk-types.d.ts.map +1 -0
  616. package/src/tools/oapi/sdk-types.js +13 -0
  617. package/src/tools/oapi/sdk-types.js.map +1 -0
  618. package/src/tools/oapi/search/doc-search.d.ts +14 -0
  619. package/src/tools/oapi/search/doc-search.d.ts.map +1 -0
  620. package/src/tools/oapi/search/doc-search.js +203 -0
  621. package/src/tools/oapi/search/doc-search.js.map +1 -0
  622. package/src/tools/oapi/search/index.d.ts +13 -0
  623. package/src/tools/oapi/search/index.d.ts.map +1 -0
  624. package/src/tools/oapi/search/index.js +34 -0
  625. package/src/tools/oapi/search/index.js.map +1 -0
  626. package/src/tools/oapi/sheets/index.d.ts +13 -0
  627. package/src/tools/oapi/sheets/index.d.ts.map +1 -0
  628. package/src/tools/oapi/sheets/index.js +32 -0
  629. package/src/tools/oapi/sheets/index.js.map +1 -0
  630. package/src/tools/oapi/sheets/sheet.d.ts +17 -0
  631. package/src/tools/oapi/sheets/sheet.d.ts.map +1 -0
  632. package/src/tools/oapi/sheets/sheet.js +652 -0
  633. package/src/tools/oapi/sheets/sheet.js.map +1 -0
  634. package/src/tools/oapi/task/comment.d.ts +16 -0
  635. package/src/tools/oapi/task/comment.d.ts.map +1 -0
  636. package/src/tools/oapi/task/comment.js +142 -0
  637. package/src/tools/oapi/task/comment.js.map +1 -0
  638. package/src/tools/oapi/task/index.d.ts +9 -0
  639. package/src/tools/oapi/task/index.d.ts.map +1 -0
  640. package/src/tools/oapi/task/index.js +9 -0
  641. package/src/tools/oapi/task/index.js.map +1 -0
  642. package/src/tools/oapi/task/subtask.d.ts +15 -0
  643. package/src/tools/oapi/task/subtask.d.ts.map +1 -0
  644. package/src/tools/oapi/task/subtask.js +164 -0
  645. package/src/tools/oapi/task/subtask.js.map +1 -0
  646. package/src/tools/oapi/task/task.d.ts +17 -0
  647. package/src/tools/oapi/task/task.d.ts.map +1 -0
  648. package/src/tools/oapi/task/task.js +346 -0
  649. package/src/tools/oapi/task/task.js.map +1 -0
  650. package/src/tools/oapi/task/tasklist.d.ts +22 -0
  651. package/src/tools/oapi/task/tasklist.d.ts.map +1 -0
  652. package/src/tools/oapi/task/tasklist.js +323 -0
  653. package/src/tools/oapi/task/tasklist.js.map +1 -0
  654. package/src/tools/oapi/wiki/index.d.ts +13 -0
  655. package/src/tools/oapi/wiki/index.d.ts.map +1 -0
  656. package/src/tools/oapi/wiki/index.js +35 -0
  657. package/src/tools/oapi/wiki/index.js.map +1 -0
  658. package/src/tools/oapi/wiki/space-node.d.ts +18 -0
  659. package/src/tools/oapi/wiki/space-node.d.ts.map +1 -0
  660. package/src/tools/oapi/wiki/space-node.js +253 -0
  661. package/src/tools/oapi/wiki/space-node.js.map +1 -0
  662. package/src/tools/oapi/wiki/space.d.ts +16 -0
  663. package/src/tools/oapi/wiki/space.d.ts.map +1 -0
  664. package/src/tools/oapi/wiki/space.js +132 -0
  665. package/src/tools/oapi/wiki/space.js.map +1 -0
  666. package/src/tools/oauth-batch-auth.d.ts +12 -0
  667. package/src/tools/oauth-batch-auth.d.ts.map +1 -0
  668. package/src/tools/oauth-batch-auth.js +142 -0
  669. package/src/tools/oauth-batch-auth.js.map +1 -0
  670. package/src/tools/oauth-cards.d.ts +27 -0
  671. package/src/tools/oauth-cards.d.ts.map +1 -0
  672. package/src/tools/oauth-cards.js +251 -0
  673. package/src/tools/oauth-cards.js.map +1 -0
  674. package/src/tools/oauth.d.ts +48 -0
  675. package/src/tools/oauth.d.ts.map +1 -0
  676. package/src/tools/oauth.js +619 -0
  677. package/src/tools/oauth.js.map +1 -0
  678. package/src/tools/onboarding-auth.d.ts +28 -0
  679. package/src/tools/onboarding-auth.d.ts.map +1 -0
  680. package/src/tools/onboarding-auth.js +131 -0
  681. package/src/tools/onboarding-auth.js.map +1 -0
  682. package/src/tools/tat/im/index.d.ts +16 -0
  683. package/src/tools/tat/im/index.d.ts.map +1 -0
  684. package/src/tools/tat/im/index.js +19 -0
  685. package/src/tools/tat/im/index.js.map +1 -0
  686. package/src/tools/tat/im/resource.d.ts +16 -0
  687. package/src/tools/tat/im/resource.d.ts.map +1 -0
  688. package/src/tools/tat/im/resource.js +158 -0
  689. package/src/tools/tat/im/resource.js.map +1 -0
@@ -0,0 +1,23 @@
1
+ /** @internal — test-only reset. */
2
+ export declare function _resetShutdownHooks(): void;
3
+ /**
4
+ * Register a cleanup callback to run during graceful shutdown.
5
+ *
6
+ * @param key - Unique identifier for this hook (duplicate keys overwrite).
7
+ * @param cleanup - Async function to execute on shutdown.
8
+ * @returns An unregister function — call it when the resource is
9
+ * released normally (e.g. card streaming completes).
10
+ */
11
+ export declare function registerShutdownHook(key: string, cleanup: () => Promise<void>): () => void;
12
+ /**
13
+ * Drain all registered shutdown hooks (best-effort, bounded by deadline).
14
+ *
15
+ * @param opts - Optional configuration.
16
+ * @param opts.deadlineMs - Maximum time to wait for all hooks (default 5000).
17
+ * @param opts.log - Logger function for progress/error output.
18
+ */
19
+ export declare function drainShutdownHooks(opts?: {
20
+ deadlineMs?: number;
21
+ log?: (...args: unknown[]) => void;
22
+ }): Promise<void>;
23
+ //# sourceMappingURL=shutdown-hooks.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"shutdown-hooks.d.ts","sourceRoot":"","sources":["../../../src/core/shutdown-hooks.ts"],"names":[],"mappings":"AAWA,mCAAmC;AACnC,wBAAgB,mBAAmB,IAAI,IAAI,CAE1C;AAED;;;;;;;GAOG;AACH,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,GAAG,MAAM,IAAI,CAK1F;AAED;;;;;;GAMG;AACH,wBAAsB,kBAAkB,CAAC,IAAI,CAAC,EAAE;IAC9C,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,KAAK,IAAI,CAAC;CACpC,GAAG,OAAO,CAAC,IAAI,CAAC,CA0BhB"}
@@ -0,0 +1,57 @@
1
+ // SPDX-License-Identifier: MIT
2
+ /**
3
+ * Process-level graceful shutdown hook registry.
4
+ *
5
+ * Provides a singleton Map of async cleanup callbacks, drained
6
+ * during graceful shutdown by the channel monitor.
7
+ */
8
+ const hooks = new Map();
9
+ /** @internal — test-only reset. */
10
+ export function _resetShutdownHooks() {
11
+ hooks.clear();
12
+ }
13
+ /**
14
+ * Register a cleanup callback to run during graceful shutdown.
15
+ *
16
+ * @param key - Unique identifier for this hook (duplicate keys overwrite).
17
+ * @param cleanup - Async function to execute on shutdown.
18
+ * @returns An unregister function — call it when the resource is
19
+ * released normally (e.g. card streaming completes).
20
+ */
21
+ export function registerShutdownHook(key, cleanup) {
22
+ hooks.set(key, cleanup);
23
+ return () => {
24
+ hooks.delete(key);
25
+ };
26
+ }
27
+ /**
28
+ * Drain all registered shutdown hooks (best-effort, bounded by deadline).
29
+ *
30
+ * @param opts - Optional configuration.
31
+ * @param opts.deadlineMs - Maximum time to wait for all hooks (default 5000).
32
+ * @param opts.log - Logger function for progress/error output.
33
+ */
34
+ export async function drainShutdownHooks(opts) {
35
+ if (hooks.size === 0)
36
+ return;
37
+ const log = opts?.log;
38
+ const deadline = opts?.deadlineMs ?? 5000;
39
+ log?.(`graceful shutdown: draining ${hooks.size} cleanup hook(s)`);
40
+ const entries = Array.from(hooks.entries());
41
+ hooks.clear();
42
+ const promises = entries.map(async ([key, cleanup]) => {
43
+ try {
44
+ await cleanup();
45
+ log?.(`graceful shutdown: hook "${key}" done`);
46
+ }
47
+ catch (err) {
48
+ log?.(`graceful shutdown: hook "${key}" failed: ${String(err)}`);
49
+ }
50
+ });
51
+ let timer;
52
+ const timeoutPromise = new Promise((resolve) => {
53
+ timer = setTimeout(resolve, deadline);
54
+ });
55
+ await Promise.race([Promise.allSettled(promises).then(() => clearTimeout(timer)), timeoutPromise]);
56
+ }
57
+ //# sourceMappingURL=shutdown-hooks.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"shutdown-hooks.js","sourceRoot":"","sources":["../../../src/core/shutdown-hooks.ts"],"names":[],"mappings":"AAAA,+BAA+B;AAE/B;;;;;GAKG;AAEH,MAAM,KAAK,GAAG,IAAI,GAAG,EAA+B,CAAC;AAErD,mCAAmC;AACnC,MAAM,UAAU,mBAAmB;IACjC,KAAK,CAAC,KAAK,EAAE,CAAC;AAChB,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,UAAU,oBAAoB,CAAC,GAAW,EAAE,OAA4B;IAC5E,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;IACxB,OAAO,GAAG,EAAE;QACV,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;IACpB,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;GAMG;AACH,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,IAGxC;IACC,IAAI,KAAK,CAAC,IAAI,KAAK,CAAC;QAAE,OAAO;IAE7B,MAAM,GAAG,GAAG,IAAI,EAAE,GAAG,CAAC;IACtB,MAAM,QAAQ,GAAG,IAAI,EAAE,UAAU,IAAI,IAAI,CAAC;IAE1C,GAAG,EAAE,CAAC,+BAA+B,KAAK,CAAC,IAAI,kBAAkB,CAAC,CAAC;IAEnE,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;IAC5C,KAAK,CAAC,KAAK,EAAE,CAAC;IAEd,MAAM,QAAQ,GAAG,OAAO,CAAC,GAAG,CAAC,KAAK,EAAE,CAAC,GAAG,EAAE,OAAO,CAAC,EAAE,EAAE;QACpD,IAAI,CAAC;YACH,MAAM,OAAO,EAAE,CAAC;YAChB,GAAG,EAAE,CAAC,4BAA4B,GAAG,QAAQ,CAAC,CAAC;QACjD,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,GAAG,EAAE,CAAC,4BAA4B,GAAG,aAAa,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;QACnE,CAAC;IACH,CAAC,CAAC,CAAC;IAEH,IAAI,KAAgD,CAAC;IACrD,MAAM,cAAc,GAAG,IAAI,OAAO,CAAO,CAAC,OAAO,EAAE,EAAE;QACnD,KAAK,GAAG,UAAU,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;IACxC,CAAC,CAAC,CAAC;IAEH,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC,OAAO,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,EAAE,cAAc,CAAC,CAAC,CAAC;AACrG,CAAC"}
@@ -0,0 +1,50 @@
1
+ /**
2
+ * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates
3
+ * SPDX-License-Identifier: MIT
4
+ *
5
+ * Feishu target ID parsing and formatting utilities.
6
+ *
7
+ * Feishu uses several namespaced identifier prefixes:
8
+ * - `oc_*` -- chat (group / DM) IDs
9
+ * - `ou_*` -- open user IDs
10
+ * - plain alphanumeric strings -- user IDs from the tenant directory
11
+ *
12
+ * This module provides helpers to detect, normalise, and format these IDs
13
+ * for both internal routing and outbound Feishu API calls.
14
+ */
15
+ import type { FeishuIdType } from './types';
16
+ /**
17
+ * Detect the Feishu ID type from a raw identifier string.
18
+ *
19
+ * Returns `null` when the string does not match any known pattern.
20
+ */
21
+ export declare function detectIdType(id: string): FeishuIdType | null;
22
+ /**
23
+ * Strip OpenClaw routing prefixes (`chat:`, `user:`, `open_id:`) from a
24
+ * raw target string, returning the bare Feishu identifier.
25
+ *
26
+ * Returns `null` when the input is empty or falsy.
27
+ */
28
+ export declare function normalizeFeishuTarget(raw: string): string | null;
29
+ /**
30
+ * Add the appropriate OpenClaw routing prefix to a bare Feishu identifier.
31
+ *
32
+ * When `type` is omitted, the prefix is inferred via `detectIdType`.
33
+ */
34
+ export declare function formatFeishuTarget(id: string, type?: FeishuIdType): string;
35
+ /**
36
+ * Determine the `receive_id_type` query parameter for the Feishu send-message
37
+ * API based on the target identifier.
38
+ */
39
+ export declare function resolveReceiveIdType(id: string): 'chat_id' | 'open_id' | 'user_id';
40
+ /**
41
+ * 规范化 message_id,去除合成后缀(如 `om_xxx:auth-complete` → `om_xxx`)。
42
+ */
43
+ export declare function normalizeMessageId(messageId: string): string;
44
+ export declare function normalizeMessageId(messageId: string | undefined): string | undefined;
45
+ /**
46
+ * Return `true` when a raw string looks like it could be a Feishu target
47
+ * (either an OpenClaw-tagged form or a native prefix).
48
+ */
49
+ export declare function looksLikeFeishuId(raw: string): boolean;
50
+ //# sourceMappingURL=targets.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"targets.d.ts","sourceRoot":"","sources":["../../../src/core/targets.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAqB5C;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,EAAE,EAAE,MAAM,GAAG,YAAY,GAAG,IAAI,CAO5D;AAMD;;;;;GAKG;AACH,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAiBhE;AAMD;;;;GAIG;AACH,wBAAgB,kBAAkB,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,YAAY,GAAG,MAAM,CAK1E;AAMD;;;GAGG;AACH,wBAAgB,oBAAoB,CAAC,EAAE,EAAE,MAAM,GAAG,SAAS,GAAG,SAAS,GAAG,SAAS,CAKlF;AAMD;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAAC;AAC9D,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,CAAC;AAYtF;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAStD"}
@@ -0,0 +1,128 @@
1
+ /**
2
+ * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates
3
+ * SPDX-License-Identifier: MIT
4
+ *
5
+ * Feishu target ID parsing and formatting utilities.
6
+ *
7
+ * Feishu uses several namespaced identifier prefixes:
8
+ * - `oc_*` -- chat (group / DM) IDs
9
+ * - `ou_*` -- open user IDs
10
+ * - plain alphanumeric strings -- user IDs from the tenant directory
11
+ *
12
+ * This module provides helpers to detect, normalise, and format these IDs
13
+ * for both internal routing and outbound Feishu API calls.
14
+ */
15
+ // ---------------------------------------------------------------------------
16
+ // Known prefix patterns
17
+ // ---------------------------------------------------------------------------
18
+ const CHAT_PREFIX = 'oc_';
19
+ const OPEN_ID_PREFIX = 'ou_';
20
+ // Canonical routing prefixes used inside OpenClaw (not Feishu-native).
21
+ const TAG_CHAT = 'chat:';
22
+ const TAG_USER = 'user:';
23
+ const TAG_OPEN_ID = 'open_id:';
24
+ // Feishu channel prefix (used by SDK for some routing scenarios).
25
+ const TAG_FEISHU = 'feishu:';
26
+ // ---------------------------------------------------------------------------
27
+ // Detection
28
+ // ---------------------------------------------------------------------------
29
+ /**
30
+ * Detect the Feishu ID type from a raw identifier string.
31
+ *
32
+ * Returns `null` when the string does not match any known pattern.
33
+ */
34
+ export function detectIdType(id) {
35
+ if (!id)
36
+ return null;
37
+ if (id.startsWith(CHAT_PREFIX))
38
+ return 'chat_id';
39
+ if (id.startsWith(OPEN_ID_PREFIX))
40
+ return 'open_id';
41
+ // Plain alphanumeric strings (no prefix) are treated as tenant user IDs.
42
+ if (/^[a-zA-Z0-9]+$/.test(id))
43
+ return 'user_id';
44
+ return null;
45
+ }
46
+ // ---------------------------------------------------------------------------
47
+ // Normalisation
48
+ // ---------------------------------------------------------------------------
49
+ /**
50
+ * Strip OpenClaw routing prefixes (`chat:`, `user:`, `open_id:`) from a
51
+ * raw target string, returning the bare Feishu identifier.
52
+ *
53
+ * Returns `null` when the input is empty or falsy.
54
+ */
55
+ export function normalizeFeishuTarget(raw) {
56
+ if (!raw)
57
+ return null;
58
+ const trimmed = raw.trim();
59
+ if (!trimmed)
60
+ return null;
61
+ // Handle Feishu channel prefix (e.g., "feishu:ou_xxx" -> "ou_xxx")
62
+ if (trimmed.startsWith(TAG_FEISHU)) {
63
+ const inner = trimmed.slice(TAG_FEISHU.length).trim();
64
+ if (inner)
65
+ return inner;
66
+ }
67
+ if (trimmed.startsWith(TAG_CHAT))
68
+ return trimmed.slice(TAG_CHAT.length);
69
+ if (trimmed.startsWith(TAG_USER))
70
+ return trimmed.slice(TAG_USER.length);
71
+ if (trimmed.startsWith(TAG_OPEN_ID))
72
+ return trimmed.slice(TAG_OPEN_ID.length);
73
+ return trimmed;
74
+ }
75
+ // ---------------------------------------------------------------------------
76
+ // Formatting
77
+ // ---------------------------------------------------------------------------
78
+ /**
79
+ * Add the appropriate OpenClaw routing prefix to a bare Feishu identifier.
80
+ *
81
+ * When `type` is omitted, the prefix is inferred via `detectIdType`.
82
+ */
83
+ export function formatFeishuTarget(id, type) {
84
+ const resolved = type ?? detectIdType(id);
85
+ if (resolved === 'chat_id')
86
+ return `${TAG_CHAT}${id}`;
87
+ return `${TAG_USER}${id}`;
88
+ }
89
+ // ---------------------------------------------------------------------------
90
+ // API receive-ID resolution
91
+ // ---------------------------------------------------------------------------
92
+ /**
93
+ * Determine the `receive_id_type` query parameter for the Feishu send-message
94
+ * API based on the target identifier.
95
+ */
96
+ export function resolveReceiveIdType(id) {
97
+ if (id.startsWith(CHAT_PREFIX))
98
+ return 'chat_id';
99
+ if (id.startsWith(OPEN_ID_PREFIX))
100
+ return 'open_id';
101
+ // Default to open_id for any other pattern (safer for outbound API calls).
102
+ return 'open_id';
103
+ }
104
+ export function normalizeMessageId(messageId) {
105
+ if (!messageId)
106
+ return undefined;
107
+ const colonIndex = messageId.indexOf(':');
108
+ if (colonIndex >= 0)
109
+ return messageId.slice(0, colonIndex);
110
+ return messageId;
111
+ }
112
+ // ---------------------------------------------------------------------------
113
+ // Quick predicate
114
+ // ---------------------------------------------------------------------------
115
+ /**
116
+ * Return `true` when a raw string looks like it could be a Feishu target
117
+ * (either an OpenClaw-tagged form or a native prefix).
118
+ */
119
+ export function looksLikeFeishuId(raw) {
120
+ if (!raw)
121
+ return false;
122
+ return (raw.startsWith(TAG_CHAT) ||
123
+ raw.startsWith(TAG_USER) ||
124
+ raw.startsWith(TAG_OPEN_ID) ||
125
+ raw.startsWith(CHAT_PREFIX) ||
126
+ raw.startsWith(OPEN_ID_PREFIX));
127
+ }
128
+ //# sourceMappingURL=targets.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"targets.js","sourceRoot":"","sources":["../../../src/core/targets.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAIH,8EAA8E;AAC9E,wBAAwB;AACxB,8EAA8E;AAE9E,MAAM,WAAW,GAAG,KAAK,CAAC;AAC1B,MAAM,cAAc,GAAG,KAAK,CAAC;AAE7B,uEAAuE;AACvE,MAAM,QAAQ,GAAG,OAAO,CAAC;AACzB,MAAM,QAAQ,GAAG,OAAO,CAAC;AACzB,MAAM,WAAW,GAAG,UAAU,CAAC;AAE/B,kEAAkE;AAClE,MAAM,UAAU,GAAG,SAAS,CAAC;AAE7B,8EAA8E;AAC9E,YAAY;AACZ,8EAA8E;AAE9E;;;;GAIG;AACH,MAAM,UAAU,YAAY,CAAC,EAAU;IACrC,IAAI,CAAC,EAAE;QAAE,OAAO,IAAI,CAAC;IACrB,IAAI,EAAE,CAAC,UAAU,CAAC,WAAW,CAAC;QAAE,OAAO,SAAS,CAAC;IACjD,IAAI,EAAE,CAAC,UAAU,CAAC,cAAc,CAAC;QAAE,OAAO,SAAS,CAAC;IACpD,yEAAyE;IACzE,IAAI,gBAAgB,CAAC,IAAI,CAAC,EAAE,CAAC;QAAE,OAAO,SAAS,CAAC;IAChD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,8EAA8E;AAC9E,gBAAgB;AAChB,8EAA8E;AAE9E;;;;;GAKG;AACH,MAAM,UAAU,qBAAqB,CAAC,GAAW;IAC/C,IAAI,CAAC,GAAG;QAAE,OAAO,IAAI,CAAC;IAEtB,MAAM,OAAO,GAAG,GAAG,CAAC,IAAI,EAAE,CAAC;IAC3B,IAAI,CAAC,OAAO;QAAE,OAAO,IAAI,CAAC;IAE1B,mEAAmE;IACnE,IAAI,OAAO,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QACnC,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,CAAC;QACtD,IAAI,KAAK;YAAE,OAAO,KAAK,CAAC;IAC1B,CAAC;IAED,IAAI,OAAO,CAAC,UAAU,CAAC,QAAQ,CAAC;QAAE,OAAO,OAAO,CAAC,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC;IACxE,IAAI,OAAO,CAAC,UAAU,CAAC,QAAQ,CAAC;QAAE,OAAO,OAAO,CAAC,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC;IACxE,IAAI,OAAO,CAAC,UAAU,CAAC,WAAW,CAAC;QAAE,OAAO,OAAO,CAAC,KAAK,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC;IAE9E,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,8EAA8E;AAC9E,aAAa;AACb,8EAA8E;AAE9E;;;;GAIG;AACH,MAAM,UAAU,kBAAkB,CAAC,EAAU,EAAE,IAAmB;IAChE,MAAM,QAAQ,GAAG,IAAI,IAAI,YAAY,CAAC,EAAE,CAAC,CAAC;IAE1C,IAAI,QAAQ,KAAK,SAAS;QAAE,OAAO,GAAG,QAAQ,GAAG,EAAE,EAAE,CAAC;IACtD,OAAO,GAAG,QAAQ,GAAG,EAAE,EAAE,CAAC;AAC5B,CAAC;AAED,8EAA8E;AAC9E,4BAA4B;AAC5B,8EAA8E;AAE9E;;;GAGG;AACH,MAAM,UAAU,oBAAoB,CAAC,EAAU;IAC7C,IAAI,EAAE,CAAC,UAAU,CAAC,WAAW,CAAC;QAAE,OAAO,SAAS,CAAC;IACjD,IAAI,EAAE,CAAC,UAAU,CAAC,cAAc,CAAC;QAAE,OAAO,SAAS,CAAC;IACpD,2EAA2E;IAC3E,OAAO,SAAS,CAAC;AACnB,CAAC;AAWD,MAAM,UAAU,kBAAkB,CAAC,SAA6B;IAC9D,IAAI,CAAC,SAAS;QAAE,OAAO,SAAS,CAAC;IACjC,MAAM,UAAU,GAAG,SAAS,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAC1C,IAAI,UAAU,IAAI,CAAC;QAAE,OAAO,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC;IAC3D,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,8EAA8E;AAC9E,kBAAkB;AAClB,8EAA8E;AAE9E;;;GAGG;AACH,MAAM,UAAU,iBAAiB,CAAC,GAAW;IAC3C,IAAI,CAAC,GAAG;QAAE,OAAO,KAAK,CAAC;IACvB,OAAO,CACL,GAAG,CAAC,UAAU,CAAC,QAAQ,CAAC;QACxB,GAAG,CAAC,UAAU,CAAC,QAAQ,CAAC;QACxB,GAAG,CAAC,UAAU,CAAC,WAAW,CAAC;QAC3B,GAAG,CAAC,UAAU,CAAC,WAAW,CAAC;QAC3B,GAAG,CAAC,UAAU,CAAC,cAAc,CAAC,CAC/B,CAAC;AACJ,CAAC"}
@@ -0,0 +1,55 @@
1
+ /**
2
+ * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates
3
+ * SPDX-License-Identifier: MIT
4
+ *
5
+ * UAT (User Access Token) persistent storage with cross-platform support.
6
+ *
7
+ * Stores OAuth token data using OS-native credential services so that tokens
8
+ * survive process restarts without introducing plain-text local files.
9
+ *
10
+ * Platform backends:
11
+ * macOS – Keychain Access via `security` CLI
12
+ * Linux – AES-256-GCM encrypted files (XDG_DATA_HOME)
13
+ * Windows – AES-256-GCM encrypted files (%LOCALAPPDATA%)
14
+ *
15
+ * Storage layout:
16
+ * Service = "openclaw-feishu-uat"
17
+ * Account = "{appId}:{userOpenId}"
18
+ * Password = JSON-serialised StoredUAToken
19
+ */
20
+ export interface StoredUAToken {
21
+ userOpenId: string;
22
+ appId: string;
23
+ accessToken: string;
24
+ refreshToken: string;
25
+ expiresAt: number;
26
+ refreshExpiresAt: number;
27
+ scope: string;
28
+ grantedAt: number;
29
+ }
30
+ /** Mask a token for safe logging: only the last 4 chars are visible. */
31
+ export declare function maskToken(token: string): string;
32
+ /**
33
+ * Read the stored UAT for a given (appId, userOpenId) pair.
34
+ * Returns `null` when no entry exists or the payload is unparseable.
35
+ */
36
+ export declare function getStoredToken(appId: string, userOpenId: string): Promise<StoredUAToken | null>;
37
+ /**
38
+ * Persist a UAT using the platform credential store.
39
+ *
40
+ * Overwrites any existing entry for the same (appId, userOpenId).
41
+ */
42
+ export declare function setStoredToken(token: StoredUAToken): Promise<void>;
43
+ /**
44
+ * Remove a stored UAT from the credential store.
45
+ */
46
+ export declare function removeStoredToken(appId: string, userOpenId: string): Promise<void>;
47
+ /**
48
+ * Determine the freshness of a stored token.
49
+ *
50
+ * - `"valid"` – access_token is still good (expires > 5 min from now)
51
+ * - `"needs_refresh"` – access_token expired/expiring but refresh_token is valid
52
+ * - `"expired"` – both tokens are expired; re-authorization required
53
+ */
54
+ export declare function tokenStatus(token: StoredUAToken): 'valid' | 'needs_refresh' | 'expired';
55
+ //# sourceMappingURL=token-store.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"token-store.d.ts","sourceRoot":"","sources":["../../../src/core/token-store.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;GAkBG;AAkBH,MAAM,WAAW,aAAa;IAC5B,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,MAAM,CAAC;IACrB,SAAS,EAAE,MAAM,CAAC;IAClB,gBAAgB,EAAE,MAAM,CAAC;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;CACnB;AAmBD,wEAAwE;AACxE,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAG/C;AAqPD;;;GAGG;AACH,wBAAsB,cAAc,CAAC,KAAK,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,GAAG,IAAI,CAAC,CAQrG;AAED;;;;GAIG;AACH,wBAAsB,cAAc,CAAC,KAAK,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAKxE;AAED;;GAEG;AACH,wBAAsB,iBAAiB,CAAC,KAAK,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAGxF;AAMD;;;;;;GAMG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,aAAa,GAAG,OAAO,GAAG,eAAe,GAAG,SAAS,CASvF"}
@@ -0,0 +1,315 @@
1
+ /**
2
+ * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates
3
+ * SPDX-License-Identifier: MIT
4
+ *
5
+ * UAT (User Access Token) persistent storage with cross-platform support.
6
+ *
7
+ * Stores OAuth token data using OS-native credential services so that tokens
8
+ * survive process restarts without introducing plain-text local files.
9
+ *
10
+ * Platform backends:
11
+ * macOS – Keychain Access via `security` CLI
12
+ * Linux – AES-256-GCM encrypted files (XDG_DATA_HOME)
13
+ * Windows – AES-256-GCM encrypted files (%LOCALAPPDATA%)
14
+ *
15
+ * Storage layout:
16
+ * Service = "openclaw-feishu-uat"
17
+ * Account = "{appId}:{userOpenId}"
18
+ * Password = JSON-serialised StoredUAToken
19
+ */
20
+ import { execFile as execFileCb } from 'node:child_process';
21
+ import { promisify } from 'node:util';
22
+ import { mkdir, unlink, readFile, writeFile, chmod } from 'node:fs/promises';
23
+ import { join } from 'node:path';
24
+ import { homedir } from 'node:os';
25
+ import { randomBytes, createCipheriv, createDecipheriv } from 'node:crypto';
26
+ import { larkLogger } from './lark-logger';
27
+ const log = larkLogger('core/token-store');
28
+ const execFile = promisify(execFileCb);
29
+ // ---------------------------------------------------------------------------
30
+ // Constants
31
+ // ---------------------------------------------------------------------------
32
+ const KEYCHAIN_SERVICE = 'openclaw-feishu-uat';
33
+ /** Refresh proactively when access_token expires within this window. */
34
+ const REFRESH_AHEAD_MS = 5 * 60 * 1000; // 5 minutes
35
+ // ---------------------------------------------------------------------------
36
+ // Helpers
37
+ // ---------------------------------------------------------------------------
38
+ function accountKey(appId, userOpenId) {
39
+ return `${appId}:${userOpenId}`;
40
+ }
41
+ /** Mask a token for safe logging: only the last 4 chars are visible. */
42
+ export function maskToken(token) {
43
+ if (token.length <= 8)
44
+ return '****';
45
+ return `****${token.slice(-4)}`;
46
+ }
47
+ // ---------------------------------------------------------------------------
48
+ // macOS backend – Keychain Access via `security` CLI
49
+ // ---------------------------------------------------------------------------
50
+ const darwinBackend = {
51
+ async get(service, account) {
52
+ try {
53
+ const { stdout } = await execFile('security', ['find-generic-password', '-s', service, '-a', account, '-w']);
54
+ return stdout.trim() || null;
55
+ }
56
+ catch {
57
+ return null;
58
+ }
59
+ },
60
+ async set(service, account, data) {
61
+ // Delete first – `add-generic-password` fails if the item already exists.
62
+ try {
63
+ await execFile('security', ['delete-generic-password', '-s', service, '-a', account]);
64
+ }
65
+ catch {
66
+ // Not found – fine.
67
+ }
68
+ await execFile('security', ['add-generic-password', '-s', service, '-a', account, '-w', data]);
69
+ },
70
+ async remove(service, account) {
71
+ try {
72
+ await execFile('security', ['delete-generic-password', '-s', service, '-a', account]);
73
+ }
74
+ catch {
75
+ // Already absent – fine.
76
+ }
77
+ },
78
+ };
79
+ // ---------------------------------------------------------------------------
80
+ // Linux backend – AES-256-GCM encrypted files (XDG Base Directory)
81
+ //
82
+ // Headless Linux servers typically lack D-Bus / GNOME Keyring, so we store
83
+ // tokens as AES-256-GCM encrypted files instead of using `secret-tool`.
84
+ //
85
+ // Storage path: ${XDG_DATA_HOME:-~/.local/share}/openclaw-feishu-uat/
86
+ // ---------------------------------------------------------------------------
87
+ const LINUX_UAT_DIR = join(process.env.XDG_DATA_HOME || join(homedir(), '.local', 'share'), 'openclaw-feishu-uat');
88
+ const MASTER_KEY_PATH = join(LINUX_UAT_DIR, 'master.key');
89
+ const MASTER_KEY_BYTES = 32; // AES-256
90
+ const IV_BYTES = 12; // GCM recommended
91
+ const TAG_BYTES = 16; // GCM auth tag
92
+ /** Convert account key to a filesystem-safe filename. */
93
+ function linuxSafeFileName(account) {
94
+ return account.replace(/[^a-zA-Z0-9._-]/g, '_') + '.enc';
95
+ }
96
+ /** Ensure the credentials directory exists with mode 0700. */
97
+ async function ensureLinuxCredDir() {
98
+ await mkdir(LINUX_UAT_DIR, { recursive: true, mode: 0o700 });
99
+ }
100
+ /**
101
+ * Load or create the 32-byte master key.
102
+ *
103
+ * On first run, generates a random key and writes it to disk (mode 0600).
104
+ * On subsequent runs, reads the existing key file.
105
+ */
106
+ async function getMasterKey() {
107
+ try {
108
+ const key = await readFile(MASTER_KEY_PATH);
109
+ if (key.length === MASTER_KEY_BYTES)
110
+ return key;
111
+ log.warn('master key has unexpected length, regenerating');
112
+ }
113
+ catch (err) {
114
+ if (!(err instanceof Error) || err.code !== 'ENOENT') {
115
+ log.warn(`failed to read master key: ${err instanceof Error ? err.message : err}`);
116
+ }
117
+ }
118
+ await ensureLinuxCredDir();
119
+ const key = randomBytes(MASTER_KEY_BYTES);
120
+ await writeFile(MASTER_KEY_PATH, key, { mode: 0o600 });
121
+ await chmod(MASTER_KEY_PATH, 0o600);
122
+ log.info('generated new master key for encrypted file storage');
123
+ return key;
124
+ }
125
+ /** AES-256-GCM encrypt. Returns [12-byte IV][16-byte tag][ciphertext]. */
126
+ function encryptData(plaintext, key) {
127
+ const iv = randomBytes(IV_BYTES);
128
+ const cipher = createCipheriv('aes-256-gcm', key, iv);
129
+ const enc = Buffer.concat([cipher.update(plaintext, 'utf8'), cipher.final()]);
130
+ return Buffer.concat([iv, cipher.getAuthTag(), enc]);
131
+ }
132
+ /** AES-256-GCM decrypt. Returns plaintext or `null` on failure. */
133
+ function decryptData(data, key) {
134
+ if (data.length < IV_BYTES + TAG_BYTES)
135
+ return null;
136
+ try {
137
+ const iv = data.subarray(0, IV_BYTES);
138
+ const tag = data.subarray(IV_BYTES, IV_BYTES + TAG_BYTES);
139
+ const enc = data.subarray(IV_BYTES + TAG_BYTES);
140
+ const decipher = createDecipheriv('aes-256-gcm', key, iv);
141
+ decipher.setAuthTag(tag);
142
+ return Buffer.concat([decipher.update(enc), decipher.final()]).toString('utf8');
143
+ }
144
+ catch {
145
+ return null;
146
+ }
147
+ }
148
+ const linuxBackend = {
149
+ async get(_service, account) {
150
+ try {
151
+ const key = await getMasterKey();
152
+ const data = await readFile(join(LINUX_UAT_DIR, linuxSafeFileName(account)));
153
+ return decryptData(data, key);
154
+ }
155
+ catch {
156
+ return null;
157
+ }
158
+ },
159
+ async set(_service, account, data) {
160
+ const key = await getMasterKey();
161
+ await ensureLinuxCredDir();
162
+ const filePath = join(LINUX_UAT_DIR, linuxSafeFileName(account));
163
+ const encrypted = encryptData(data, key);
164
+ await writeFile(filePath, encrypted, { mode: 0o600 });
165
+ await chmod(filePath, 0o600);
166
+ },
167
+ async remove(_service, account) {
168
+ try {
169
+ await unlink(join(LINUX_UAT_DIR, linuxSafeFileName(account)));
170
+ }
171
+ catch {
172
+ // Already absent – fine.
173
+ }
174
+ },
175
+ };
176
+ // ---------------------------------------------------------------------------
177
+ // Windows backend – AES-256-GCM encrypted files
178
+ //
179
+ // Replaces the previous DPAPI-via-PowerShell approach which was unreliable
180
+ // (PowerShell cold-start latency, execution policy restrictions, cmd.exe
181
+ // command-line length limits, and unavailability in containers).
182
+ //
183
+ // Uses the same AES-256-GCM scheme as the Linux backend with its own
184
+ // independent storage directory and master key.
185
+ //
186
+ // Storage path: %LOCALAPPDATA%\openclaw-feishu-uat\
187
+ // ---------------------------------------------------------------------------
188
+ const WIN32_UAT_DIR = join(process.env.LOCALAPPDATA ?? join(process.env.USERPROFILE ?? homedir(), 'AppData', 'Local'), KEYCHAIN_SERVICE);
189
+ const WIN32_MASTER_KEY_PATH = join(WIN32_UAT_DIR, 'master.key');
190
+ /** Convert account key to a filesystem-safe filename (whitelist approach). */
191
+ function win32SafeFileName(account) {
192
+ return account.replace(/[^a-zA-Z0-9._-]/g, '_') + '.enc';
193
+ }
194
+ async function ensureWin32CredDir() {
195
+ await mkdir(WIN32_UAT_DIR, { recursive: true });
196
+ }
197
+ async function getWin32MasterKey() {
198
+ try {
199
+ const key = await readFile(WIN32_MASTER_KEY_PATH);
200
+ if (key.length === MASTER_KEY_BYTES)
201
+ return key;
202
+ log.warn('win32 master key has unexpected length, regenerating');
203
+ }
204
+ catch (err) {
205
+ if (!(err instanceof Error) || err.code !== 'ENOENT') {
206
+ log.warn(`failed to read win32 master key: ${err instanceof Error ? err.message : err}`);
207
+ }
208
+ }
209
+ await ensureWin32CredDir();
210
+ const key = randomBytes(MASTER_KEY_BYTES);
211
+ await writeFile(WIN32_MASTER_KEY_PATH, key);
212
+ log.info('generated new master key for win32 encrypted file storage');
213
+ return key;
214
+ }
215
+ const win32Backend = {
216
+ async get(_service, account) {
217
+ try {
218
+ const key = await getWin32MasterKey();
219
+ const data = await readFile(join(WIN32_UAT_DIR, win32SafeFileName(account)));
220
+ return decryptData(data, key);
221
+ }
222
+ catch {
223
+ return null;
224
+ }
225
+ },
226
+ async set(_service, account, data) {
227
+ const key = await getWin32MasterKey();
228
+ await ensureWin32CredDir();
229
+ const filePath = join(WIN32_UAT_DIR, win32SafeFileName(account));
230
+ const encrypted = encryptData(data, key);
231
+ await writeFile(filePath, encrypted);
232
+ },
233
+ async remove(_service, account) {
234
+ try {
235
+ await unlink(join(WIN32_UAT_DIR, win32SafeFileName(account)));
236
+ }
237
+ catch {
238
+ // Already absent – fine.
239
+ }
240
+ },
241
+ };
242
+ // ---------------------------------------------------------------------------
243
+ // Platform selection
244
+ // ---------------------------------------------------------------------------
245
+ function createBackend() {
246
+ switch (process.platform) {
247
+ case 'darwin':
248
+ return darwinBackend;
249
+ case 'linux':
250
+ return linuxBackend;
251
+ case 'win32':
252
+ return win32Backend;
253
+ default:
254
+ log.warn(`unsupported platform "${process.platform}", falling back to macOS backend`);
255
+ return darwinBackend;
256
+ }
257
+ }
258
+ const backend = createBackend();
259
+ // ---------------------------------------------------------------------------
260
+ // Public API – Credential operations
261
+ // ---------------------------------------------------------------------------
262
+ /**
263
+ * Read the stored UAT for a given (appId, userOpenId) pair.
264
+ * Returns `null` when no entry exists or the payload is unparseable.
265
+ */
266
+ export async function getStoredToken(appId, userOpenId) {
267
+ try {
268
+ const json = await backend.get(KEYCHAIN_SERVICE, accountKey(appId, userOpenId));
269
+ if (!json)
270
+ return null;
271
+ return JSON.parse(json);
272
+ }
273
+ catch {
274
+ return null;
275
+ }
276
+ }
277
+ /**
278
+ * Persist a UAT using the platform credential store.
279
+ *
280
+ * Overwrites any existing entry for the same (appId, userOpenId).
281
+ */
282
+ export async function setStoredToken(token) {
283
+ const key = accountKey(token.appId, token.userOpenId);
284
+ const payload = JSON.stringify(token);
285
+ await backend.set(KEYCHAIN_SERVICE, key, payload);
286
+ log.info(`saved UAT for ${token.userOpenId} (at:${maskToken(token.accessToken)})`);
287
+ }
288
+ /**
289
+ * Remove a stored UAT from the credential store.
290
+ */
291
+ export async function removeStoredToken(appId, userOpenId) {
292
+ await backend.remove(KEYCHAIN_SERVICE, accountKey(appId, userOpenId));
293
+ log.info(`removed UAT for ${userOpenId}`);
294
+ }
295
+ // ---------------------------------------------------------------------------
296
+ // Token validity check
297
+ // ---------------------------------------------------------------------------
298
+ /**
299
+ * Determine the freshness of a stored token.
300
+ *
301
+ * - `"valid"` – access_token is still good (expires > 5 min from now)
302
+ * - `"needs_refresh"` – access_token expired/expiring but refresh_token is valid
303
+ * - `"expired"` – both tokens are expired; re-authorization required
304
+ */
305
+ export function tokenStatus(token) {
306
+ const now = Date.now();
307
+ if (now < token.expiresAt - REFRESH_AHEAD_MS) {
308
+ return 'valid';
309
+ }
310
+ if (now < token.refreshExpiresAt) {
311
+ return 'needs_refresh';
312
+ }
313
+ return 'expired';
314
+ }
315
+ //# sourceMappingURL=token-store.js.map