digital-tools 2.1.3 → 2.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (294) hide show
  1. package/CHANGELOG.md +9 -0
  2. package/README.md +2 -0
  3. package/dist/client.d.ts +109 -0
  4. package/dist/client.d.ts.map +1 -0
  5. package/dist/client.js +69 -0
  6. package/dist/client.js.map +1 -0
  7. package/dist/define.d.ts +2 -2
  8. package/dist/define.d.ts.map +1 -1
  9. package/dist/define.js +21 -11
  10. package/dist/define.js.map +1 -1
  11. package/dist/function-ref.d.ts +229 -0
  12. package/dist/function-ref.d.ts.map +1 -0
  13. package/dist/function-ref.js +28 -0
  14. package/dist/function-ref.js.map +1 -0
  15. package/dist/function-sugar.d.ts +57 -0
  16. package/dist/function-sugar.d.ts.map +1 -0
  17. package/dist/function-sugar.js +79 -0
  18. package/dist/function-sugar.js.map +1 -0
  19. package/dist/index.d.ts +10 -3
  20. package/dist/index.d.ts.map +1 -1
  21. package/dist/index.js +24 -4
  22. package/dist/index.js.map +1 -1
  23. package/dist/providers/analytics/mixpanel.d.ts.map +1 -1
  24. package/dist/providers/analytics/mixpanel.js +21 -18
  25. package/dist/providers/analytics/mixpanel.js.map +1 -1
  26. package/dist/providers/calendar/cal-com.d.ts.map +1 -1
  27. package/dist/providers/calendar/cal-com.js +10 -10
  28. package/dist/providers/calendar/cal-com.js.map +1 -1
  29. package/dist/providers/calendar/google-calendar.d.ts.map +1 -1
  30. package/dist/providers/calendar/google-calendar.js +4 -4
  31. package/dist/providers/calendar/google-calendar.js.map +1 -1
  32. package/dist/providers/crm/hubspot.d.ts.map +1 -1
  33. package/dist/providers/crm/hubspot.js +107 -85
  34. package/dist/providers/crm/hubspot.js.map +1 -1
  35. package/dist/providers/development/github.d.ts.map +1 -1
  36. package/dist/providers/development/github.js +40 -43
  37. package/dist/providers/development/github.js.map +1 -1
  38. package/dist/providers/ecommerce/shopify.d.ts.map +1 -1
  39. package/dist/providers/ecommerce/shopify.js +79 -62
  40. package/dist/providers/ecommerce/shopify.js.map +1 -1
  41. package/dist/providers/email/resend.d.ts.map +1 -1
  42. package/dist/providers/email/resend.js +20 -16
  43. package/dist/providers/email/resend.js.map +1 -1
  44. package/dist/providers/email/sendgrid.d.ts.map +1 -1
  45. package/dist/providers/email/sendgrid.js +12 -9
  46. package/dist/providers/email/sendgrid.js.map +1 -1
  47. package/dist/providers/finance/stripe.d.ts.map +1 -1
  48. package/dist/providers/finance/stripe.js +44 -42
  49. package/dist/providers/finance/stripe.js.map +1 -1
  50. package/dist/providers/forms/typeform.d.ts.map +1 -1
  51. package/dist/providers/forms/typeform.js +68 -58
  52. package/dist/providers/forms/typeform.js.map +1 -1
  53. package/dist/providers/knowledge/notion.d.ts.map +1 -1
  54. package/dist/providers/knowledge/notion.js +75 -41
  55. package/dist/providers/knowledge/notion.js.map +1 -1
  56. package/dist/providers/marketing/mailchimp.d.ts.map +1 -1
  57. package/dist/providers/marketing/mailchimp.js +74 -61
  58. package/dist/providers/marketing/mailchimp.js.map +1 -1
  59. package/dist/providers/media/cloudinary.d.ts.map +1 -1
  60. package/dist/providers/media/cloudinary.js +30 -28
  61. package/dist/providers/media/cloudinary.js.map +1 -1
  62. package/dist/providers/messaging/slack.d.ts.map +1 -1
  63. package/dist/providers/messaging/slack.js +75 -58
  64. package/dist/providers/messaging/slack.js.map +1 -1
  65. package/dist/providers/messaging/twilio-sms.d.ts.map +1 -1
  66. package/dist/providers/messaging/twilio-sms.js +33 -15
  67. package/dist/providers/messaging/twilio-sms.js.map +1 -1
  68. package/dist/providers/project-management/linear.d.ts.map +1 -1
  69. package/dist/providers/project-management/linear.js +31 -27
  70. package/dist/providers/project-management/linear.js.map +1 -1
  71. package/dist/providers/spreadsheet/google-sheets.d.ts.map +1 -1
  72. package/dist/providers/spreadsheet/google-sheets.js +21 -18
  73. package/dist/providers/spreadsheet/google-sheets.js.map +1 -1
  74. package/dist/providers/spreadsheet/xlsx.d.ts.map +1 -1
  75. package/dist/providers/spreadsheet/xlsx.js +4 -4
  76. package/dist/providers/spreadsheet/xlsx.js.map +1 -1
  77. package/dist/providers/storage/index.js +1 -0
  78. package/dist/providers/storage/index.js.map +1 -1
  79. package/dist/providers/storage/s3.d.ts.map +1 -1
  80. package/dist/providers/storage/s3.js +36 -27
  81. package/dist/providers/storage/s3.js.map +1 -1
  82. package/dist/providers/support/zendesk.d.ts.map +1 -1
  83. package/dist/providers/support/zendesk.js +24 -25
  84. package/dist/providers/support/zendesk.js.map +1 -1
  85. package/dist/providers/tasks/todoist.d.ts.map +1 -1
  86. package/dist/providers/tasks/todoist.js +18 -18
  87. package/dist/providers/tasks/todoist.js.map +1 -1
  88. package/dist/providers/video-conferencing/google-meet.d.ts.map +1 -1
  89. package/dist/providers/video-conferencing/google-meet.js +11 -11
  90. package/dist/providers/video-conferencing/google-meet.js.map +1 -1
  91. package/dist/providers/video-conferencing/jitsi.js +14 -14
  92. package/dist/providers/video-conferencing/jitsi.js.map +1 -1
  93. package/dist/providers/video-conferencing/teams.d.ts.map +1 -1
  94. package/dist/providers/video-conferencing/teams.js +9 -7
  95. package/dist/providers/video-conferencing/teams.js.map +1 -1
  96. package/dist/providers/video-conferencing/zoom.d.ts.map +1 -1
  97. package/dist/providers/video-conferencing/zoom.js +26 -24
  98. package/dist/providers/video-conferencing/zoom.js.map +1 -1
  99. package/dist/tools/data.d.ts.map +1 -1
  100. package/dist/tools/data.js +5 -12
  101. package/dist/tools/data.js.map +1 -1
  102. package/dist/tools/index.d.ts +1 -0
  103. package/dist/tools/index.d.ts.map +1 -1
  104. package/dist/tools/index.js +1 -0
  105. package/dist/tools/index.js.map +1 -1
  106. package/dist/tools/system.d.ts +289 -0
  107. package/dist/tools/system.d.ts.map +1 -0
  108. package/dist/tools/system.js +752 -0
  109. package/dist/tools/system.js.map +1 -0
  110. package/dist/tools/web.d.ts.map +1 -1
  111. package/dist/tools/web.js +22 -10
  112. package/dist/tools/web.js.map +1 -1
  113. package/dist/track-record.d.ts +101 -0
  114. package/dist/track-record.d.ts.map +1 -0
  115. package/dist/track-record.js +17 -0
  116. package/dist/track-record.js.map +1 -0
  117. package/dist/types.d.ts +210 -9
  118. package/dist/types.d.ts.map +1 -1
  119. package/dist/verb-registration.d.ts +122 -0
  120. package/dist/verb-registration.d.ts.map +1 -0
  121. package/dist/verb-registration.js +176 -0
  122. package/dist/verb-registration.js.map +1 -0
  123. package/dist/worker.d.ts +93 -0
  124. package/dist/worker.d.ts.map +1 -0
  125. package/dist/worker.js +315 -0
  126. package/dist/worker.js.map +1 -0
  127. package/dist/wrap.d.ts +89 -0
  128. package/dist/wrap.d.ts.map +1 -0
  129. package/dist/wrap.js +225 -0
  130. package/dist/wrap.js.map +1 -0
  131. package/package.json +31 -14
  132. package/src/client.ts +136 -0
  133. package/src/define.ts +30 -24
  134. package/src/function-ref.ts +264 -0
  135. package/src/function-sugar.ts +134 -0
  136. package/src/index.ts +132 -10
  137. package/src/providers/analytics/mixpanel.ts +19 -18
  138. package/src/providers/calendar/cal-com.ts +29 -18
  139. package/src/providers/calendar/google-calendar.ts +20 -14
  140. package/src/providers/crm/hubspot.ts +225 -99
  141. package/src/providers/development/github.ts +206 -135
  142. package/src/providers/ecommerce/shopify.ts +250 -89
  143. package/src/providers/email/resend.ts +101 -28
  144. package/src/providers/email/sendgrid.ts +12 -9
  145. package/src/providers/finance/stripe.ts +128 -49
  146. package/src/providers/forms/typeform.ts +74 -58
  147. package/src/providers/knowledge/notion.ts +340 -88
  148. package/src/providers/marketing/mailchimp.ts +86 -70
  149. package/src/providers/media/cloudinary.ts +99 -41
  150. package/src/providers/messaging/slack.ts +283 -85
  151. package/src/providers/messaging/twilio-sms.ts +35 -15
  152. package/src/providers/project-management/linear.ts +143 -55
  153. package/src/providers/spreadsheet/google-sheets.ts +222 -56
  154. package/src/providers/spreadsheet/xlsx.ts +47 -16
  155. package/src/providers/storage/s3.ts +119 -47
  156. package/src/providers/support/zendesk.ts +196 -46
  157. package/src/providers/tasks/todoist.ts +20 -26
  158. package/src/providers/video-conferencing/google-meet.ts +17 -20
  159. package/src/providers/video-conferencing/jitsi.ts +14 -14
  160. package/src/providers/video-conferencing/teams.ts +14 -13
  161. package/src/providers/video-conferencing/zoom.ts +54 -49
  162. package/src/tools/data.ts +6 -16
  163. package/src/tools/index.ts +1 -0
  164. package/src/tools/system.ts +887 -0
  165. package/src/tools/web.ts +22 -10
  166. package/src/track-record.ts +106 -0
  167. package/src/types.ts +241 -13
  168. package/src/verb-registration.ts +197 -0
  169. package/src/worker.ts +370 -0
  170. package/src/wrap.ts +260 -0
  171. package/test/client.test.ts +146 -0
  172. package/test/communication-tools-extended.test.ts +734 -0
  173. package/test/data-tools-extended.test.ts +743 -0
  174. package/test/define-extended.test.ts +819 -0
  175. package/test/define.test.ts +150 -41
  176. package/test/entities.test.ts +623 -0
  177. package/test/extended-entities.test.ts +1228 -0
  178. package/test/provider-implementations.test.ts +725 -0
  179. package/test/provider-registry-extended.test.ts +583 -0
  180. package/test/providers/google-sheets.test.ts +851 -0
  181. package/test/providers/helpers.ts +554 -0
  182. package/test/providers/hubspot.test.ts +576 -0
  183. package/test/providers/slack.test.ts +932 -0
  184. package/test/providers/stripe.test.ts +701 -0
  185. package/test/providers.test.ts +578 -0
  186. package/test/system-tools-extended.test.ts +632 -0
  187. package/test/system.test.ts +673 -0
  188. package/test/tools.test.ts +15 -11
  189. package/test/types.test.ts +402 -0
  190. package/test/verb-registration.test.ts +395 -0
  191. package/test/web-tools.test.ts +553 -0
  192. package/test/worker-extended.test.ts +699 -0
  193. package/test/worker.test.ts +576 -0
  194. package/test/wrap.test.ts +366 -0
  195. package/tsconfig.json +3 -13
  196. package/vitest.config.ts +37 -0
  197. package/wrangler.jsonc +9 -0
  198. package/.turbo/turbo-build.log +0 -4
  199. package/LICENSE +0 -21
  200. package/dist/providers/voice/vapi.d.ts +0 -27
  201. package/dist/providers/voice/vapi.d.ts.map +0 -1
  202. package/dist/providers/voice/vapi.js +0 -440
  203. package/dist/providers/voice/vapi.js.map +0 -1
  204. package/src/define.js +0 -259
  205. package/src/entities/advertising.js +0 -999
  206. package/src/entities/ai.js +0 -756
  207. package/src/entities/analytics.js +0 -1588
  208. package/src/entities/automation.js +0 -601
  209. package/src/entities/communication.js +0 -1150
  210. package/src/entities/crm.js +0 -1386
  211. package/src/entities/design.js +0 -546
  212. package/src/entities/development.js +0 -2212
  213. package/src/entities/document.js +0 -874
  214. package/src/entities/ecommerce.js +0 -1429
  215. package/src/entities/experiment.js +0 -1039
  216. package/src/entities/finance.js +0 -3478
  217. package/src/entities/forms.js +0 -1892
  218. package/src/entities/hr.js +0 -661
  219. package/src/entities/identity.js +0 -997
  220. package/src/entities/index.js +0 -282
  221. package/src/entities/infrastructure.js +0 -1153
  222. package/src/entities/knowledge.js +0 -1438
  223. package/src/entities/marketing.js +0 -1610
  224. package/src/entities/media.js +0 -1634
  225. package/src/entities/notification.js +0 -1199
  226. package/src/entities/presentation.js +0 -1274
  227. package/src/entities/productivity.js +0 -1317
  228. package/src/entities/project-management.js +0 -1136
  229. package/src/entities/recruiting.js +0 -736
  230. package/src/entities/shipping.js +0 -509
  231. package/src/entities/signature.js +0 -1102
  232. package/src/entities/site.js +0 -222
  233. package/src/entities/spreadsheet.js +0 -1341
  234. package/src/entities/storage.js +0 -1198
  235. package/src/entities/support.js +0 -1166
  236. package/src/entities/video-conferencing.js +0 -1750
  237. package/src/entities/video.js +0 -950
  238. package/src/entities.js +0 -1663
  239. package/src/index.js +0 -74
  240. package/src/providers/analytics/index.js +0 -17
  241. package/src/providers/analytics/mixpanel.js +0 -255
  242. package/src/providers/calendar/cal-com.js +0 -303
  243. package/src/providers/calendar/google-calendar.js +0 -335
  244. package/src/providers/calendar/index.js +0 -20
  245. package/src/providers/crm/hubspot.js +0 -566
  246. package/src/providers/crm/index.js +0 -17
  247. package/src/providers/development/github.js +0 -472
  248. package/src/providers/development/index.js +0 -17
  249. package/src/providers/ecommerce/index.js +0 -17
  250. package/src/providers/ecommerce/shopify.js +0 -378
  251. package/src/providers/email/index.js +0 -20
  252. package/src/providers/email/resend.js +0 -258
  253. package/src/providers/email/sendgrid.js +0 -161
  254. package/src/providers/finance/index.js +0 -17
  255. package/src/providers/finance/stripe.js +0 -549
  256. package/src/providers/forms/index.js +0 -17
  257. package/src/providers/forms/typeform.js +0 -500
  258. package/src/providers/index.js +0 -123
  259. package/src/providers/knowledge/index.js +0 -17
  260. package/src/providers/knowledge/notion.js +0 -389
  261. package/src/providers/marketing/index.js +0 -17
  262. package/src/providers/marketing/mailchimp.js +0 -443
  263. package/src/providers/media/cloudinary.js +0 -318
  264. package/src/providers/media/index.js +0 -17
  265. package/src/providers/messaging/index.js +0 -20
  266. package/src/providers/messaging/slack.js +0 -393
  267. package/src/providers/messaging/twilio-sms.js +0 -249
  268. package/src/providers/project-management/index.js +0 -17
  269. package/src/providers/project-management/linear.js +0 -575
  270. package/src/providers/registry.js +0 -86
  271. package/src/providers/spreadsheet/google-sheets.js +0 -375
  272. package/src/providers/spreadsheet/index.js +0 -20
  273. package/src/providers/spreadsheet/xlsx.js +0 -423
  274. package/src/providers/storage/index.js +0 -24
  275. package/src/providers/storage/s3.js +0 -419
  276. package/src/providers/support/index.js +0 -17
  277. package/src/providers/support/zendesk.js +0 -373
  278. package/src/providers/tasks/index.js +0 -17
  279. package/src/providers/tasks/todoist.js +0 -286
  280. package/src/providers/types.js +0 -9
  281. package/src/providers/video-conferencing/google-meet.js +0 -286
  282. package/src/providers/video-conferencing/index.js +0 -31
  283. package/src/providers/video-conferencing/jitsi.js +0 -254
  284. package/src/providers/video-conferencing/teams.js +0 -270
  285. package/src/providers/video-conferencing/zoom.js +0 -332
  286. package/src/registry.js +0 -128
  287. package/src/tools/communication.js +0 -184
  288. package/src/tools/data.js +0 -205
  289. package/src/tools/index.js +0 -11
  290. package/src/tools/web.js +0 -137
  291. package/src/types.js +0 -10
  292. package/test/define.test.js +0 -306
  293. package/test/registry.test.js +0 -357
  294. package/test/tools.test.js +0 -363
@@ -29,6 +29,175 @@ import { defineProvider } from '../registry.js'
29
29
 
30
30
  const SLACK_API_URL = 'https://slack.com/api'
31
31
 
32
+ // =============================================================================
33
+ // Slack API Response Types
34
+ // =============================================================================
35
+
36
+ /** Slack API response base */
37
+ interface SlackApiResponse {
38
+ ok: boolean
39
+ error?: string
40
+ }
41
+
42
+ /** Slack reaction from API */
43
+ interface SlackReaction {
44
+ name: string
45
+ count: number
46
+ users: string[]
47
+ }
48
+
49
+ /** Slack message edit info */
50
+ interface SlackEditInfo {
51
+ ts?: string
52
+ }
53
+
54
+ /** Slack message from API */
55
+ interface SlackMessage {
56
+ ts: string
57
+ user: string
58
+ text: string
59
+ thread_ts?: string
60
+ reply_count?: number
61
+ reactions?: SlackReaction[]
62
+ edited?: SlackEditInfo
63
+ channel?: { id: string }
64
+ }
65
+
66
+ /** Slack channel topic/purpose from API */
67
+ interface SlackChannelMeta {
68
+ value?: string
69
+ }
70
+
71
+ /** Slack channel from API */
72
+ interface SlackChannel {
73
+ id: string
74
+ name: string
75
+ topic?: SlackChannelMeta
76
+ purpose?: SlackChannelMeta
77
+ is_private?: boolean
78
+ is_archived?: boolean
79
+ num_members?: number
80
+ created: number
81
+ }
82
+
83
+ /** Slack user profile from API */
84
+ interface SlackUserProfile {
85
+ display_name?: string
86
+ email?: string
87
+ image_192?: string
88
+ title?: string
89
+ }
90
+
91
+ /** Slack user from API */
92
+ interface SlackUser {
93
+ id: string
94
+ name: string
95
+ real_name?: string
96
+ profile?: SlackUserProfile
97
+ is_admin?: boolean
98
+ is_owner?: boolean
99
+ is_bot?: boolean
100
+ deleted?: boolean
101
+ tz?: string
102
+ }
103
+
104
+ /** Slack team icon from API */
105
+ interface SlackTeamIcon {
106
+ image_132?: string
107
+ }
108
+
109
+ /** Slack team from API */
110
+ interface SlackTeam {
111
+ id: string
112
+ name: string
113
+ domain: string
114
+ icon?: SlackTeamIcon
115
+ }
116
+
117
+ /** Slack response metadata */
118
+ interface SlackResponseMetadata {
119
+ next_cursor?: string
120
+ }
121
+
122
+ /** Slack paging info */
123
+ interface SlackPaging {
124
+ pages: number
125
+ page: number
126
+ }
127
+
128
+ /** Slack messages search result */
129
+ interface SlackMessagesSearchResult {
130
+ matches: SlackMessage[]
131
+ paging: SlackPaging
132
+ total: number
133
+ }
134
+
135
+ /** Slack auth test response */
136
+ interface SlackAuthTestResponse extends SlackApiResponse {
137
+ user?: string
138
+ }
139
+
140
+ /** Slack conversations open response */
141
+ interface SlackConversationsOpenResponse extends SlackApiResponse {
142
+ channel?: { id: string }
143
+ }
144
+
145
+ /** Slack post message response */
146
+ interface SlackPostMessageResponse extends SlackApiResponse {
147
+ ts?: string
148
+ channel?: string
149
+ }
150
+
151
+ /** Slack conversations history response */
152
+ interface SlackConversationsHistoryResponse extends SlackApiResponse {
153
+ messages?: SlackMessage[]
154
+ has_more?: boolean
155
+ response_metadata?: SlackResponseMetadata
156
+ }
157
+
158
+ /** Slack search messages response */
159
+ interface SlackSearchMessagesResponse extends SlackApiResponse {
160
+ messages: SlackMessagesSearchResult
161
+ }
162
+
163
+ /** Slack conversations list response */
164
+ interface SlackConversationsListResponse extends SlackApiResponse {
165
+ channels: SlackChannel[]
166
+ response_metadata?: SlackResponseMetadata
167
+ }
168
+
169
+ /** Slack conversations info response */
170
+ interface SlackConversationsInfoResponse extends SlackApiResponse {
171
+ channel: SlackChannel
172
+ }
173
+
174
+ /** Slack conversations members response */
175
+ interface SlackConversationsMembersResponse extends SlackApiResponse {
176
+ members: string[]
177
+ response_metadata?: SlackResponseMetadata
178
+ }
179
+
180
+ /** Slack users list response */
181
+ interface SlackUsersListResponse extends SlackApiResponse {
182
+ members: SlackUser[]
183
+ response_metadata?: SlackResponseMetadata
184
+ }
185
+
186
+ /** Slack users info response */
187
+ interface SlackUsersInfoResponse extends SlackApiResponse {
188
+ user: SlackUser
189
+ }
190
+
191
+ /** Slack presence response */
192
+ interface SlackPresenceResponse extends SlackApiResponse {
193
+ presence: string
194
+ }
195
+
196
+ /** Slack team info response */
197
+ interface SlackTeamInfoResponse extends SlackApiResponse {
198
+ team: SlackTeam
199
+ }
200
+
32
201
  /**
33
202
  * Slack provider info
34
203
  */
@@ -49,17 +218,20 @@ export const slackInfo: ProviderInfo = {
49
218
  export function createSlackProvider(config: ProviderConfig): MessagingProvider {
50
219
  let token: string
51
220
 
52
- async function slackApi(method: string, body?: Record<string, unknown>): Promise<any> {
221
+ async function slackApi<T extends SlackApiResponse>(
222
+ method: string,
223
+ body?: Record<string, unknown>
224
+ ): Promise<T> {
53
225
  const response = await fetch(`${SLACK_API_URL}/${method}`, {
54
226
  method: 'POST',
55
227
  headers: {
56
228
  'Content-Type': 'application/json; charset=utf-8',
57
229
  Authorization: `Bearer ${token}`,
58
230
  },
59
- body: body ? JSON.stringify(body) : undefined,
231
+ ...(body !== undefined && { body: JSON.stringify(body) }),
60
232
  })
61
233
 
62
- const data = await response.json()
234
+ const data = (await response.json()) as T
63
235
  return data
64
236
  }
65
237
 
@@ -67,7 +239,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
67
239
  info: slackInfo,
68
240
 
69
241
  async initialize(cfg: ProviderConfig): Promise<void> {
70
- token = (cfg.accessToken || cfg.botToken) as string
242
+ token = (cfg['accessToken'] || cfg['botToken']) as string
71
243
  if (!token) {
72
244
  throw new Error('Slack access token or bot token is required')
73
245
  }
@@ -76,11 +248,11 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
76
248
  async healthCheck(): Promise<ProviderHealth> {
77
249
  const start = Date.now()
78
250
  try {
79
- const data = await slackApi('auth.test')
251
+ const data = await slackApi<SlackAuthTestResponse>('auth.test')
80
252
  return {
81
253
  healthy: data.ok === true,
82
254
  latencyMs: Date.now() - start,
83
- message: data.ok ? `Connected as ${data.user}` : data.error,
255
+ message: data.ok ? `Connected as ${data.user}` : data.error || 'Unknown error',
84
256
  checkedAt: new Date(),
85
257
  }
86
258
  } catch (error) {
@@ -103,17 +275,19 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
103
275
  }
104
276
 
105
277
  if (options.channel) {
106
- body.channel = options.channel
278
+ body['channel'] = options.channel
107
279
  } else if (options.userId) {
108
280
  // Open DM conversation first
109
- const dm = await slackApi('conversations.open', { users: options.userId })
281
+ const dm = await slackApi<SlackConversationsOpenResponse>('conversations.open', {
282
+ users: options.userId,
283
+ })
110
284
  if (!dm.ok) {
111
285
  return {
112
286
  success: false,
113
- error: { code: dm.error, message: `Failed to open DM: ${dm.error}` },
287
+ error: { code: dm.error || 'UNKNOWN', message: `Failed to open DM: ${dm.error}` },
114
288
  }
115
289
  }
116
- body.channel = dm.channel.id
290
+ body['channel'] = dm.channel?.id
117
291
  } else {
118
292
  return {
119
293
  success: false,
@@ -122,34 +296,34 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
122
296
  }
123
297
 
124
298
  if (options.threadId) {
125
- body.thread_ts = options.threadId
299
+ body['thread_ts'] = options.threadId
126
300
  }
127
301
 
128
302
  if (options.blocks) {
129
- body.blocks = options.blocks
303
+ body['blocks'] = options.blocks
130
304
  }
131
305
 
132
306
  if (options.metadata) {
133
- body.metadata = {
307
+ body['metadata'] = {
134
308
  event_type: 'message_metadata',
135
309
  event_payload: options.metadata,
136
310
  }
137
311
  }
138
312
 
139
- const data = await slackApi('chat.postMessage', body)
313
+ const data = await slackApi<SlackPostMessageResponse>('chat.postMessage', body)
140
314
 
141
315
  if (data.ok) {
142
316
  return {
143
317
  success: true,
144
- messageId: data.ts,
145
- timestamp: data.ts,
146
- channel: data.channel,
318
+ ...(data.ts !== undefined && { messageId: data.ts }),
319
+ ...(data.ts !== undefined && { timestamp: data.ts }),
320
+ ...(data.channel !== undefined && { channel: data.channel }),
147
321
  }
148
322
  }
149
323
 
150
324
  return {
151
325
  success: false,
152
- error: { code: data.error, message: data.error },
326
+ error: { code: data.error || 'UNKNOWN', message: data.error || 'Unknown error' },
153
327
  }
154
328
  },
155
329
 
@@ -160,33 +334,33 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
160
334
  }
161
335
 
162
336
  if (blocks) {
163
- body.blocks = blocks
337
+ body['blocks'] = blocks
164
338
  }
165
339
 
166
- const data = await slackApi('chat.update', body)
340
+ const data = await slackApi<SlackPostMessageResponse>('chat.update', body)
167
341
 
168
342
  if (data.ok) {
169
343
  return {
170
344
  success: true,
171
- messageId: data.ts,
172
- timestamp: data.ts,
173
- channel: data.channel,
345
+ ...(data.ts !== undefined && { messageId: data.ts }),
346
+ ...(data.ts !== undefined && { timestamp: data.ts }),
347
+ ...(data.channel !== undefined && { channel: data.channel }),
174
348
  }
175
349
  }
176
350
 
177
351
  return {
178
352
  success: false,
179
- error: { code: data.error, message: data.error },
353
+ error: { code: data.error || 'UNKNOWN', message: data.error || 'Unknown error' },
180
354
  }
181
355
  },
182
356
 
183
357
  async delete(messageId: string, channel: string): Promise<boolean> {
184
- const data = await slackApi('chat.delete', { ts: messageId, channel })
358
+ const data = await slackApi<SlackApiResponse>('chat.delete', { ts: messageId, channel })
185
359
  return data.ok === true
186
360
  },
187
361
 
188
362
  async react(messageId: string, channel: string, emoji: string): Promise<boolean> {
189
- const data = await slackApi('reactions.add', {
363
+ const data = await slackApi<SlackApiResponse>('reactions.add', {
190
364
  name: emoji.replace(/:/g, ''),
191
365
  timestamp: messageId,
192
366
  channel,
@@ -195,7 +369,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
195
369
  },
196
370
 
197
371
  async unreact(messageId: string, channel: string, emoji: string): Promise<boolean> {
198
- const data = await slackApi('reactions.remove', {
372
+ const data = await slackApi<SlackApiResponse>('reactions.remove', {
199
373
  name: emoji.replace(/:/g, ''),
200
374
  timestamp: messageId,
201
375
  channel,
@@ -204,7 +378,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
204
378
  },
205
379
 
206
380
  async getMessage(messageId: string, channel: string): Promise<MessageData | null> {
207
- const data = await slackApi('conversations.history', {
381
+ const data = await slackApi<SlackConversationsHistoryResponse>('conversations.history', {
208
382
  channel,
209
383
  latest: messageId,
210
384
  inclusive: true,
@@ -216,40 +390,49 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
216
390
  }
217
391
 
218
392
  const msg = data.messages[0]
393
+ if (!msg) return null
219
394
  return mapSlackMessage(msg, channel)
220
395
  },
221
396
 
222
- async listMessages(channel: string, options?: MessageListOptions): Promise<PaginatedResult<MessageData>> {
397
+ async listMessages(
398
+ channel: string,
399
+ options?: MessageListOptions
400
+ ): Promise<PaginatedResult<MessageData>> {
223
401
  const body: Record<string, unknown> = {
224
402
  channel,
225
403
  limit: options?.limit || 100,
226
404
  }
227
405
 
228
406
  if (options?.cursor) {
229
- body.cursor = options.cursor
407
+ body['cursor'] = options.cursor
230
408
  }
231
409
  if (options?.since) {
232
- body.oldest = (options.since.getTime() / 1000).toString()
410
+ body['oldest'] = (options.since.getTime() / 1000).toString()
233
411
  }
234
412
  if (options?.until) {
235
- body.latest = (options.until.getTime() / 1000).toString()
413
+ body['latest'] = (options.until.getTime() / 1000).toString()
236
414
  }
237
415
 
238
- const data = await slackApi('conversations.history', body)
416
+ const data = await slackApi<SlackConversationsHistoryResponse>('conversations.history', body)
239
417
 
240
418
  if (!data.ok) {
241
419
  return { items: [], hasMore: false }
242
420
  }
243
421
 
244
422
  return {
245
- items: data.messages.map((msg: any) => mapSlackMessage(msg, channel)),
423
+ items: (data.messages || []).map((msg) => mapSlackMessage(msg, channel)),
246
424
  hasMore: data.has_more || false,
247
- nextCursor: data.response_metadata?.next_cursor,
425
+ ...(data.response_metadata?.next_cursor !== undefined && {
426
+ nextCursor: data.response_metadata.next_cursor,
427
+ }),
248
428
  }
249
429
  },
250
430
 
251
- async searchMessages(query: string, options?: MessageSearchOptions): Promise<PaginatedResult<MessageData>> {
252
- const data = await slackApi('search.messages', {
431
+ async searchMessages(
432
+ query: string,
433
+ options?: MessageSearchOptions
434
+ ): Promise<PaginatedResult<MessageData>> {
435
+ const data = await slackApi<SlackSearchMessagesResponse>('search.messages', {
253
436
  query,
254
437
  count: options?.limit || 100,
255
438
  page: options?.offset ? Math.floor(options.offset / (options.limit || 100)) + 1 : 1,
@@ -260,7 +443,9 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
260
443
  }
261
444
 
262
445
  return {
263
- items: data.messages.matches.map((match: any) => mapSlackMessage(match, match.channel.id)),
446
+ items: data.messages.matches.map((match) =>
447
+ mapSlackMessage(match, match.channel?.id || '')
448
+ ),
264
449
  hasMore: data.messages.paging.pages > data.messages.paging.page,
265
450
  total: data.messages.total,
266
451
  }
@@ -273,14 +458,16 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
273
458
  }
274
459
 
275
460
  if (options?.cursor) {
276
- body.cursor = options.cursor
461
+ body['cursor'] = options.cursor
277
462
  }
278
463
 
279
464
  if (options?.types) {
280
- body.types = options.types.map((t) => (t === 'private' ? 'private_channel' : 'public_channel')).join(',')
465
+ body['types'] = options.types
466
+ .map((t) => (t === 'private' ? 'private_channel' : 'public_channel'))
467
+ .join(',')
281
468
  }
282
469
 
283
- const data = await slackApi('conversations.list', body)
470
+ const data = await slackApi<SlackConversationsListResponse>('conversations.list', body)
284
471
 
285
472
  if (!data.ok) {
286
473
  return { items: [], hasMore: false }
@@ -289,12 +476,16 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
289
476
  return {
290
477
  items: data.channels.map(mapSlackChannel),
291
478
  hasMore: data.response_metadata?.next_cursor ? true : false,
292
- nextCursor: data.response_metadata?.next_cursor,
479
+ ...(data.response_metadata?.next_cursor !== undefined && {
480
+ nextCursor: data.response_metadata.next_cursor,
481
+ }),
293
482
  }
294
483
  },
295
484
 
296
485
  async getChannel(channelId: string): Promise<ChannelData | null> {
297
- const data = await slackApi('conversations.info', { channel: channelId })
486
+ const data = await slackApi<SlackConversationsInfoResponse>('conversations.info', {
487
+ channel: channelId,
488
+ })
298
489
 
299
490
  if (!data.ok) {
300
491
  return null
@@ -309,7 +500,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
309
500
  is_private: options?.isPrivate || false,
310
501
  }
311
502
 
312
- const data = await slackApi('conversations.create', body)
503
+ const data = await slackApi<SlackConversationsInfoResponse>('conversations.create', body)
313
504
 
314
505
  if (!data.ok) {
315
506
  throw new Error(`Failed to create channel: ${data.error}`)
@@ -319,7 +510,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
319
510
 
320
511
  // Set topic if provided
321
512
  if (options?.topic) {
322
- await slackApi('conversations.setTopic', {
513
+ await slackApi<SlackApiResponse>('conversations.setTopic', {
323
514
  channel: data.channel.id,
324
515
  topic: options.topic,
325
516
  })
@@ -327,7 +518,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
327
518
 
328
519
  // Set description/purpose if provided
329
520
  if (options?.description) {
330
- await slackApi('conversations.setPurpose', {
521
+ await slackApi<SlackApiResponse>('conversations.setPurpose', {
331
522
  channel: data.channel.id,
332
523
  purpose: options.description,
333
524
  })
@@ -337,17 +528,17 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
337
528
  },
338
529
 
339
530
  async archiveChannel(channelId: string): Promise<boolean> {
340
- const data = await slackApi('conversations.archive', { channel: channelId })
531
+ const data = await slackApi<SlackApiResponse>('conversations.archive', { channel: channelId })
341
532
  return data.ok === true
342
533
  },
343
534
 
344
535
  async joinChannel(channelId: string): Promise<boolean> {
345
- const data = await slackApi('conversations.join', { channel: channelId })
536
+ const data = await slackApi<SlackApiResponse>('conversations.join', { channel: channelId })
346
537
  return data.ok === true
347
538
  },
348
539
 
349
540
  async leaveChannel(channelId: string): Promise<boolean> {
350
- const data = await slackApi('conversations.leave', { channel: channelId })
541
+ const data = await slackApi<SlackApiResponse>('conversations.leave', { channel: channelId })
351
542
  return data.ok === true
352
543
  },
353
544
 
@@ -357,48 +548,53 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
357
548
  }
358
549
 
359
550
  if (options?.cursor) {
360
- body.cursor = options.cursor
551
+ body['cursor'] = options.cursor
361
552
  }
362
553
 
363
- let data: any
364
-
365
554
  if (options?.channel) {
366
555
  // Get members of specific channel
367
- data = await slackApi('conversations.members', { ...body, channel: options.channel })
368
- if (!data.ok) {
556
+ const channelData = await slackApi<SlackConversationsMembersResponse>(
557
+ 'conversations.members',
558
+ { ...body, channel: options.channel }
559
+ )
560
+ if (!channelData.ok) {
369
561
  return { items: [], hasMore: false }
370
562
  }
371
563
 
372
564
  // Fetch user info for each member
373
565
  const members = await Promise.all(
374
- data.members.map(async (userId: string) => {
375
- const userInfo = await slackApi('users.info', { user: userId })
566
+ channelData.members.map(async (userId: string) => {
567
+ const userInfo = await slackApi<SlackUsersInfoResponse>('users.info', { user: userId })
376
568
  return userInfo.ok ? mapSlackUser(userInfo.user) : null
377
569
  })
378
570
  )
379
571
 
380
572
  return {
381
- items: members.filter(Boolean) as MemberData[],
382
- hasMore: data.response_metadata?.next_cursor ? true : false,
383
- nextCursor: data.response_metadata?.next_cursor,
573
+ items: members.filter((m): m is MemberData => m !== null),
574
+ hasMore: channelData.response_metadata?.next_cursor ? true : false,
575
+ ...(channelData.response_metadata?.next_cursor !== undefined && {
576
+ nextCursor: channelData.response_metadata.next_cursor,
577
+ }),
384
578
  }
385
579
  } else {
386
580
  // Get all workspace members
387
- data = await slackApi('users.list', body)
388
- if (!data.ok) {
581
+ const usersData = await slackApi<SlackUsersListResponse>('users.list', body)
582
+ if (!usersData.ok) {
389
583
  return { items: [], hasMore: false }
390
584
  }
391
585
 
392
586
  return {
393
- items: data.members.filter((m: any) => !m.deleted).map(mapSlackUser),
394
- hasMore: data.response_metadata?.next_cursor ? true : false,
395
- nextCursor: data.response_metadata?.next_cursor,
587
+ items: usersData.members.filter((m) => !m.deleted).map(mapSlackUser),
588
+ hasMore: usersData.response_metadata?.next_cursor ? true : false,
589
+ ...(usersData.response_metadata?.next_cursor !== undefined && {
590
+ nextCursor: usersData.response_metadata.next_cursor,
591
+ }),
396
592
  }
397
593
  }
398
594
  },
399
595
 
400
596
  async getMember(userId: string): Promise<MemberData | null> {
401
- const data = await slackApi('users.info', { user: userId })
597
+ const data = await slackApi<SlackUsersInfoResponse>('users.info', { user: userId })
402
598
 
403
599
  if (!data.ok) {
404
600
  return null
@@ -408,7 +604,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
408
604
  },
409
605
 
410
606
  async getPresence(userId: string): Promise<PresenceData> {
411
- const data = await slackApi('users.getPresence', { user: userId })
607
+ const data = await slackApi<SlackPresenceResponse>('users.getPresence', { user: userId })
412
608
 
413
609
  return {
414
610
  userId,
@@ -417,7 +613,7 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
417
613
  },
418
614
 
419
615
  async getWorkspace(): Promise<WorkspaceData> {
420
- const data = await slackApi('team.info')
616
+ const data = await slackApi<SlackTeamInfoResponse>('team.info')
421
617
 
422
618
  if (!data.ok) {
423
619
  throw new Error(`Failed to get workspace info: ${data.error}`)
@@ -427,37 +623,39 @@ export function createSlackProvider(config: ProviderConfig): MessagingProvider {
427
623
  id: data.team.id,
428
624
  name: data.team.name,
429
625
  domain: data.team.domain,
430
- icon: data.team.icon?.image_132,
626
+ ...(data.team.icon?.image_132 !== undefined && { icon: data.team.icon.image_132 }),
431
627
  }
432
628
  },
433
629
  }
434
630
  }
435
631
 
436
- function mapSlackMessage(msg: any, channel: string): MessageData {
632
+ function mapSlackMessage(msg: SlackMessage, channel: string): MessageData {
437
633
  return {
438
634
  id: msg.ts,
439
635
  channel,
440
636
  userId: msg.user,
441
637
  text: msg.text,
442
638
  timestamp: msg.ts,
443
- threadId: msg.thread_ts,
444
- replyCount: msg.reply_count,
445
- reactions: msg.reactions?.map((r: any) => ({
446
- emoji: r.name,
447
- count: r.count,
448
- users: r.users,
449
- })),
639
+ ...(msg.thread_ts !== undefined && { threadId: msg.thread_ts }),
640
+ ...(msg.reply_count !== undefined && { replyCount: msg.reply_count }),
641
+ ...(msg.reactions && {
642
+ reactions: msg.reactions.map((r) => ({
643
+ emoji: r.name,
644
+ count: r.count,
645
+ users: r.users,
646
+ })),
647
+ }),
450
648
  edited: !!msg.edited,
451
- editedAt: msg.edited?.ts ? new Date(parseFloat(msg.edited.ts) * 1000) : undefined,
649
+ ...(msg.edited?.ts && { editedAt: new Date(parseFloat(msg.edited.ts) * 1000) }),
452
650
  }
453
651
  }
454
652
 
455
- function mapSlackChannel(ch: any): ChannelData {
653
+ function mapSlackChannel(ch: SlackChannel): ChannelData {
456
654
  return {
457
655
  id: ch.id,
458
656
  name: ch.name,
459
- topic: ch.topic?.value,
460
- description: ch.purpose?.value,
657
+ ...(ch.topic?.value !== undefined && { topic: ch.topic.value }),
658
+ ...(ch.purpose?.value !== undefined && { description: ch.purpose.value }),
461
659
  isPrivate: ch.is_private || false,
462
660
  isArchived: ch.is_archived || false,
463
661
  memberCount: ch.num_members || 0,
@@ -465,17 +663,17 @@ function mapSlackChannel(ch: any): ChannelData {
465
663
  }
466
664
  }
467
665
 
468
- function mapSlackUser(user: any): MemberData {
666
+ function mapSlackUser(user: SlackUser): MemberData {
469
667
  return {
470
668
  id: user.id,
471
669
  username: user.name,
472
670
  displayName: user.real_name || user.profile?.display_name || user.name,
473
- email: user.profile?.email,
474
- avatar: user.profile?.image_192,
475
- title: user.profile?.title,
671
+ ...(user.profile?.email !== undefined && { email: user.profile.email }),
672
+ ...(user.profile?.image_192 !== undefined && { avatar: user.profile.image_192 }),
673
+ ...(user.profile?.title !== undefined && { title: user.profile.title }),
476
674
  isAdmin: user.is_admin || user.is_owner || false,
477
675
  isBot: user.is_bot || false,
478
- timezone: user.tz,
676
+ ...(user.tz !== undefined && { timezone: user.tz }),
479
677
  }
480
678
  }
481
679