@stream-io/video-client 0.0.6 → 0.0.8
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.
- package/CHANGELOG.md +14 -0
- package/dist/index.browser.es.js +41 -10
- package/dist/index.browser.es.js.map +1 -1
- package/dist/index.cjs.js +41 -10
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.es.js +41 -10
- package/dist/index.es.js.map +1 -1
- package/dist/src/Call.d.ts +6 -0
- package/dist/src/StreamVideoClient.d.ts +5 -3
- package/package.json +1 -1
- package/src/Call.ts +16 -1
- package/src/StreamVideoClient.ts +32 -8
- package/src/rtc/signal.ts +3 -3
package/dist/src/Call.d.ts
CHANGED
|
@@ -30,6 +30,12 @@ export declare class Call {
|
|
|
30
30
|
* The state of this call.
|
|
31
31
|
*/
|
|
32
32
|
readonly state: CallState;
|
|
33
|
+
private rejoinPromise;
|
|
34
|
+
/**
|
|
35
|
+
* A promise that exposes the reconnection logic
|
|
36
|
+
* The use-case is for the react-native platform where online/offline events are not available in the window
|
|
37
|
+
*/
|
|
38
|
+
get rejoin(): (() => Promise<void>) | undefined;
|
|
33
39
|
/**
|
|
34
40
|
* Flag indicating whether this call is "watched" and receives
|
|
35
41
|
* updates from the backend.
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { Call } from './Call';
|
|
2
2
|
import { StreamClient } from './coordinator/connection/client';
|
|
3
3
|
import { StreamVideoReadOnlyStateStore } from './store';
|
|
4
|
-
import type { CreateCallTypeRequest, CreateCallTypeResponse, CreateDeviceRequest, CreateGuestRequest, CreateGuestResponse, GetCallTypeResponse, GetEdgesResponse, ListCallTypeResponse, ListDevicesResponse, QueryCallsRequest, UpdateCallTypeRequest, UpdateCallTypeResponse } from './gen/coordinator';
|
|
4
|
+
import type { ConnectedEvent, CreateCallTypeRequest, CreateCallTypeResponse, CreateDeviceRequest, CreateGuestRequest, CreateGuestResponse, GetCallTypeResponse, GetEdgesResponse, ListCallTypeResponse, ListDevicesResponse, QueryCallsRequest, UpdateCallTypeRequest, UpdateCallTypeResponse } from './gen/coordinator';
|
|
5
5
|
import type { EventHandler, EventTypes, StreamClientOptions, TokenOrProvider, User } from './coordinator/connection/types';
|
|
6
6
|
/**
|
|
7
7
|
* A `StreamVideoClient` instance lets you communicate with our API, and authenticate users.
|
|
@@ -14,6 +14,8 @@ export declare class StreamVideoClient {
|
|
|
14
14
|
private readonly writeableStateStore;
|
|
15
15
|
streamClient: StreamClient;
|
|
16
16
|
private eventHandlersToUnregister;
|
|
17
|
+
private connectionPromise;
|
|
18
|
+
private disconnectionPromise;
|
|
17
19
|
/**
|
|
18
20
|
* You should create only one instance of `StreamVideoClient`.
|
|
19
21
|
* @param apiKey your Stream API key
|
|
@@ -28,14 +30,14 @@ export declare class StreamVideoClient {
|
|
|
28
30
|
* @param user the user to connect.
|
|
29
31
|
* @param tokenOrProvider a token or a function that returns a token.
|
|
30
32
|
*/
|
|
31
|
-
connectUser: (user: User, tokenOrProvider: TokenOrProvider) => Promise<void |
|
|
33
|
+
connectUser: (user: User, tokenOrProvider: TokenOrProvider) => Promise<void | ConnectedEvent>;
|
|
32
34
|
/**
|
|
33
35
|
* Connects the given anonymous user to the client.
|
|
34
36
|
*
|
|
35
37
|
* @param user the user to connect.
|
|
36
38
|
* @param tokenOrProvider a token or a function that returns a token.
|
|
37
39
|
*/
|
|
38
|
-
connectAnonymousUser: (user: User, tokenOrProvider: TokenOrProvider) => Promise<void>;
|
|
40
|
+
connectAnonymousUser: (user: User, tokenOrProvider: TokenOrProvider) => Promise<void | ConnectedEvent>;
|
|
39
41
|
/**
|
|
40
42
|
* Disconnects the currently connected user from the client.
|
|
41
43
|
*
|
package/package.json
CHANGED
package/src/Call.ts
CHANGED
|
@@ -135,6 +135,16 @@ export class Call {
|
|
|
135
135
|
*/
|
|
136
136
|
readonly state = new CallState();
|
|
137
137
|
|
|
138
|
+
private rejoinPromise: (() => Promise<void>) | undefined;
|
|
139
|
+
|
|
140
|
+
/**
|
|
141
|
+
* A promise that exposes the reconnection logic
|
|
142
|
+
* The use-case is for the react-native platform where online/offline events are not available in the window
|
|
143
|
+
*/
|
|
144
|
+
get rejoin(): (() => Promise<void>) | undefined {
|
|
145
|
+
return this.rejoinPromise;
|
|
146
|
+
}
|
|
147
|
+
|
|
138
148
|
/**
|
|
139
149
|
* Flag indicating whether this call is "watched" and receives
|
|
140
150
|
* updates from the backend.
|
|
@@ -370,6 +380,7 @@ export class Call {
|
|
|
370
380
|
if (callingState === CallingState.LEFT) {
|
|
371
381
|
throw new Error('Cannot leave call that has already been left.');
|
|
372
382
|
}
|
|
383
|
+
this.rejoinPromise = undefined;
|
|
373
384
|
|
|
374
385
|
if (this.ringing) {
|
|
375
386
|
// I'm the one who started the call, so I should cancel it.
|
|
@@ -642,7 +653,7 @@ export class Call {
|
|
|
642
653
|
await sleep(retryInterval(this.reconnectAttempts));
|
|
643
654
|
await this.join(data);
|
|
644
655
|
console.log(`Rejoin: ${this.reconnectAttempts} successful!`);
|
|
645
|
-
if (localParticipant) {
|
|
656
|
+
if (localParticipant && !isReactNative()) {
|
|
646
657
|
const {
|
|
647
658
|
audioStream,
|
|
648
659
|
videoStream,
|
|
@@ -657,6 +668,8 @@ export class Call {
|
|
|
657
668
|
console.log(`Rejoin: state restored ${this.reconnectAttempts}`);
|
|
658
669
|
};
|
|
659
670
|
|
|
671
|
+
this.rejoinPromise = rejoin;
|
|
672
|
+
|
|
660
673
|
// reconnect if the connection was closed unexpectedly. example:
|
|
661
674
|
// - SFU crash or restart
|
|
662
675
|
// - network change
|
|
@@ -667,6 +680,8 @@ export class Call {
|
|
|
667
680
|
// do nothing if the connection was closed because of a policy violation
|
|
668
681
|
// e.g., the user has been blocked by an admin or moderator
|
|
669
682
|
if (e.code === KnownCodes.WS_POLICY_VIOLATION) return;
|
|
683
|
+
// do nothing for react-native as its handled by SDK
|
|
684
|
+
if (isReactNative()) return;
|
|
670
685
|
if (this.reconnectAttempts < this.maxReconnectAttempts) {
|
|
671
686
|
rejoin().catch(() => {
|
|
672
687
|
console.log(
|
package/src/StreamVideoClient.ts
CHANGED
|
@@ -5,6 +5,7 @@ import {
|
|
|
5
5
|
StreamVideoWriteableStateStore,
|
|
6
6
|
} from './store';
|
|
7
7
|
import type {
|
|
8
|
+
ConnectedEvent,
|
|
8
9
|
CreateCallTypeRequest,
|
|
9
10
|
CreateCallTypeResponse,
|
|
10
11
|
CreateDeviceRequest,
|
|
@@ -40,6 +41,8 @@ export class StreamVideoClient {
|
|
|
40
41
|
streamClient: StreamClient;
|
|
41
42
|
|
|
42
43
|
private eventHandlersToUnregister: Array<() => void> = [];
|
|
44
|
+
private connectionPromise: Promise<void | ConnectedEvent> | undefined;
|
|
45
|
+
private disconnectionPromise: Promise<void> | undefined;
|
|
43
46
|
|
|
44
47
|
/**
|
|
45
48
|
* You should create only one instance of `StreamVideoClient`.
|
|
@@ -67,11 +70,19 @@ export class StreamVideoClient {
|
|
|
67
70
|
* @param tokenOrProvider a token or a function that returns a token.
|
|
68
71
|
*/
|
|
69
72
|
connectUser = async (user: User, tokenOrProvider: TokenOrProvider) => {
|
|
70
|
-
const
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
73
|
+
const connectUser = () => {
|
|
74
|
+
return this.streamClient.connectUser(
|
|
75
|
+
// @ts-expect-error
|
|
76
|
+
user,
|
|
77
|
+
tokenOrProvider,
|
|
78
|
+
);
|
|
79
|
+
};
|
|
80
|
+
this.connectionPromise = this.disconnectionPromise
|
|
81
|
+
? this.disconnectionPromise.then(() => connectUser())
|
|
82
|
+
: connectUser();
|
|
83
|
+
|
|
84
|
+
this.connectionPromise?.finally(() => (this.connectionPromise = undefined));
|
|
85
|
+
const connectUserResponse = await this.connectionPromise;
|
|
75
86
|
this.writeableStateStore.setConnectedUser(user);
|
|
76
87
|
|
|
77
88
|
this.eventHandlersToUnregister.push(
|
|
@@ -163,8 +174,14 @@ export class StreamVideoClient {
|
|
|
163
174
|
user: User,
|
|
164
175
|
tokenOrProvider: TokenOrProvider,
|
|
165
176
|
) => {
|
|
166
|
-
|
|
167
|
-
|
|
177
|
+
const connectAnonymousUser = () =>
|
|
178
|
+
// @ts-expect-error
|
|
179
|
+
this.streamClient.connectAnonymousUser(user, tokenOrProvider);
|
|
180
|
+
this.connectionPromise = this.disconnectionPromise
|
|
181
|
+
? this.disconnectionPromise.then(() => connectAnonymousUser())
|
|
182
|
+
: connectAnonymousUser();
|
|
183
|
+
this.connectionPromise.finally(() => (this.connectionPromise = undefined));
|
|
184
|
+
return this.connectionPromise;
|
|
168
185
|
};
|
|
169
186
|
|
|
170
187
|
/**
|
|
@@ -176,7 +193,14 @@ export class StreamVideoClient {
|
|
|
176
193
|
* https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent
|
|
177
194
|
*/
|
|
178
195
|
disconnectUser = async (timeout?: number) => {
|
|
179
|
-
|
|
196
|
+
const disconnectUser = () => this.streamClient.disconnectUser(timeout);
|
|
197
|
+
this.disconnectionPromise = this.connectionPromise
|
|
198
|
+
? this.connectionPromise.then(() => disconnectUser())
|
|
199
|
+
: disconnectUser();
|
|
200
|
+
this.disconnectionPromise.finally(
|
|
201
|
+
() => (this.disconnectionPromise = undefined),
|
|
202
|
+
);
|
|
203
|
+
await this.disconnectionPromise;
|
|
180
204
|
this.eventHandlersToUnregister.forEach((unregister) => unregister());
|
|
181
205
|
this.eventHandlersToUnregister = [];
|
|
182
206
|
this.writeableStateStore.setConnectedUser(undefined);
|
package/src/rtc/signal.ts
CHANGED
|
@@ -9,15 +9,15 @@ export const createWebSocketSignalChannel = (opts: {
|
|
|
9
9
|
ws.binaryType = 'arraybuffer'; // do we need this?
|
|
10
10
|
|
|
11
11
|
ws.addEventListener('error', (e) => {
|
|
12
|
-
console.
|
|
12
|
+
console.log('Signaling WS channel error', e);
|
|
13
13
|
});
|
|
14
14
|
|
|
15
15
|
ws.addEventListener('close', (e) => {
|
|
16
|
-
console.
|
|
16
|
+
console.log('Signaling WS channel is closed', e);
|
|
17
17
|
});
|
|
18
18
|
|
|
19
19
|
ws.addEventListener('open', (e) => {
|
|
20
|
-
console.log('
|
|
20
|
+
console.log('Signaling WS channel is open', e);
|
|
21
21
|
});
|
|
22
22
|
|
|
23
23
|
if (onMessage) {
|