@stream-io/node-sdk 0.4.18 → 0.4.20

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.
@@ -6,10 +6,15 @@ import { StreamChatClient } from './StreamChatClient';
6
6
  import { CallTokenPayload, UserTokenPayload } from './types';
7
7
  import { QueryBannedUsersPayload, UserRequest } from './gen/models';
8
8
  import { StreamModerationClient } from './StreamModerationClient';
9
+ import { Agent } from 'undici';
9
10
 
10
11
  export interface StreamClientOptions {
11
12
  timeout?: number;
12
13
  basePath?: string;
14
+ /** The max number of clients to create. `null` if no limit. Default is 100. Has no effect if `agent` is provided. */
15
+ maxConnections?: number | null;
16
+ /** The [HTTP Agent](https://undici.nodejs.org/#/docs/api/Agent.md) to use. */
17
+ agent?: Agent;
13
18
  }
14
19
 
15
20
  export class StreamClient extends CommonApi {
@@ -19,6 +24,7 @@ export class StreamClient extends CommonApi {
19
24
  public readonly options: StreamClientOptions = {};
20
25
 
21
26
  private static readonly DEFAULT_TIMEOUT = 3000;
27
+ private static readonly MAX_CONNECTIONS = 100;
22
28
 
23
29
  /**
24
30
  *
@@ -33,9 +39,17 @@ export class StreamClient extends CommonApi {
33
39
  ) {
34
40
  const token = JWTServerToken(secret);
35
41
  const timeout = config?.timeout ?? StreamClient.DEFAULT_TIMEOUT;
42
+ const agent =
43
+ config?.agent ??
44
+ new Agent({
45
+ connections:
46
+ config?.maxConnections === undefined
47
+ ? StreamClient.MAX_CONNECTIONS
48
+ : config.maxConnections,
49
+ });
36
50
  const chatBaseUrl = config?.basePath ?? 'https://chat.stream-io-api.com';
37
51
  const videoBaseUrl = config?.basePath ?? 'https://video.stream-io-api.com';
38
- super({ apiKey, token, timeout, baseUrl: chatBaseUrl });
52
+ super({ apiKey, token, timeout, baseUrl: chatBaseUrl, agent });
39
53
 
40
54
  this.video = new StreamVideoClient({
41
55
  streamClient: this,
@@ -43,18 +57,21 @@ export class StreamClient extends CommonApi {
43
57
  token,
44
58
  timeout,
45
59
  baseUrl: videoBaseUrl,
60
+ agent,
46
61
  });
47
62
  this.chat = new StreamChatClient({
48
63
  apiKey,
49
64
  token,
50
65
  timeout,
51
66
  baseUrl: chatBaseUrl,
67
+ agent,
52
68
  });
53
69
  this.moderation = new StreamModerationClient({
54
70
  apiKey,
55
71
  token,
56
72
  timeout,
57
73
  baseUrl: chatBaseUrl,
74
+ agent,
58
75
  });
59
76
  }
60
77
 
@@ -7,6 +7,7 @@ import {
7
7
  EventResponse,
8
8
  FileUploadRequest,
9
9
  FileUploadResponse,
10
+ GetDraftResponse,
10
11
  GetManyMessagesResponse,
11
12
  HideChannelRequest,
12
13
  HideChannelResponse,
@@ -83,6 +84,34 @@ export class ChannelApi {
83
84
  });
84
85
  };
85
86
 
87
+ deleteDraft = (request?: {
88
+ parent_id?: string;
89
+ user_id?: string;
90
+ }): Promise<StreamResponse<Response>> => {
91
+ if (!this.id) {
92
+ throw new Error(
93
+ `Channel isn't yet created, call getOrCreateDistinctChannel() before this operation`,
94
+ );
95
+ }
96
+ return this.chatApi.deleteDraft({
97
+ id: this.id,
98
+ type: this.type,
99
+ ...request,
100
+ });
101
+ };
102
+
103
+ getDraft = (request?: {
104
+ parent_id?: string;
105
+ user_id?: string;
106
+ }): Promise<StreamResponse<GetDraftResponse>> => {
107
+ if (!this.id) {
108
+ throw new Error(
109
+ `Channel isn't yet created, call getOrCreateDistinctChannel() before this operation`,
110
+ );
111
+ }
112
+ return this.chatApi.getDraft({ id: this.id, type: this.type, ...request });
113
+ };
114
+
86
115
  sendEvent = (
87
116
  request: SendEventRequest,
88
117
  ): Promise<StreamResponse<EventResponse>> => {
@@ -27,6 +27,7 @@ import {
27
27
  GetCampaignResponse,
28
28
  GetChannelTypeResponse,
29
29
  GetCommandResponse,
30
+ GetDraftResponse,
30
31
  GetManyMessagesResponse,
31
32
  GetMessageResponse,
32
33
  GetReactionsResponse,
@@ -58,6 +59,8 @@ import {
58
59
  QueryCampaignsResponse,
59
60
  QueryChannelsRequest,
60
61
  QueryChannelsResponse,
62
+ QueryDraftsRequest,
63
+ QueryDraftsResponse,
61
64
  QueryMembersPayload,
62
65
  QueryMessageFlagsPayload,
63
66
  QueryMessageFlagsResponse,
@@ -129,6 +132,7 @@ export class ChatApi extends BaseApi {
129
132
  limit: request?.limit,
130
133
  next: request?.next,
131
134
  prev: request?.prev,
135
+ user_limit: request?.user_limit,
132
136
  sort: request?.sort,
133
137
  filter: request?.filter,
134
138
  };
@@ -144,14 +148,22 @@ export class ChatApi extends BaseApi {
144
148
 
145
149
  getCampaign = async (request: {
146
150
  id: string;
151
+ prev?: string;
152
+ next?: string;
153
+ limit?: number;
147
154
  }): Promise<StreamResponse<GetCampaignResponse>> => {
155
+ const queryParams = {
156
+ prev: request?.prev,
157
+ next: request?.next,
158
+ limit: request?.limit,
159
+ };
148
160
  const pathParams = {
149
161
  id: request?.id,
150
162
  };
151
163
 
152
164
  const response = await this.sendRequest<
153
165
  StreamResponse<GetCampaignResponse>
154
- >('GET', '/api/v2/chat/campaigns/{id}', pathParams, undefined);
166
+ >('GET', '/api/v2/chat/campaigns/{id}', pathParams, queryParams);
155
167
 
156
168
  decoders.GetCampaignResponse?.(response.body);
157
169
 
@@ -378,6 +390,60 @@ export class ChatApi extends BaseApi {
378
390
  return { ...response.body, metadata: response.metadata };
379
391
  };
380
392
 
393
+ deleteDraft = async (request: {
394
+ type: string;
395
+ id: string;
396
+ parent_id?: string;
397
+ user_id?: string;
398
+ }): Promise<StreamResponse<Response>> => {
399
+ const queryParams = {
400
+ parent_id: request?.parent_id,
401
+ user_id: request?.user_id,
402
+ };
403
+ const pathParams = {
404
+ type: request?.type,
405
+ id: request?.id,
406
+ };
407
+
408
+ const response = await this.sendRequest<StreamResponse<Response>>(
409
+ 'DELETE',
410
+ '/api/v2/chat/channels/{type}/{id}/draft',
411
+ pathParams,
412
+ queryParams,
413
+ );
414
+
415
+ decoders.Response?.(response.body);
416
+
417
+ return { ...response.body, metadata: response.metadata };
418
+ };
419
+
420
+ getDraft = async (request: {
421
+ type: string;
422
+ id: string;
423
+ parent_id?: string;
424
+ user_id?: string;
425
+ }): Promise<StreamResponse<GetDraftResponse>> => {
426
+ const queryParams = {
427
+ parent_id: request?.parent_id,
428
+ user_id: request?.user_id,
429
+ };
430
+ const pathParams = {
431
+ type: request?.type,
432
+ id: request?.id,
433
+ };
434
+
435
+ const response = await this.sendRequest<StreamResponse<GetDraftResponse>>(
436
+ 'GET',
437
+ '/api/v2/chat/channels/{type}/{id}/draft',
438
+ pathParams,
439
+ queryParams,
440
+ );
441
+
442
+ decoders.GetDraftResponse?.(response.body);
443
+
444
+ return { ...response.body, metadata: response.metadata };
445
+ };
446
+
381
447
  sendEvent = async (
382
448
  request: SendEventRequest & { type: string; id: string },
383
449
  ): Promise<StreamResponse<EventResponse>> => {
@@ -991,6 +1057,28 @@ export class ChatApi extends BaseApi {
991
1057
  return { ...response.body, metadata: response.metadata };
992
1058
  };
993
1059
 
1060
+ queryDrafts = async (
1061
+ request?: QueryDraftsRequest,
1062
+ ): Promise<StreamResponse<QueryDraftsResponse>> => {
1063
+ const body = {
1064
+ limit: request?.limit,
1065
+ next: request?.next,
1066
+ prev: request?.prev,
1067
+ user_id: request?.user_id,
1068
+ sort: request?.sort,
1069
+ filter: request?.filter,
1070
+ user: request?.user,
1071
+ };
1072
+
1073
+ const response = await this.sendRequest<
1074
+ StreamResponse<QueryDraftsResponse>
1075
+ >('POST', '/api/v2/chat/drafts/query', undefined, undefined, body);
1076
+
1077
+ decoders.QueryDraftsResponse?.(response.body);
1078
+
1079
+ return { ...response.body, metadata: response.metadata };
1080
+ };
1081
+
994
1082
  exportChannels = async (
995
1083
  request: ExportChannelsRequest,
996
1084
  ): Promise<StreamResponse<ExportChannelsResponse>> => {
@@ -435,6 +435,8 @@ decoders.ChannelStateResponse = (input?: Record<string, any>) => {
435
435
 
436
436
  channel: { type: 'ChannelResponse', isSingle: true },
437
437
 
438
+ draft: { type: 'DraftResponse', isSingle: true },
439
+
438
440
  membership: { type: 'ChannelMember', isSingle: true },
439
441
 
440
442
  push_preferences: { type: 'ChannelPushPreferences', isSingle: true },
@@ -462,6 +464,8 @@ decoders.ChannelStateResponseFields = (input?: Record<string, any>) => {
462
464
 
463
465
  channel: { type: 'ChannelResponse', isSingle: true },
464
466
 
467
+ draft: { type: 'DraftResponse', isSingle: true },
468
+
465
469
  membership: { type: 'ChannelMember', isSingle: true },
466
470
 
467
471
  push_preferences: { type: 'ChannelPushPreferences', isSingle: true },
@@ -616,6 +620,28 @@ decoders.DeviceResponse = (input?: Record<string, any>) => {
616
620
  return decode(typeMappings, input);
617
621
  };
618
622
 
623
+ decoders.DraftPayloadResponse = (input?: Record<string, any>) => {
624
+ const typeMappings: TypeMapping = {
625
+ mentioned_users: { type: 'UserResponse', isSingle: false },
626
+ };
627
+ return decode(typeMappings, input);
628
+ };
629
+
630
+ decoders.DraftResponse = (input?: Record<string, any>) => {
631
+ const typeMappings: TypeMapping = {
632
+ created_at: { type: 'DatetimeType', isSingle: true },
633
+
634
+ message: { type: 'DraftPayloadResponse', isSingle: true },
635
+
636
+ channel: { type: 'ChannelResponse', isSingle: true },
637
+
638
+ parent_message: { type: 'MessageResponse', isSingle: true },
639
+
640
+ quoted_message: { type: 'MessageResponse', isSingle: true },
641
+ };
642
+ return decode(typeMappings, input);
643
+ };
644
+
619
645
  decoders.EgressRTMPResponse = (input?: Record<string, any>) => {
620
646
  const typeMappings: TypeMapping = {
621
647
  started_at: { type: 'DatetimeType', isSingle: true },
@@ -688,7 +714,7 @@ decoders.ExportUserResponse = (input?: Record<string, any>) => {
688
714
  return decode(typeMappings, input);
689
715
  };
690
716
 
691
- decoders.Flag2 = (input?: Record<string, any>) => {
717
+ decoders.Flag = (input?: Record<string, any>) => {
692
718
  const typeMappings: TypeMapping = {
693
719
  created_at: { type: 'DatetimeType', isSingle: true },
694
720
 
@@ -699,17 +725,6 @@ decoders.Flag2 = (input?: Record<string, any>) => {
699
725
  return decode(typeMappings, input);
700
726
  };
701
727
 
702
- decoders.Flag2Response = (input?: Record<string, any>) => {
703
- const typeMappings: TypeMapping = {
704
- created_at: { type: 'DatetimeType', isSingle: true },
705
-
706
- updated_at: { type: 'DatetimeType', isSingle: true },
707
-
708
- user: { type: 'UserResponse', isSingle: true },
709
- };
710
- return decode(typeMappings, input);
711
- };
712
-
713
728
  decoders.FlagDetails = (input?: Record<string, any>) => {
714
729
  const typeMappings: TypeMapping = {
715
730
  automod: { type: 'AutomodDetails', isSingle: true },
@@ -736,6 +751,8 @@ decoders.FullUserResponse = (input?: Record<string, any>) => {
736
751
 
737
752
  mutes: { type: 'UserMuteResponse', isSingle: false },
738
753
 
754
+ ban_expires: { type: 'DatetimeType', isSingle: true },
755
+
739
756
  deactivated_at: { type: 'DatetimeType', isSingle: true },
740
757
 
741
758
  deleted_at: { type: 'DatetimeType', isSingle: true },
@@ -786,13 +803,6 @@ decoders.GetCallTypeResponse = (input?: Record<string, any>) => {
786
803
  return decode(typeMappings, input);
787
804
  };
788
805
 
789
- decoders.GetCampaignResponse = (input?: Record<string, any>) => {
790
- const typeMappings: TypeMapping = {
791
- campaign: { type: 'CampaignResponse', isSingle: true },
792
- };
793
- return decode(typeMappings, input);
794
- };
795
-
796
806
  decoders.GetChannelTypeResponse = (input?: Record<string, any>) => {
797
807
  const typeMappings: TypeMapping = {
798
808
  created_at: { type: 'DatetimeType', isSingle: true },
@@ -820,6 +830,13 @@ decoders.GetConfigResponse = (input?: Record<string, any>) => {
820
830
  return decode(typeMappings, input);
821
831
  };
822
832
 
833
+ decoders.GetDraftResponse = (input?: Record<string, any>) => {
834
+ const typeMappings: TypeMapping = {
835
+ draft: { type: 'DraftResponse', isSingle: true },
836
+ };
837
+ return decode(typeMappings, input);
838
+ };
839
+
823
840
  decoders.GetImportResponse = (input?: Record<string, any>) => {
824
841
  const typeMappings: TypeMapping = {
825
842
  import_task: { type: 'ImportTask', isSingle: true },
@@ -896,17 +913,6 @@ decoders.GetThreadResponse = (input?: Record<string, any>) => {
896
913
  return decode(typeMappings, input);
897
914
  };
898
915
 
899
- decoders.GetUserModerationReportResponse = (input?: Record<string, any>) => {
900
- const typeMappings: TypeMapping = {
901
- user_blocks: { type: 'UserBlock', isSingle: false },
902
-
903
- user_mutes: { type: 'UserMute', isSingle: false },
904
-
905
- user: { type: 'UserResponse', isSingle: true },
906
- };
907
- return decode(typeMappings, input);
908
- };
909
-
910
916
  decoders.GoLiveResponse = (input?: Record<string, any>) => {
911
917
  const typeMappings: TypeMapping = {
912
918
  call: { type: 'CallResponse', isSingle: true },
@@ -1144,6 +1150,8 @@ decoders.MessageResponse = (input?: Record<string, any>) => {
1144
1150
 
1145
1151
  thread_participants: { type: 'UserResponse', isSingle: false },
1146
1152
 
1153
+ draft: { type: 'DraftResponse', isSingle: true },
1154
+
1147
1155
  pinned_by: { type: 'UserResponse', isSingle: true },
1148
1156
 
1149
1157
  poll: { type: 'PollResponseData', isSingle: true },
@@ -1181,6 +1189,8 @@ decoders.MessageWithChannelResponse = (input?: Record<string, any>) => {
1181
1189
 
1182
1190
  thread_participants: { type: 'UserResponse', isSingle: false },
1183
1191
 
1192
+ draft: { type: 'DraftResponse', isSingle: true },
1193
+
1184
1194
  pinned_by: { type: 'UserResponse', isSingle: true },
1185
1195
 
1186
1196
  poll: { type: 'PollResponseData', isSingle: true },
@@ -1192,15 +1202,6 @@ decoders.MessageWithChannelResponse = (input?: Record<string, any>) => {
1192
1202
  return decode(typeMappings, input);
1193
1203
  };
1194
1204
 
1195
- decoders.ModerationUsageStats = (input?: Record<string, any>) => {
1196
- const typeMappings: TypeMapping = {
1197
- reference_date: { type: 'DatetimeType', isSingle: true },
1198
-
1199
- updated_at: { type: 'DatetimeType', isSingle: true },
1200
- };
1201
- return decode(typeMappings, input);
1202
- };
1203
-
1204
1205
  decoders.MuteChannelResponse = (input?: Record<string, any>) => {
1205
1206
  const typeMappings: TypeMapping = {
1206
1207
  channel_mutes: { type: 'ChannelMute', isSingle: false },
@@ -1440,6 +1441,13 @@ decoders.QueryChannelsResponse = (input?: Record<string, any>) => {
1440
1441
  return decode(typeMappings, input);
1441
1442
  };
1442
1443
 
1444
+ decoders.QueryDraftsResponse = (input?: Record<string, any>) => {
1445
+ const typeMappings: TypeMapping = {
1446
+ drafts: { type: 'DraftResponse', isSingle: false },
1447
+ };
1448
+ return decode(typeMappings, input);
1449
+ };
1450
+
1443
1451
  decoders.QueryFeedModerationTemplate = (input?: Record<string, any>) => {
1444
1452
  const typeMappings: TypeMapping = {
1445
1453
  created_at: { type: 'DatetimeType', isSingle: true },
@@ -1528,13 +1536,6 @@ decoders.QueryThreadsResponse = (input?: Record<string, any>) => {
1528
1536
  return decode(typeMappings, input);
1529
1537
  };
1530
1538
 
1531
- decoders.QueryUsageStatsResponse = (input?: Record<string, any>) => {
1532
- const typeMappings: TypeMapping = {
1533
- items: { type: 'ModerationUsageStats', isSingle: false },
1534
- };
1535
- return decode(typeMappings, input);
1536
- };
1537
-
1538
1539
  decoders.QueryUsersResponse = (input?: Record<string, any>) => {
1539
1540
  const typeMappings: TypeMapping = {
1540
1541
  users: { type: 'FullUserResponse', isSingle: false },
@@ -1599,7 +1600,7 @@ decoders.ReviewQueueItem = (input?: Record<string, any>) => {
1599
1600
 
1600
1601
  bans: { type: 'Ban', isSingle: false },
1601
1602
 
1602
- flags: { type: 'Flag2', isSingle: false },
1603
+ flags: { type: 'Flag', isSingle: false },
1603
1604
 
1604
1605
  assigned_to: { type: 'User', isSingle: true },
1605
1606
 
@@ -1608,6 +1609,8 @@ decoders.ReviewQueueItem = (input?: Record<string, any>) => {
1608
1609
  feeds_v2_reaction: { type: 'Reaction', isSingle: true },
1609
1610
 
1610
1611
  message: { type: 'Message', isSingle: true },
1612
+
1613
+ reaction: { type: 'Reaction', isSingle: true },
1611
1614
  };
1612
1615
  return decode(typeMappings, input);
1613
1616
  };
@@ -1622,8 +1625,6 @@ decoders.ReviewQueueItemResponse = (input?: Record<string, any>) => {
1622
1625
 
1623
1626
  bans: { type: 'Ban', isSingle: false },
1624
1627
 
1625
- flags: { type: 'Flag2Response', isSingle: false },
1626
-
1627
1628
  completed_at: { type: 'DatetimeType', isSingle: true },
1628
1629
 
1629
1630
  reviewed_at: { type: 'DatetimeType', isSingle: true },
@@ -1635,6 +1636,8 @@ decoders.ReviewQueueItemResponse = (input?: Record<string, any>) => {
1635
1636
  feeds_v2_reaction: { type: 'Reaction', isSingle: true },
1636
1637
 
1637
1638
  message: { type: 'MessageResponse', isSingle: true },
1639
+
1640
+ reaction: { type: 'Reaction', isSingle: true },
1638
1641
  };
1639
1642
  return decode(typeMappings, input);
1640
1643
  };
@@ -1681,6 +1684,8 @@ decoders.SearchResultMessage = (input?: Record<string, any>) => {
1681
1684
 
1682
1685
  channel: { type: 'ChannelResponse', isSingle: true },
1683
1686
 
1687
+ draft: { type: 'DraftResponse', isSingle: true },
1688
+
1684
1689
  pinned_by: { type: 'UserResponse', isSingle: true },
1685
1690
 
1686
1691
  poll: { type: 'PollResponseData', isSingle: true },
@@ -1737,13 +1742,6 @@ decoders.SendReactionResponse = (input?: Record<string, any>) => {
1737
1742
  return decode(typeMappings, input);
1738
1743
  };
1739
1744
 
1740
- decoders.StartCampaignResponse = (input?: Record<string, any>) => {
1741
- const typeMappings: TypeMapping = {
1742
- campaign: { type: 'CampaignResponse', isSingle: true },
1743
- };
1744
- return decode(typeMappings, input);
1745
- };
1746
-
1747
1745
  decoders.StopLiveResponse = (input?: Record<string, any>) => {
1748
1746
  const typeMappings: TypeMapping = {
1749
1747
  call: { type: 'CallResponse', isSingle: true },
@@ -1814,6 +1812,8 @@ decoders.ThreadStateResponse = (input?: Record<string, any>) => {
1814
1812
 
1815
1813
  created_by: { type: 'UserResponse', isSingle: true },
1816
1814
 
1815
+ draft: { type: 'DraftResponse', isSingle: true },
1816
+
1817
1817
  parent_message: { type: 'MessageResponse', isSingle: true },
1818
1818
  };
1819
1819
  return decode(typeMappings, input);
@@ -2012,13 +2012,6 @@ decoders.User = (input?: Record<string, any>) => {
2012
2012
  return decode(typeMappings, input);
2013
2013
  };
2014
2014
 
2015
- decoders.UserBlock = (input?: Record<string, any>) => {
2016
- const typeMappings: TypeMapping = {
2017
- created_at: { type: 'DatetimeType', isSingle: true },
2018
- };
2019
- return decode(typeMappings, input);
2020
- };
2021
-
2022
2015
  decoders.UserMute = (input?: Record<string, any>) => {
2023
2016
  const typeMappings: TypeMapping = {
2024
2017
  created_at: { type: 'DatetimeType', isSingle: true },