@stream-io/video-client 0.1.4 → 0.1.6

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 CHANGED
@@ -2,6 +2,20 @@
2
2
 
3
3
  This file was generated using [@jscutlery/semver](https://github.com/jscutlery/semver).
4
4
 
5
+ ### [0.1.6](https://github.com/GetStream/stream-video-js/compare/client0.1.5...client0.1.6) (2023-07-26)
6
+
7
+
8
+ ### Documentation
9
+
10
+ * Readme for js client, contributing guide ([#858](https://github.com/GetStream/stream-video-js/issues/858)) ([4d25c90](https://github.com/GetStream/stream-video-js/commit/4d25c909d2db3c5f98f89ad37dd810fc4ab7cc95))
11
+
12
+ ### [0.1.5](https://github.com/GetStream/stream-video-js/compare/client0.1.4...client0.1.5) (2023-07-21)
13
+
14
+
15
+ ### Bug Fixes
16
+
17
+ * strict mode issue ([#740](https://github.com/GetStream/stream-video-js/issues/740)) ([c39e4e4](https://github.com/GetStream/stream-video-js/commit/c39e4e4041a2326393478ad808b2aa791d50f8ce))
18
+
5
19
  ### [0.1.4](https://github.com/GetStream/stream-video-js/compare/client0.1.3...client0.1.4) (2023-07-21)
6
20
 
7
21
 
package/README.md CHANGED
@@ -1,14 +1,60 @@
1
1
  # @stream-io/video-client
2
2
 
3
- 🚧 **WARNING** This package is not yet stable, it is for internal use only. For more information check out our [video product page](https://getstream.io/video/).
3
+ 🚧 **WARNING** This package is not yet stable, it is for internal use only. For more information check out our [video product page](https://getstream.io/video/). 🚧
4
4
 
5
- This package holds the autogenerated Protobuf code and clients.
5
+ Low-level video client for browser and Node.js integrations.
6
6
 
7
- ## Generate Coordinator Models from OpenAPI spec (Dev Mode):
7
+ ## **Quick Links**
8
8
 
9
- We have a shell script which will generate the Coordinator models from the OpenAPI spec.
10
- This script expects the following directory structure to be set up:
9
+ - [Register](https://getstream.io/chat/trial/) to get an API key for Stream Video
10
+ TODO: add links to docs and tutorials
11
11
 
12
- - `chat` - the `chat` repository
13
- - `stream-video-js` - current repository
14
- - `cd stream-video-js/packages/client && yarn generate:open-api`
12
+ ## What is Stream?
13
+
14
+ Stream allows developers to rapidly deploy scalable feeds, chat messaging and video with an industry leading 99.999% uptime SLA guarantee.
15
+
16
+ With Stream's video components, you can use their SDK to build in-app video calling, audio rooms, audio calls, or live streaming. The best place to get started is with their tutorials:
17
+
18
+ - Video & Audio Calling Tutorial
19
+ - Audio Rooms Tutorial
20
+ - Livestreaming Tutorial
21
+
22
+ Stream provides UI components and state handling that make it easy to build video calling for your app. All calls run on Stream's network of edge servers around the world, ensuring optimal latency and reliability.
23
+
24
+ ## 👩‍💻 Free for Makers 👨‍💻
25
+
26
+ Stream is free for most side and hobby projects. To qualify, your project/company needs to have < 5 team members and < $10k in monthly revenue. Makers get $100 in monthly credit for video for free.
27
+
28
+ ## 💡Supported Features💡
29
+
30
+ Here are some of the features we support:
31
+
32
+ - Developer experience: Great SDKs, docs, tutorials and support so you can build quickly
33
+ - Edge network: Servers around the world ensure optimal latency and reliability
34
+ - Chat: Stored chat, reactions, threads, typing indicators, URL previews etc
35
+ - Security & Privacy: Based in USA and EU, Soc2 certified, GDPR compliant
36
+ - Dynascale: Automatically switch resolutions, fps, bitrate, codecs and paginate video on large calls
37
+ - Screen sharing
38
+ - Picture in picture support
39
+ - Active speaker
40
+ - Custom events
41
+ - Geofencing
42
+ - Notifications and ringing calls
43
+ - Opus DTX & Red for reliable audio
44
+ - Webhooks & SQS
45
+ - Backstage mode
46
+ - Flexible permissions system
47
+ - Joining calls by ID, link or invite
48
+ - Enabling and disabling audio and video when in calls
49
+ - Flipping, Enabling and disabling camera in calls
50
+ - Enabling and disabling speakerphone in calls
51
+ - Push notification providers support
52
+ - Call recording
53
+ - Broadcasting to HLS
54
+
55
+ ## Contributing
56
+
57
+ - How can I submit a sample app?
58
+ - Apps submissions are always welcome. 🥳 Open a PR with a proper description and we'll review it as soon as possible.
59
+ - Spot a bug 🕷 ?
60
+ - We welcome code changes that improve the apps or fix a problem. Please make sure to follow all best practices and add tests if applicable before submitting a Pull Request on Github.
@@ -4,7 +4,7 @@ import { ServiceType, stackIntercept } from '@protobuf-ts/runtime-rpc';
4
4
  import axios, { AxiosHeaders } from 'axios';
5
5
  export { AxiosError } from 'axios';
6
6
  import { TwirpFetchTransport } from '@protobuf-ts/twirp-transport';
7
- import { ReplaySubject, BehaviorSubject, takeWhile, pairwise, tap, debounce, timer, map as map$2, Observable, debounceTime, concatMap, from, shareReplay, merge, combineLatest, filter } from 'rxjs';
7
+ import { ReplaySubject, BehaviorSubject, takeWhile, filter, pairwise, tap, debounce, timer, map as map$2, Observable, debounceTime, concatMap, from, shareReplay, merge, combineLatest } from 'rxjs';
8
8
  import * as SDP from 'sdp-transform';
9
9
  import WebSocket from 'isomorphic-ws';
10
10
  import { take, map as map$1, distinctUntilChanged } from 'rxjs/operators';
@@ -9465,11 +9465,13 @@ class Call {
9465
9465
  */
9466
9466
  this.leave = ({ reject = false } = {}) => __awaiter(this, void 0, void 0, function* () {
9467
9467
  var _a, _b, _c, _d;
9468
- // TODO: handle case when leave is called during JOINING
9469
9468
  const callingState = this.state.callingState;
9470
9469
  if (callingState === CallingState.LEFT) {
9471
9470
  throw new Error('Cannot leave call that has already been left.');
9472
9471
  }
9472
+ if (callingState === CallingState.JOINING) {
9473
+ yield this.assertCallJoined();
9474
+ }
9473
9475
  if (this.ringing) {
9474
9476
  // I'm the one who started the call, so I should cancel it.
9475
9477
  const hasOtherParticipants = this.state.remoteParticipants.length > 0;
@@ -9875,13 +9877,6 @@ class Call {
9875
9877
  }, timeout);
9876
9878
  });
9877
9879
  };
9878
- this.assertCallJoined = () => {
9879
- return new Promise((resolve) => {
9880
- this.state.callingState$
9881
- .pipe(takeWhile((state) => state !== CallingState.JOINED, true))
9882
- .subscribe(() => resolve());
9883
- });
9884
- };
9885
9880
  /**
9886
9881
  * Starts publishing the given video stream to the call.
9887
9882
  * The stream will be stopped if the user changes an input device, or if the user leaves the call.
@@ -10112,6 +10107,13 @@ class Call {
10112
10107
  var _h;
10113
10108
  return (_h = this.publisher) === null || _h === void 0 ? void 0 : _h.updateVideoPublishQuality(enabledRids);
10114
10109
  });
10110
+ this.assertCallJoined = () => {
10111
+ return new Promise((resolve) => {
10112
+ this.state.callingState$
10113
+ .pipe(takeWhile((state) => state !== CallingState.JOINED, true), filter((s) => s === CallingState.JOINED))
10114
+ .subscribe(() => resolve());
10115
+ });
10116
+ };
10115
10117
  /**
10116
10118
  * Sends a reaction to the other call participants.
10117
10119
  *
@@ -10323,7 +10325,7 @@ class Call {
10323
10325
  * @returns
10324
10326
  */
10325
10327
  this.queryMembers = (request) => {
10326
- return this.streamClient.post('/call/members', Object.assign(Object.assign({}, request), { id: this.id, type: this.type }));
10328
+ return this.streamClient.post('/call/members', Object.assign(Object.assign({}, (request || {})), { id: this.id, type: this.type }));
10327
10329
  };
10328
10330
  /**
10329
10331
  * Will update the call members.
@@ -11634,7 +11636,7 @@ class WSConnectionFallback {
11634
11636
  }
11635
11637
  }
11636
11638
 
11637
- const version = '0.1.4';
11639
+ const version = '0.1.6';
11638
11640
 
11639
11641
  const logger = getLogger(['location']);
11640
11642
  const HINT_URL = `https://hint.stream-io-video.com/`;
@@ -11697,14 +11699,6 @@ class StreamClient {
11697
11699
  });
11698
11700
  this._getConnectionID = () => { var _a, _b; return ((_a = this.wsConnection) === null || _a === void 0 ? void 0 : _a.connectionID) || ((_b = this.wsFallback) === null || _b === void 0 ? void 0 : _b.connectionID); };
11699
11701
  this._hasConnectionID = () => Boolean(this._getConnectionID());
11700
- /**
11701
- * This will start a promise to hold API calls until `connectUser` is called, useful when user is set in `StreamVideoClient constructor`
11702
- */
11703
- this.startWaitingForConnection = () => {
11704
- this.waitForConnectPromise = new Promise((resolve) => {
11705
- this.resolveConnectPromise = resolve;
11706
- });
11707
- };
11708
11702
  /**
11709
11703
  * connectUser - Set the current user and open a WebSocket connection
11710
11704
  *
@@ -11739,11 +11733,6 @@ class StreamClient {
11739
11733
  this._setUser(user);
11740
11734
  const wsPromise = this.openConnection();
11741
11735
  this.setUserPromise = Promise.all([setTokenPromise, wsPromise]).then((result) => result[1]);
11742
- if (this.resolveConnectPromise) {
11743
- this.resolveConnectPromise();
11744
- this.waitForConnectPromise = undefined;
11745
- this.resolveConnectPromise = undefined;
11746
- }
11747
11736
  try {
11748
11737
  return yield this.setUserPromise;
11749
11738
  }
@@ -11858,11 +11847,6 @@ class StreamClient {
11858
11847
  });
11859
11848
  this.anonymous = true;
11860
11849
  yield this._setToken(user, tokenOrProvider, this.anonymous);
11861
- if (this.resolveConnectPromise) {
11862
- this.resolveConnectPromise();
11863
- this.waitForConnectPromise = undefined;
11864
- this.resolveConnectPromise = undefined;
11865
- }
11866
11850
  this._setUser(user);
11867
11851
  // some endpoints require a connection_id to be resolved.
11868
11852
  // as anonymous users aren't allowed to open WS connections, we just
@@ -11919,9 +11903,6 @@ class StreamClient {
11919
11903
  this.logger('trace', `client:${type} - Response - url: ${url} > status ${response.status}`, {
11920
11904
  response,
11921
11905
  });
11922
- this.logger('trace', `client:${type} - Response payload`, {
11923
- response,
11924
- });
11925
11906
  };
11926
11907
  this._logApiError = (type, url, error) => {
11927
11908
  this.logger('error', `client:${type} - Error - url: ${url}`, {
@@ -11932,9 +11913,6 @@ class StreamClient {
11932
11913
  this.doAxiosRequest = (type, url, data, options = {}) => __awaiter(this, void 0, void 0, function* () {
11933
11914
  var _h;
11934
11915
  if (!options.publicEndpoint) {
11935
- if (this.waitForConnectPromise) {
11936
- yield this.waitForConnectPromise;
11937
- }
11938
11916
  yield Promise.all([
11939
11917
  this.tokenManager.tokenReady(),
11940
11918
  this.connectionIdPromise,
@@ -11973,9 +11951,9 @@ class StreamClient {
11973
11951
  }
11974
11952
  catch (e /**TODO: generalize error types */) {
11975
11953
  e.client_request_id = (_h = requestConfig.headers) === null || _h === void 0 ? void 0 : _h['x-client-request-id'];
11976
- this._logApiError(type, url, e);
11977
11954
  this.consecutiveFailures += 1;
11978
11955
  if (e.response) {
11956
+ this._logApiError(type, url, e.response);
11979
11957
  /** connection_fallback depends on this token expiration logic */
11980
11958
  if (e.response.data.code === KnownCodes.TOKEN_EXPIRED &&
11981
11959
  !this.tokenManager.isStatic()) {
@@ -11988,6 +11966,7 @@ class StreamClient {
11988
11966
  return this.handleResponse(e.response);
11989
11967
  }
11990
11968
  else {
11969
+ this._logApiError(type, url, e);
11991
11970
  // eslint-disable-next-line no-throw-literal
11992
11971
  throw e;
11993
11972
  }
@@ -12272,6 +12251,7 @@ class StreamClient {
12272
12251
  class StreamVideoClient {
12273
12252
  constructor(apiKeyOrArgs, opts) {
12274
12253
  var _a, _b;
12254
+ this.logLevel = 'warn';
12275
12255
  this.eventHandlersToUnregister = [];
12276
12256
  /**
12277
12257
  * Disconnects the currently connected user from the client.
@@ -12282,7 +12262,7 @@ class StreamVideoClient {
12282
12262
  * https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent
12283
12263
  */
12284
12264
  this.disconnectUser = (timeout) => __awaiter(this, void 0, void 0, function* () {
12285
- if (!this.streamClient.user) {
12265
+ if (!this.streamClient.user && !this.connectionPromise) {
12286
12266
  return;
12287
12267
  }
12288
12268
  const disconnectUser = () => this.streamClient.disconnectUser(timeout);
@@ -12343,7 +12323,7 @@ class StreamVideoClient {
12343
12323
  *
12344
12324
  * @param data the query data.
12345
12325
  */
12346
- this.queryCalls = (data) => __awaiter(this, void 0, void 0, function* () {
12326
+ this.queryCalls = (data = {}) => __awaiter(this, void 0, void 0, function* () {
12347
12327
  const response = yield this.streamClient.post('/calls', data);
12348
12328
  const calls = response.calls.map((c) => {
12349
12329
  const call = new Call({
@@ -12459,14 +12439,16 @@ class StreamVideoClient {
12459
12439
  this.streamClient.setUserAgent(this.streamClient.getUserAgent() +
12460
12440
  `-video-${SdkType[sdkInfo.type].toLowerCase()}-sdk-${sdkInfo.major}.${sdkInfo.minor}.${sdkInfo.patch}`);
12461
12441
  }
12462
- this.user = apiKeyOrArgs.user;
12463
- this.token = apiKeyOrArgs.token || apiKeyOrArgs.tokenProvider;
12464
- if (this.user) {
12465
- this.streamClient.startWaitingForConnection();
12466
- }
12467
12442
  }
12468
12443
  this.writeableStateStore = new StreamVideoWriteableStateStore();
12469
12444
  this.readOnlyStateStore = new StreamVideoReadOnlyStateStore(this.writeableStateStore);
12445
+ if (typeof apiKeyOrArgs !== 'string') {
12446
+ const user = apiKeyOrArgs.user;
12447
+ const token = apiKeyOrArgs.token || apiKeyOrArgs.tokenProvider;
12448
+ if (user) {
12449
+ this.connectUser(user, token);
12450
+ }
12451
+ }
12470
12452
  }
12471
12453
  /**
12472
12454
  * Connects the given user to the client.
@@ -12479,24 +12461,21 @@ class StreamVideoClient {
12479
12461
  connectUser(user, token) {
12480
12462
  var _a;
12481
12463
  return __awaiter(this, void 0, void 0, function* () {
12482
- const userToConnect = user || this.user;
12483
- const tokenToUse = token || this.token;
12484
- if (!userToConnect) {
12485
- throw new Error('Connect user is called without user');
12486
- }
12487
- if (userToConnect.type === 'anonymous') {
12488
- userToConnect.id = '!anon';
12489
- return this.connectAnonymousUser(userToConnect, tokenToUse);
12490
- }
12491
- if (userToConnect.type === 'guest') {
12492
- const response = yield this.createGuestUser({
12493
- user: Object.assign(Object.assign({}, userToConnect), { role: 'guest' }),
12494
- });
12495
- return this.connectUser(response.user, response.access_token);
12464
+ if (user.type === 'anonymous') {
12465
+ user.id = '!anon';
12466
+ return this.connectAnonymousUser(user, token);
12496
12467
  }
12497
- const connectUser = () => {
12498
- return this.streamClient.connectUser(userToConnect, tokenToUse);
12468
+ let connectUser = () => {
12469
+ return this.streamClient.connectUser(user, token);
12499
12470
  };
12471
+ if (user.type === 'guest') {
12472
+ connectUser = () => __awaiter(this, void 0, void 0, function* () {
12473
+ const response = yield this.createGuestUser({
12474
+ user: Object.assign(Object.assign({}, user), { role: 'guest' }),
12475
+ });
12476
+ return this.streamClient.connectUser(response.user, response.access_token);
12477
+ });
12478
+ }
12500
12479
  this.connectionPromise = this.disconnectionPromise
12501
12480
  ? this.disconnectionPromise.then(() => connectUser())
12502
12481
  : connectUser();
@@ -12530,7 +12509,7 @@ class StreamVideoClient {
12530
12509
  if (event.type !== 'call.created')
12531
12510
  return;
12532
12511
  const { call, members } = event;
12533
- if (userToConnect.id === call.created_by.id) {
12512
+ if (user.id === call.created_by.id) {
12534
12513
  this.logger('warn', 'Received `call.created` sent by the current user');
12535
12514
  return;
12536
12515
  }
@@ -12548,7 +12527,7 @@ class StreamVideoClient {
12548
12527
  if (event.type !== 'call.ring')
12549
12528
  return;
12550
12529
  const { call, members } = event;
12551
- if (userToConnect.id === call.created_by.id) {
12530
+ if (user.id === call.created_by.id) {
12552
12531
  this.logger('debug', 'Received `call.ring` sent by the current user so ignoring the event');
12553
12532
  return;
12554
12533
  }