@stream-io/video-client 1.46.1 → 1.47.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.
package/CHANGELOG.md CHANGED
@@ -2,6 +2,16 @@
2
2
 
3
3
  This file was generated using [@jscutlery/semver](https://github.com/jscutlery/semver).
4
4
 
5
+ ## [1.47.0](https://github.com/GetStream/stream-video-js/compare/@stream-io/video-client-1.46.1...@stream-io/video-client-1.47.0) (2026-04-15)
6
+
7
+ ### Features
8
+
9
+ - **client:** JoinCall with hints for high scale livestream ([#2199](https://github.com/GetStream/stream-video-js/issues/2199)) ([704681a](https://github.com/GetStream/stream-video-js/commit/704681ad9ce7a0013325b6db91644e1907d0db0b))
10
+
11
+ ### Bug Fixes
12
+
13
+ - **client:** align device preference persistence with permission and track end events ([#2196](https://github.com/GetStream/stream-video-js/issues/2196)) ([b4ed7c2](https://github.com/GetStream/stream-video-js/commit/b4ed7c2c6bc6fb6777a411b69747ccc36aa82f44))
14
+
5
15
  ## [1.46.1](https://github.com/GetStream/stream-video-js/compare/@stream-io/video-client-1.46.0...@stream-io/video-client-1.46.1) (2026-04-09)
6
16
 
7
17
  - remove listeners and stop even on permission error - rn speech detector ([f4fdd9e](https://github.com/GetStream/stream-video-js/commit/f4fdd9e1a008b52011ef18562152aad60a1f7936))
@@ -6284,7 +6284,7 @@ const getSdkVersion = (sdk) => {
6284
6284
  return sdk ? `${sdk.major}.${sdk.minor}.${sdk.patch}` : '0.0.0-development';
6285
6285
  };
6286
6286
 
6287
- const version = "1.46.1";
6287
+ const version = "1.47.0";
6288
6288
  const [major, minor, patch] = version.split('.');
6289
6289
  let sdkInfo = {
6290
6290
  type: SdkType.PLAIN_JAVASCRIPT,
@@ -10865,8 +10865,14 @@ class DeviceManager {
10865
10865
  this.handleDisconnectedOrReplacedDevices();
10866
10866
  }
10867
10867
  if (this.devicePersistence.enabled) {
10868
- this.subscriptions.push(createSubscription(combineLatest([this.state.selectedDevice$, this.state.status$]), ([selectedDevice, status]) => {
10869
- if (!status)
10868
+ this.subscriptions.push(createSubscription(combineLatest([
10869
+ this.state.selectedDevice$,
10870
+ this.state.status$,
10871
+ this.state.browserPermissionState$,
10872
+ ]), ([selectedDevice, status, browserPermissionState]) => {
10873
+ if (!status ||
10874
+ (this.isTrackStoppedDueToTrackEnd && status === 'disabled') ||
10875
+ browserPermissionState !== 'granted')
10870
10876
  return;
10871
10877
  this.persistPreference(selectedDevice, status);
10872
10878
  }));
@@ -11631,7 +11637,10 @@ class CameraManager extends DeviceManager {
11631
11637
  const shouldApplyDefaults = this.state.status === undefined &&
11632
11638
  this.state.optimisticStatus === undefined;
11633
11639
  let persistedPreferencesApplied = false;
11634
- if (shouldApplyDefaults && this.devicePersistence.enabled) {
11640
+ const permissionState = await firstValueFrom(this.state.browserPermissionState$);
11641
+ if (shouldApplyDefaults &&
11642
+ this.devicePersistence.enabled &&
11643
+ permissionState === 'granted') {
11635
11644
  persistedPreferencesApplied =
11636
11645
  await this.applyPersistedPreferences(enabledInCallType);
11637
11646
  }
@@ -12373,7 +12382,10 @@ class MicrophoneManager extends AudioDeviceManager {
12373
12382
  const shouldApplyDefaults = this.state.status === undefined &&
12374
12383
  this.state.optimisticStatus === undefined;
12375
12384
  let persistedPreferencesApplied = false;
12376
- if (shouldApplyDefaults && this.devicePersistence.enabled) {
12385
+ const permissionState = await firstValueFrom(this.state.browserPermissionState$);
12386
+ if (shouldApplyDefaults &&
12387
+ this.devicePersistence.enabled &&
12388
+ permissionState === 'granted') {
12377
12389
  persistedPreferencesApplied = await this.applyPersistedPreferences(true);
12378
12390
  }
12379
12391
  const canPublish = this.call.permissionsContext.canPublish(this.trackType);
@@ -12757,7 +12769,12 @@ class SpeakerManager {
12757
12769
  }));
12758
12770
  }
12759
12771
  if (!isReactNative() && this.devicePersistence.enabled) {
12760
- this.subscriptions.push(createSubscription(this.state.selectedDevice$, (selectedDevice) => {
12772
+ this.subscriptions.push(createSubscription(combineLatest([
12773
+ this.state.selectedDevice$,
12774
+ getAudioBrowserPermission(this.call.tracer).asStateObservable(),
12775
+ ]), ([selectedDevice, browserPermissionState]) => {
12776
+ if (!selectedDevice || browserPermissionState !== 'granted')
12777
+ return;
12761
12778
  this.persistSpeakerDevicePreference(selectedDevice);
12762
12779
  }));
12763
12780
  }
@@ -16134,7 +16151,7 @@ class StreamClient {
16134
16151
  this.getUserAgent = () => {
16135
16152
  if (!this.cachedUserAgent) {
16136
16153
  const { clientAppIdentifier = {} } = this.options;
16137
- const { sdkName = 'js', sdkVersion = "1.46.1", ...extras } = clientAppIdentifier;
16154
+ const { sdkName = 'js', sdkVersion = "1.47.0", ...extras } = clientAppIdentifier;
16138
16155
  this.cachedUserAgent = [
16139
16156
  `stream-video-${sdkName}-v${sdkVersion}`,
16140
16157
  ...Object.entries(extras).map(([key, value]) => `${key}=${value}`),