@unboundcx/sdk 2.7.7 → 2.8.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.
@@ -0,0 +1,458 @@
1
+ export class EmailMailboxesService {
2
+ constructor(sdk) {
3
+ this.sdk = sdk;
4
+ }
5
+
6
+ /**
7
+ * Create a new mailbox with system address
8
+ * @param {string} [mailbox] - Custom mailbox name (optional, must be unique per account)
9
+ * @param {string} [name] - Display name for the mailbox (optional)
10
+ * @param {string} [userId] - User ID to assign mailbox to (optional)
11
+ * @param {string} [recordTypeId] - Record type ID for permissions (optional)
12
+ * @param {boolean} [useEngagementSessions=false] - Enable engagement session linking for ticketing (optional)
13
+ * @param {string} [queueId] - Queue ID for contact center routing (optional)
14
+ * @param {string} [ticketPrefix] - Ticket prefix for engagement sessions (e.g., 'SUP', 'TECH') (optional)
15
+ * @param {string} [ticketCreateEmailTemplateId] - Email template ID for auto-reply on new tickets (optional)
16
+ * @param {string} [ticketCreateEmailFrom] - From address for auto-reply emails (optional, defaults to received address)
17
+ * @returns {Promise<Object>} Created mailbox with system address
18
+ * @example
19
+ * // Create basic mailbox
20
+ * const mailbox = await sdk.messaging.email.mailboxes.create();
21
+ *
22
+ * // Create support mailbox with engagement sessions and auto-reply
23
+ * const supportMailbox = await sdk.messaging.email.mailboxes.create({
24
+ * mailbox: 'support',
25
+ * name: 'Support Team',
26
+ * useEngagementSessions: true,
27
+ * queueId: 'queue123',
28
+ * ticketPrefix: 'SUP',
29
+ * ticketCreateEmailTemplateId: 'template123',
30
+ * ticketCreateEmailFrom: 'support@company.com'
31
+ * });
32
+ */
33
+ async create(options = {}) {
34
+ // Support both old positional parameters and new options object
35
+ let mailboxData;
36
+ if (typeof options === 'string' || arguments.length > 1) {
37
+ // Old API: positional parameters
38
+ const [
39
+ mailbox,
40
+ name,
41
+ userId,
42
+ recordTypeId,
43
+ useEngagementSessions,
44
+ queueId,
45
+ ticketPrefix,
46
+ ticketCreateEmailTemplateId,
47
+ ticketCreateEmailFrom,
48
+ ] = arguments;
49
+ mailboxData = {};
50
+ if (mailbox !== undefined) mailboxData.mailbox = mailbox;
51
+ if (name !== undefined) mailboxData.name = name;
52
+ if (userId !== undefined) mailboxData.userId = userId;
53
+ if (recordTypeId !== undefined) mailboxData.recordTypeId = recordTypeId;
54
+ if (useEngagementSessions !== undefined)
55
+ mailboxData.useEngagementSessions = useEngagementSessions;
56
+ if (queueId !== undefined) mailboxData.queueId = queueId;
57
+ if (ticketPrefix !== undefined) mailboxData.ticketPrefix = ticketPrefix;
58
+ if (ticketCreateEmailTemplateId !== undefined)
59
+ mailboxData.ticketCreateEmailTemplateId = ticketCreateEmailTemplateId;
60
+ if (ticketCreateEmailFrom !== undefined)
61
+ mailboxData.ticketCreateEmailFrom = ticketCreateEmailFrom;
62
+ } else {
63
+ // New API: options object
64
+ mailboxData = { ...options };
65
+ }
66
+
67
+ this.sdk.validateParams(mailboxData, {
68
+ mailbox: { type: 'string', required: false },
69
+ name: { type: 'string', required: false },
70
+ userId: { type: 'string', required: false },
71
+ recordTypeId: { type: 'string', required: false },
72
+ useEngagementSessions: { type: 'boolean', required: false },
73
+ queueId: { type: 'string', required: false },
74
+ ticketPrefix: { type: 'string', required: false },
75
+ ticketCreateEmailTemplateId: { type: 'string', required: false },
76
+ ticketCreateEmailFrom: { type: 'string', required: false },
77
+ });
78
+
79
+ const result = await this.sdk._fetch('/messaging/email/mailbox', 'POST', {
80
+ body: mailboxData,
81
+ });
82
+ return result;
83
+ }
84
+
85
+ /**
86
+ * List mailboxes with optional filtering
87
+ * @param {string} [userId] - Filter by assigned user ID
88
+ * @param {string} [search] - Search in mailbox name or display name
89
+ * @param {string[]} [folderCounts] - Array of folders to count messages for (if provided, returns counts)
90
+ * @param {number} [page=1] - Page number for pagination
91
+ * @param {number} [limit=50] - Number of items per page (max 100)
92
+ * @param {string} [sortBy='createdAt'] - Sort field: createdAt, mailbox, name
93
+ * @param {string} [sortOrder='desc'] - Sort order: asc, desc
94
+ * @returns {Promise<Object>} Paginated list of mailboxes with system addresses, optional message counts, and available folders
95
+ * @example
96
+ * // List all mailboxes (no counts)
97
+ * const result = await sdk.messaging.email.mailboxes.list();
98
+ *
99
+ * // List mailboxes with message counts for open folder
100
+ * const withCounts = await sdk.messaging.email.mailboxes.list({folderCounts: ['open']});
101
+ * // Returns: { mailboxes: [{ ..., messageCounts: { open: 5, total: 5 }, availableFolders: ['open', 'completed', 'trash', 'spam'] }] }
102
+ *
103
+ * // List mailboxes with counts for multiple folders
104
+ * const allCounts = await sdk.messaging.email.mailboxes.list({folderCounts: ['open', 'completed', 'trash']});
105
+ * // Returns: { mailboxes: [{ ..., messageCounts: { open: 5, completed: 3, trash: 1, total: 9 }, availableFolders: [...] }] }
106
+ *
107
+ * // List mailboxes for specific user
108
+ * const userMailboxes = await sdk.messaging.email.mailboxes.list({userId:'userId123'});
109
+ *
110
+ * // Search and paginate
111
+ * const searchResults = await sdk.messaging.email.mailboxes.list({search: 'support', page: 1, limit: 10});
112
+ */
113
+ async list({
114
+ userId,
115
+ searchQuery,
116
+ folderCounts,
117
+ page = 1,
118
+ limit = 50,
119
+ sortBy = 'createdAt',
120
+ sortOrder = 'desc',
121
+ }) {
122
+ this.sdk.validateParams(
123
+ {
124
+ userId,
125
+ searchQuery,
126
+ folderCounts,
127
+ page,
128
+ limit,
129
+ sortBy,
130
+ sortOrder,
131
+ },
132
+ {
133
+ userId: { type: 'string', required: false },
134
+ searchQuery: { type: 'string', required: false },
135
+ folderCounts: { type: 'array', required: false },
136
+ page: { type: 'number', required: false },
137
+ limit: { type: 'number', required: false },
138
+ sortBy: { type: 'string', required: false },
139
+ sortOrder: { type: 'string', required: false },
140
+ },
141
+ );
142
+
143
+ const params = {
144
+ query: {
145
+ userId,
146
+ search: searchQuery,
147
+ folderCounts: Array.isArray(folderCounts)
148
+ ? folderCounts.join(',')
149
+ : folderCounts,
150
+ page,
151
+ limit,
152
+ sortBy,
153
+ sortOrder,
154
+ },
155
+ };
156
+
157
+ const result = await this.sdk._fetch(
158
+ '/messaging/email/mailbox',
159
+ 'GET',
160
+ params,
161
+ );
162
+ return result;
163
+ }
164
+
165
+ /**
166
+ * Get mailbox by ID with optional alias information
167
+ * @param {string} id - Mailbox ID
168
+ * @param {boolean} [includeAliases=false] - Include custom aliases information
169
+ * @returns {Promise<Object>} Mailbox details with system address and optional aliases
170
+ * @example
171
+ * // Get basic mailbox info
172
+ * const mailbox = await sdk.messaging.email.mailboxes.get('01030181181');
173
+ *
174
+ * // Get mailbox with all aliases
175
+ * const mailboxWithAliases = await sdk.messaging.email.mailboxes.get('01030181181', true);
176
+ */
177
+ async get(id, includeAliases = true) {
178
+ this.sdk.validateParams(
179
+ { id, includeAliases },
180
+ {
181
+ id: { type: 'string', required: true },
182
+ includeAliases: { type: 'boolean', required: false },
183
+ },
184
+ );
185
+
186
+ const params = {
187
+ query: {
188
+ includeAliases,
189
+ },
190
+ };
191
+
192
+ const result = await this.sdk._fetch(
193
+ `/messaging/email/mailbox/${id}`,
194
+ 'GET',
195
+ params,
196
+ );
197
+ return result;
198
+ }
199
+
200
+ /**
201
+ * Update mailbox settings
202
+ * @param {string} id - Mailbox ID
203
+ * @param {Object} updates - Update data object
204
+ * @param {string} [updates.mailbox] - Custom mailbox name (must be unique per account)
205
+ * @param {string} [updates.name] - Display name
206
+ * @param {string} [updates.userId] - User ID to assign mailbox to
207
+ * @param {string} [updates.recordTypeId] - Record type ID for permissions
208
+ * @param {boolean} [updates.useEngagementSessions] - Enable engagement session linking
209
+ * @param {string} [updates.queueId] - Queue ID for contact center routing
210
+ * @param {string} [updates.ticketPrefix] - Ticket prefix for engagement sessions
211
+ * @param {string} [updates.ticketCreateEmailTemplateId] - Email template ID for auto-reply
212
+ * @param {string} [updates.ticketCreateEmailFrom] - From address for auto-reply emails
213
+ * @param {boolean} [updates.isActive] - Whether mailbox is active
214
+ * @returns {Promise<Object>} Update result
215
+ * @example
216
+ * // Update mailbox with engagement sessions and queue
217
+ * await sdk.messaging.email.mailboxes.update('01030181181', {
218
+ * name: 'Support Team',
219
+ * useEngagementSessions: true,
220
+ * queueId: 'queue123',
221
+ * ticketPrefix: 'SUP',
222
+ * ticketCreateEmailTemplateId: 'template123'
223
+ * });
224
+ *
225
+ * // Deactivate mailbox
226
+ * await sdk.messaging.email.mailboxes.update('01030181181', { isActive: false });
227
+ */
228
+ async update(id, updates = {}) {
229
+ // Support both old positional API and new object API for backward compatibility
230
+ let updateData;
231
+ if (typeof updates === 'string' || arguments.length > 2) {
232
+ // Old API: positional parameters
233
+ const [
234
+ mailbox,
235
+ name,
236
+ userId,
237
+ recordTypeId,
238
+ isActive,
239
+ useEngagementSessions,
240
+ queueId,
241
+ ticketPrefix,
242
+ ticketCreateEmailTemplateId,
243
+ ticketCreateEmailFrom,
244
+ ] = Array.from(arguments).slice(1);
245
+ updateData = {};
246
+ if (mailbox !== undefined) updateData.mailbox = mailbox;
247
+ if (name !== undefined) updateData.name = name;
248
+ if (userId !== undefined) updateData.userId = userId;
249
+ if (recordTypeId !== undefined) updateData.recordTypeId = recordTypeId;
250
+ if (isActive !== undefined) updateData.isActive = isActive;
251
+ if (useEngagementSessions !== undefined)
252
+ updateData.useEngagementSessions = useEngagementSessions;
253
+ if (queueId !== undefined) updateData.queueId = queueId;
254
+ if (ticketPrefix !== undefined) updateData.ticketPrefix = ticketPrefix;
255
+ if (ticketCreateEmailTemplateId !== undefined)
256
+ updateData.ticketCreateEmailTemplateId = ticketCreateEmailTemplateId;
257
+ if (ticketCreateEmailFrom !== undefined)
258
+ updateData.ticketCreateEmailFrom = ticketCreateEmailFrom;
259
+ } else {
260
+ // New API: options object
261
+ updateData = { ...updates };
262
+ }
263
+
264
+ this.sdk.validateParams(
265
+ { id, ...updateData },
266
+ {
267
+ id: { type: 'string', required: true },
268
+ mailbox: { type: 'string', required: false },
269
+ name: { type: 'string', required: false },
270
+ userId: { type: 'string', required: false },
271
+ recordTypeId: { type: 'string', required: false },
272
+ useEngagementSessions: { type: 'boolean', required: false },
273
+ queueId: { type: 'string', required: false },
274
+ ticketPrefix: { type: 'string', required: false },
275
+ ticketCreateEmailTemplateId: { type: 'string', required: false },
276
+ ticketCreateEmailFrom: { type: 'string', required: false },
277
+ isActive: { type: 'boolean', required: false },
278
+ },
279
+ );
280
+
281
+ const result = await this.sdk._fetch(
282
+ `/messaging/email/mailbox/${id}`,
283
+ 'PUT',
284
+ {
285
+ body: updateData,
286
+ },
287
+ );
288
+ return result;
289
+ }
290
+
291
+ /**
292
+ * Delete a mailbox (soft delete)
293
+ * @param {string} id - Mailbox ID
294
+ * @returns {Promise<Object>} Deletion result
295
+ * @example
296
+ * await sdk.messaging.email.mailboxes.delete('01030181181');
297
+ */
298
+ async delete(id) {
299
+ this.sdk.validateParams(
300
+ { id },
301
+ {
302
+ id: { type: 'string', required: true },
303
+ },
304
+ );
305
+
306
+ const result = await this.sdk._fetch(
307
+ `/messaging/email/mailbox/${id}`,
308
+ 'DELETE',
309
+ );
310
+ return result;
311
+ }
312
+
313
+ /**
314
+ * Create a custom alias for a mailbox on a verified domain
315
+ * @param {string} mailboxId - Mailbox ID to create alias for
316
+ * @param {string} emailDomainId - Verified email domain ID
317
+ * @param {string} mailboxName - Mailbox name (the part before @)
318
+ * @param {string} [recordTypeId] - Record type ID for permissions
319
+ * @param {boolean} [isDefault=false] - Whether this alias should be the default for the mailbox
320
+ * @returns {Promise<Object>} Created alias details
321
+ * @example
322
+ * // Add 'support@unbound.cx' alias to mailbox
323
+ * const alias = await sdk.messaging.email.mailboxes.createAlias(
324
+ * '01030181181',
325
+ * 'domainId123',
326
+ * 'support'
327
+ * );
328
+ * // Returns: { id: 'aliasId', address: 'support@unbound.cx', mailboxId: '01030181181' }
329
+ *
330
+ * // Create alias and set as default
331
+ * const defaultAlias = await sdk.messaging.email.mailboxes.createAlias(
332
+ * '01030181181',
333
+ * 'domainId123',
334
+ * 'info',
335
+ * null,
336
+ * true
337
+ * );
338
+ */
339
+ async createAlias(
340
+ mailboxId,
341
+ emailDomainId,
342
+ mailboxName,
343
+ recordTypeId,
344
+ isDefault = false,
345
+ ) {
346
+ const aliasData = {
347
+ emailDomainId,
348
+ mailbox: mailboxName,
349
+ };
350
+ if (recordTypeId !== undefined) aliasData.recordTypeId = recordTypeId;
351
+ if (isDefault !== undefined) aliasData.isDefault = isDefault;
352
+
353
+ this.sdk.validateParams(
354
+ { mailboxId, ...aliasData },
355
+ {
356
+ mailboxId: { type: 'string', required: true },
357
+ emailDomainId: { type: 'string', required: true },
358
+ mailbox: { type: 'string', required: true },
359
+ recordTypeId: { type: 'string', required: false },
360
+ isDefault: { type: 'boolean', required: false },
361
+ },
362
+ );
363
+
364
+ const result = await this.sdk._fetch(
365
+ `/messaging/email/mailbox/${mailboxId}/alias`,
366
+ 'POST',
367
+ {
368
+ body: aliasData,
369
+ },
370
+ );
371
+ return result;
372
+ }
373
+
374
+ /**
375
+ * Update a custom alias
376
+ * @param {string} aliasId - Alias ID to update
377
+ * @param {boolean} [isDefault] - Whether this alias should be the default for the mailbox
378
+ * @param {boolean} [isActive] - Whether the alias is active
379
+ * @param {string} [recordTypeId] - Record type ID for permissions
380
+ * @returns {Promise<Object>} Update result
381
+ * @example
382
+ * // Set alias as default
383
+ * await sdk.messaging.email.mailboxes.updateAlias('aliasId123', true);
384
+ *
385
+ * // Deactivate alias
386
+ * await sdk.messaging.email.mailboxes.updateAlias('aliasId123', undefined, false);
387
+ */
388
+ async updateAlias(aliasId, isDefault, isActive, recordTypeId) {
389
+ const updateData = {};
390
+ if (isDefault !== undefined) updateData.isDefault = isDefault;
391
+ if (isActive !== undefined) updateData.isActive = isActive;
392
+ if (recordTypeId !== undefined) updateData.recordTypeId = recordTypeId;
393
+
394
+ this.sdk.validateParams(
395
+ { aliasId, ...updateData },
396
+ {
397
+ aliasId: { type: 'string', required: true },
398
+ isDefault: { type: 'boolean', required: false },
399
+ isActive: { type: 'boolean', required: false },
400
+ recordTypeId: { type: 'string', required: false },
401
+ },
402
+ );
403
+
404
+ const result = await this.sdk._fetch(
405
+ `/messaging/email/mailbox/alias/${aliasId}`,
406
+ 'PUT',
407
+ {
408
+ body: updateData,
409
+ },
410
+ );
411
+ return result;
412
+ }
413
+
414
+ /**
415
+ * Delete a custom alias
416
+ * @param {string} aliasId - Alias ID to delete
417
+ * @returns {Promise<Object>} Deletion result
418
+ * @example
419
+ * await sdk.messaging.email.mailboxes.deleteAlias('aliasId123');
420
+ */
421
+ async deleteAlias(aliasId) {
422
+ this.sdk.validateParams(
423
+ { aliasId },
424
+ {
425
+ aliasId: { type: 'string', required: true },
426
+ },
427
+ );
428
+
429
+ const result = await this.sdk._fetch(
430
+ `/messaging/email/mailbox/alias/${aliasId}`,
431
+ 'DELETE',
432
+ );
433
+ return result;
434
+ }
435
+
436
+ /**
437
+ * Get list of folders for a specific mailbox
438
+ * @param {string} mailboxId - Mailbox ID to get folders for
439
+ * @returns {Promise<Object>} List of folders including standard and custom folders
440
+ * @example
441
+ * const result = await sdk.messaging.email.mailboxes.listFolders('01030181181');
442
+ * // Returns: { folders: ['open', 'completed', 'trash', 'spam', 'archive', 'important'] }
443
+ */
444
+ async listFolders(mailboxId) {
445
+ this.sdk.validateParams(
446
+ { mailboxId },
447
+ {
448
+ mailboxId: { type: 'string', required: true },
449
+ },
450
+ );
451
+
452
+ const result = await this.sdk._fetch(
453
+ `/messaging/email/mailbox/${mailboxId}/folders`,
454
+ 'GET',
455
+ );
456
+ return result;
457
+ }
458
+ }
@@ -0,0 +1,96 @@
1
+ export class EmailQueueService {
2
+ constructor(sdk) {
3
+ this.sdk = sdk;
4
+ }
5
+
6
+ /**
7
+ * Get email queue items with pagination and status filtering
8
+ * @param {Object} [params] - Queue query parameters
9
+ * @param {number} [params.page=1] - Page number (1-based)
10
+ * @param {number} [params.limit=50] - Number of items per page (max 100)
11
+ * @param {string} [params.status='queued'] - Filter by status: 'queued', 'sent', 'delivered', 'failed'
12
+ * @returns {Promise<Object>} Paginated queue items with metadata
13
+ * @example
14
+ * // Get first page of queued emails
15
+ * const queue = await sdk.messaging.email.queue.list({ page: 1, limit: 25, status: 'queued' });
16
+ * // Returns: {
17
+ * // items: [{
18
+ * // id, status, to, from, subject, carrier, carrierId,
19
+ * // createdAt, lastStatusUpdatedAt, processingTimeSeconds
20
+ * // }],
21
+ * // pagination: {
22
+ * // page, limit, totalItems, totalPages, hasNextPage, hasPreviousPage
23
+ * // },
24
+ * // filter: { status }
25
+ * // }
26
+ */
27
+ async list({ page, limit, status } = {}) {
28
+ const options = { query: {} };
29
+ if (page !== undefined) options.query.page = page;
30
+ if (limit !== undefined) options.query.limit = limit;
31
+ if (status) options.query.status = status;
32
+
33
+ const result = await this.sdk._fetch(
34
+ '/messaging/email/queue',
35
+ 'GET',
36
+ options,
37
+ );
38
+ return result;
39
+ }
40
+
41
+ /**
42
+ * Get queued emails only (convenience method)
43
+ * @param {Object} [params] - Query parameters
44
+ * @param {number} [params.page=1] - Page number (1-based)
45
+ * @param {number} [params.limit=50] - Number of items per page (max 100)
46
+ * @returns {Promise<Object>} Paginated queued emails
47
+ * @example
48
+ * // Get pending emails waiting to be sent
49
+ * const pending = await sdk.messaging.email.queue.getQueued({ page: 1, limit: 50 });
50
+ */
51
+ async getQueued({ page, limit } = {}) {
52
+ return this.list({ page, limit, status: 'queued' });
53
+ }
54
+
55
+ /**
56
+ * Get failed emails only (convenience method)
57
+ * @param {Object} [params] - Query parameters
58
+ * @param {number} [params.page=1] - Page number (1-based)
59
+ * @param {number} [params.limit=50] - Number of items per page (max 100)
60
+ * @returns {Promise<Object>} Paginated failed emails
61
+ * @example
62
+ * // Get emails that failed to send
63
+ * const failed = await sdk.messaging.email.queue.getFailed({ page: 1, limit: 50 });
64
+ */
65
+ async getFailed({ page, limit } = {}) {
66
+ return this.list({ page, limit, status: 'failed' });
67
+ }
68
+
69
+ /**
70
+ * Get sent emails only (convenience method)
71
+ * @param {Object} [params] - Query parameters
72
+ * @param {number} [params.page=1] - Page number (1-based)
73
+ * @param {number} [params.limit=50] - Number of items per page (max 100)
74
+ * @returns {Promise<Object>} Paginated sent emails
75
+ * @example
76
+ * // Get emails that have been sent successfully
77
+ * const sent = await sdk.messaging.email.queue.getSent({ page: 1, limit: 50 });
78
+ */
79
+ async getSent({ page, limit } = {}) {
80
+ return this.list({ page, limit, status: 'sent' });
81
+ }
82
+
83
+ /**
84
+ * Get delivered emails only (convenience method)
85
+ * @param {Object} [params] - Query parameters
86
+ * @param {number} [params.page=1] - Page number (1-based)
87
+ * @param {number} [params.limit=50] - Number of items per page (max 100)
88
+ * @returns {Promise<Object>} Paginated delivered emails
89
+ * @example
90
+ * // Get emails that have been delivered to recipients
91
+ * const delivered = await sdk.messaging.email.queue.getDelivered({ page: 1, limit: 50 });
92
+ */
93
+ async getDelivered({ page, limit } = {}) {
94
+ return this.list({ page, limit, status: 'delivered' });
95
+ }
96
+ }