@defcomm/meetingsdk 0.2.4 → 0.2.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/dist/index.mjs CHANGED
@@ -349,9 +349,6 @@ var SFUClient = class {
349
349
  this.localStream = null;
350
350
  this.screenStream = null;
351
351
  this.videoSender = null;
352
- this.audioMuted = false;
353
- this.videoMuted = false;
354
- this.activeRecording = null;
355
352
  this.audioSender = null;
356
353
  this.screenSender = null;
357
354
  this.audioTransceiver = null;
@@ -372,7 +369,7 @@ var SFUClient = class {
372
369
  this.joiningWithResume = false;
373
370
  this.reconnectTimer = null;
374
371
  this.reconnectAttempt = 0;
375
- this.maxReconnectAttempts = 6;
372
+ this.maxReconnectAttempts = 8;
376
373
  this.reconnectBaseMs = 750;
377
374
  this.joinWaiter = null;
378
375
  this.transportRecoveryInProgress = false;
@@ -395,8 +392,6 @@ var SFUClient = class {
395
392
  this.trackToSource = /* @__PURE__ */ new Map();
396
393
  this.localTrackIds = /* @__PURE__ */ new Map();
397
394
  this.subscriberStatsTimer = null;
398
- this.roomSyncTimer = null;
399
- this.roomSyncInFlight = false;
400
395
  this.heartbeatTimer = null;
401
396
  this.apiBase = options.apiBase || "https://api.example.com/api";
402
397
  this.wsBase = options.wsBase || "wss://api.example.com/ws";
@@ -435,14 +430,10 @@ var SFUClient = class {
435
430
  });
436
431
  this.onTrackStateChanged = options.onTrackStateChanged || (() => {
437
432
  });
438
- this.onParticipantMediaState = options.onParticipantMediaState || (() => {
439
- });
440
433
  this.onRecordingStarted = options.onRecordingStarted || (() => {
441
434
  });
442
435
  this.onRecordingStopped = options.onRecordingStopped || (() => {
443
436
  });
444
- this.onRoomState = options.onRoomState || (() => {
445
- });
446
437
  this.onError = options.onError || console.error;
447
438
  this.autoSubscribe = options.autoSubscribe !== false;
448
439
  }
@@ -464,29 +455,6 @@ var SFUClient = class {
464
455
  this.heartbeatTimer = null;
465
456
  }
466
457
  }
467
- startRoomStateSync() {
468
- this.stopRoomStateSync();
469
- this.roomSyncTimer = setInterval(() => {
470
- if (this.state !== "connected") return;
471
- void this.syncRoomState();
472
- }, 5e3);
473
- }
474
- stopRoomStateSync() {
475
- if (this.roomSyncTimer) {
476
- clearInterval(this.roomSyncTimer);
477
- this.roomSyncTimer = null;
478
- }
479
- this.roomSyncInFlight = false;
480
- }
481
- async syncRoomState() {
482
- if (this.roomSyncInFlight || !this.isSocketOpen()) return;
483
- this.roomSyncInFlight = true;
484
- try {
485
- this.send({ type: "sync_room_state" });
486
- } finally {
487
- this.roomSyncInFlight = false;
488
- }
489
- }
490
458
  createId() {
491
459
  return typeof crypto !== "undefined" && crypto.randomUUID ? crypto.randomUUID() : `id_${Math.random().toString(36).slice(2)}_${Date.now()}`;
492
460
  }
@@ -584,13 +552,9 @@ var SFUClient = class {
584
552
  this.resumeToken = null;
585
553
  }
586
554
  this.room = nextRoom;
587
- this.audioMuted = Boolean(options.audioMuted);
588
- this.videoMuted = Boolean(options.videoMuted);
589
555
  this.joinOptions = {
590
556
  displayName: options.displayName,
591
- avatarUrl: options.avatarUrl,
592
- audioMuted: this.audioMuted,
593
- videoMuted: this.videoMuted
557
+ avatarUrl: options.avatarUrl
594
558
  };
595
559
  if (options.participantId) this.participantId = options.participantId;
596
560
  if (!this.resumeToken) {
@@ -659,9 +623,7 @@ var SFUClient = class {
659
623
  room_code: this.room,
660
624
  resume_token: this.resumeToken,
661
625
  display_name: options.displayName,
662
- avatar_url: options.avatarUrl,
663
- audio_muted: this.audioMuted,
664
- video_muted: this.videoMuted
626
+ avatar_url: options.avatarUrl
665
627
  };
666
628
  if (this.pendingJoinRequestId) {
667
629
  this.send({
@@ -702,20 +664,8 @@ var SFUClient = class {
702
664
  scheduleReconnect() {
703
665
  if (this.reconnectTimer || this.intentionalClose) return;
704
666
  if (this.reconnectAttempt >= this.maxReconnectAttempts) {
705
- const error = new Error("SFU reconnect attempts exhausted");
706
- console.error("[SFU] Reconnect attempts exhausted; leaving meeting", error);
707
- this.intentionalClose = true;
708
- this.stopHeartbeat();
709
- this.stopRoomStateSync();
710
- this.cleanupAll();
711
667
  this.setState("disconnected");
712
- this.onError({
713
- code: "RECONNECT_TIMEOUT",
714
- message: error.message,
715
- recoverable: false
716
- });
717
- this.onDisconnected();
718
- this.failJoin(error);
668
+ this.failJoin(new Error("SFU reconnect attempts exhausted"));
719
669
  return;
720
670
  }
721
671
  this.reconnectAttempt += 1;
@@ -787,9 +737,7 @@ var SFUClient = class {
787
737
  room_code: this.room,
788
738
  resume_token: this.resumeToken,
789
739
  display_name: this.joinOptions.displayName,
790
- avatar_url: this.joinOptions.avatarUrl,
791
- audio_muted: this.audioMuted,
792
- video_muted: this.videoMuted
740
+ avatar_url: this.joinOptions.avatarUrl
793
741
  }
794
742
  });
795
743
  }
@@ -864,8 +812,22 @@ var SFUClient = class {
864
812
  if (!track?.track_id) break;
865
813
  this.rememberTrack(track);
866
814
  if (track.participant_id === this.currentParticipantId) {
867
- if (track.source === "audio") this.localTrackIds.set("audio", track.track_id);
868
- if (track.source === "camera") this.localTrackIds.set("camera", track.track_id);
815
+ if (track.source === "audio") {
816
+ this.localTrackIds.set("audio", track.track_id);
817
+ const muted = !(this.localStream?.getAudioTracks()[0]?.enabled ?? true);
818
+ this.send({
819
+ type: "track_state",
820
+ payload: { track_id: track.track_id, muted }
821
+ });
822
+ }
823
+ if (track.source === "camera") {
824
+ this.localTrackIds.set("camera", track.track_id);
825
+ const muted = !(this.localStream?.getVideoTracks()[0]?.enabled ?? true);
826
+ this.send({
827
+ type: "track_state",
828
+ payload: { track_id: track.track_id, muted }
829
+ });
830
+ }
869
831
  if (track.source === "screen")
870
832
  this.localTrackIds.set("screen", track.track_id);
871
833
  break;
@@ -894,27 +856,6 @@ var SFUClient = class {
894
856
  this.onTrackUnpublished(track);
895
857
  break;
896
858
  }
897
- case "participant_media_state": {
898
- const participantId = payload.participant_id;
899
- if (!participantId) break;
900
- const participant = this.participants.get(participantId);
901
- if (participant) {
902
- participant.audio_muted = Boolean(payload.audio_muted);
903
- participant.video_muted = Boolean(payload.video_muted);
904
- this.participants.set(participantId, participant);
905
- }
906
- for (const track of this.trackMetadata.values()) {
907
- if (track.participant_id !== participantId) continue;
908
- if (track.source === "audio") track.muted = Boolean(payload.audio_muted);
909
- if (track.source === "camera") track.muted = Boolean(payload.video_muted);
910
- }
911
- this.onParticipantMediaState(
912
- participantId,
913
- Boolean(payload.audio_muted),
914
- Boolean(payload.video_muted)
915
- );
916
- break;
917
- }
918
859
  case "track_state_changed": {
919
860
  const trackId = payload.track_id || payload.track?.track_id;
920
861
  if (!trackId) break;
@@ -936,20 +877,14 @@ var SFUClient = class {
936
877
  case "subscription_updated": {
937
878
  break;
938
879
  }
939
- case "room_state": {
940
- await this.applyRoomState(payload);
941
- break;
942
- }
943
880
  case "recording_started": {
944
- this.activeRecording = {
881
+ this.onRecordingStarted({
945
882
  recording_id: payload.recording_id,
946
883
  started_at: payload.started_at
947
- };
948
- this.onRecordingStarted(this.activeRecording);
884
+ });
949
885
  break;
950
886
  }
951
887
  case "recording_stopped": {
952
- this.activeRecording = null;
953
888
  this.onRecordingStopped({
954
889
  recording_id: payload.recording_id,
955
890
  stopped_at: payload.stopped_at
@@ -1007,67 +942,6 @@ var SFUClient = class {
1007
942
  console.debug("[SFU] Ignoring unknown server message", message);
1008
943
  }
1009
944
  }
1010
- async applyRoomState(payload) {
1011
- const authoritative = /* @__PURE__ */ new Map();
1012
- for (const participant of payload?.participants || []) {
1013
- if (participant?.participant_id) authoritative.set(participant.participant_id, participant);
1014
- }
1015
- for (const id of [...this.participants.keys()]) {
1016
- if (!authoritative.has(id) && id !== this.currentParticipantId) {
1017
- this.participants.delete(id);
1018
- this.removeRemoteParticipant(id);
1019
- this.onParticipantLeft(id);
1020
- }
1021
- }
1022
- for (const [id, participant] of authoritative) {
1023
- if (id === this.currentParticipantId) continue;
1024
- const previous = this.participants.get(id);
1025
- this.participants.set(id, {
1026
- ...previous,
1027
- ...participant,
1028
- audio_muted: Boolean(participant.audio_muted),
1029
- video_muted: Boolean(participant.video_muted)
1030
- });
1031
- if (!previous) this.onParticipantJoined(participant);
1032
- if (participant.presence) this.onParticipantPresence(id, String(participant.presence));
1033
- }
1034
- const nextTracks = /* @__PURE__ */ new Map();
1035
- for (const track of payload?.tracks || []) {
1036
- if (!track?.track_id) continue;
1037
- nextTracks.set(track.track_id, track);
1038
- this.rememberTrack(track);
1039
- }
1040
- for (const id of [...this.trackMetadata.keys()]) {
1041
- if (!nextTracks.has(id)) {
1042
- this.trackMetadata.delete(id);
1043
- this.subscribedTracks.delete(id);
1044
- this.trackToParticipant.delete(id);
1045
- this.trackToSource.delete(id);
1046
- }
1047
- }
1048
- if (payload?.recording) {
1049
- const current = {
1050
- recording_id: payload.recording.recording_id,
1051
- started_at: payload.recording.started_at
1052
- };
1053
- if (!this.activeRecording || this.activeRecording.recording_id !== current.recording_id) {
1054
- this.activeRecording = current;
1055
- this.onRecordingStarted(current);
1056
- }
1057
- } else if (this.activeRecording) {
1058
- const previous = this.activeRecording;
1059
- this.activeRecording = null;
1060
- this.onRecordingStopped({
1061
- recording_id: previous.recording_id,
1062
- stopped_at: (/* @__PURE__ */ new Date()).toISOString()
1063
- });
1064
- }
1065
- if (this.autoSubscribe) {
1066
- const missing = [...nextTracks.values()].filter((t) => t.participant_id !== this.currentParticipantId && !this.subscribedTracks.has(t.track_id)).map((t) => t.track_id);
1067
- if (missing.length) await this.subscribeMultiple(missing);
1068
- }
1069
- this.onRoomState(payload);
1070
- }
1071
945
  rememberTrack(track) {
1072
946
  this.trackMetadata.set(track.track_id, track);
1073
947
  this.trackToParticipant.set(track.track_id, track.participant_id);
@@ -1097,23 +971,8 @@ var SFUClient = class {
1097
971
  for (const track of payload.tracks || []) {
1098
972
  if (track?.track_id) this.rememberTrack(track);
1099
973
  }
1100
- if (payload.recording) {
1101
- this.activeRecording = {
1102
- recording_id: payload.recording.recording_id,
1103
- started_at: payload.recording.started_at
1104
- };
1105
- this.onRecordingStarted(this.activeRecording);
1106
- } else if (this.activeRecording) {
1107
- const previous = this.activeRecording;
1108
- this.activeRecording = null;
1109
- this.onRecordingStopped({
1110
- recording_id: previous.recording_id,
1111
- stopped_at: (/* @__PURE__ */ new Date()).toISOString()
1112
- });
1113
- }
1114
974
  await this.initializePeerConnections();
1115
975
  this.setState("connected");
1116
- this.startRoomStateSync();
1117
976
  this.onConnected(payload, resumed);
1118
977
  for (const participant of this.participants.values()) {
1119
978
  if (participant.participant_id !== this.currentParticipantId) {
@@ -1668,7 +1527,6 @@ var SFUClient = class {
1668
1527
  }
1669
1528
  async leave() {
1670
1529
  this.stopHeartbeat();
1671
- this.stopRoomStateSync();
1672
1530
  this.intentionalClose = true;
1673
1531
  this.setState("leaving");
1674
1532
  if (this.reconnectTimer) {
@@ -2036,13 +1894,9 @@ var VideoSDKCore = class {
2036
1894
  );
2037
1895
  return;
2038
1896
  }
2039
- if (state === "disconnected" || state === "idle") {
2040
- this.sfuClient = null;
2041
- } else {
2042
- throw new Error(
2043
- `SFU client already exists in state "${state}". Disconnect explicitly before creating another connection.`
2044
- );
2045
- }
1897
+ throw new Error(
1898
+ `SFU client already exists in state "${state}". Disconnect explicitly before creating another connection.`
1899
+ );
2046
1900
  }
2047
1901
  const client = new SFUClient({
2048
1902
  apiBase: this.apiBase,
@@ -2060,48 +1914,6 @@ var VideoSDKCore = class {
2060
1914
  name: this.participantName
2061
1915
  });
2062
1916
  },
2063
- onRoomState: (roomState) => {
2064
- for (const participant of roomState?.participants || []) {
2065
- const pid = participant?.participant_id;
2066
- if (!pid || pid === this.myId) continue;
2067
- const current = this.state.getParticipant(pid);
2068
- if (!current) continue;
2069
- this.state.updateParticipantMedia(pid, {
2070
- stream: current.media?.stream ?? null,
2071
- micEnabled: !Boolean(participant.audio_muted),
2072
- camEnabled: !Boolean(participant.video_muted),
2073
- isScreenSharing: Boolean(participant.screen_sharing)
2074
- });
2075
- }
2076
- const presenters = /* @__PURE__ */ new Set();
2077
- for (const participant of roomState?.participants || []) {
2078
- const pid = participant?.participant_id;
2079
- if (!pid || pid === this.myId) continue;
2080
- const current = this.state.getParticipant(pid);
2081
- if (!current) continue;
2082
- if (participant.screen_sharing) {
2083
- presenters.add(pid);
2084
- this.state.updateParticipantMedia(pid, {
2085
- isScreenSharing: true,
2086
- screenStream: current.media?.screenStream ?? null
2087
- });
2088
- } else if (current.media?.isScreenSharing) {
2089
- const screen = this.remoteScreenStreams.get(pid);
2090
- screen?.getTracks().forEach((track) => track.stop());
2091
- this.remoteScreenStreams.delete(pid);
2092
- this.state.updateParticipantMedia(pid, {
2093
- isScreenSharing: false,
2094
- screenStream: null,
2095
- screenTrack: void 0
2096
- });
2097
- }
2098
- }
2099
- const presenter = [...presenters][0] ?? null;
2100
- if (this.state.presenterId !== presenter) {
2101
- this.state.setPresenterId(presenter);
2102
- }
2103
- this.events.onRoomUpdate?.(roomState);
2104
- },
2105
1917
  onDisconnected: () => {
2106
1918
  console.log("[SFU] Signaling WebSocket disconnected; reconnecting");
2107
1919
  },
@@ -2111,11 +1923,6 @@ var VideoSDKCore = class {
2111
1923
  // ADMISSION CONTROL
2112
1924
  onJoinPending: (info) => {
2113
1925
  console.log("[SFU] Join request pending", info);
2114
- this.events.onEntryRequested?.({
2115
- requestId: info.request_id,
2116
- participantId: this.myId,
2117
- name: this.participantName
2118
- });
2119
1926
  },
2120
1927
  onJoinApproved: (requestId) => {
2121
1928
  console.log("[SFU] Join approved", requestId);
@@ -2173,8 +1980,8 @@ var VideoSDKCore = class {
2173
1980
  name: pname,
2174
1981
  connectionState: "connected",
2175
1982
  media: {
2176
- micEnabled: !Boolean(participant.audio_muted),
2177
- camEnabled: !Boolean(participant.video_muted),
1983
+ micEnabled: true,
1984
+ camEnabled: true,
2178
1985
  isScreenSharing: false,
2179
1986
  stream: null
2180
1987
  }
@@ -2247,18 +2054,6 @@ var VideoSDKCore = class {
2247
2054
  camEnabled: track.kind === "video" ? false : current.media?.camEnabled ?? true
2248
2055
  });
2249
2056
  },
2250
- onParticipantMediaState: (participantId, audioMuted, videoMuted) => {
2251
- if (participantId === this.myId) return;
2252
- const current = this.state.getParticipant(participantId);
2253
- if (!current) return;
2254
- this.state.updateParticipantMedia(participantId, {
2255
- stream: current.media?.stream ?? null,
2256
- micEnabled: !audioMuted,
2257
- camEnabled: !videoMuted
2258
- });
2259
- this.events.onMuteStateChanged?.(participantId, "audio", audioMuted);
2260
- this.events.onMuteStateChanged?.(participantId, "video", videoMuted);
2261
- },
2262
2057
  onTrackStateChanged: (track) => {
2263
2058
  const pid = track.participant_id;
2264
2059
  if (!pid || pid === this.myId) {
@@ -2359,9 +2154,7 @@ var VideoSDKCore = class {
2359
2154
  client.setLocalStream(this.localStream);
2360
2155
  await client.getToken(roomId, {
2361
2156
  displayName: name,
2362
- participantId: this.myId,
2363
- audioMuted: this.state.localParticipant?.media?.micEnabled,
2364
- videoMuted: this.state.localParticipant?.media?.camEnabled
2157
+ participantId: this.myId
2365
2158
  });
2366
2159
  }
2367
2160
  // SFU STATE
@@ -2675,7 +2468,6 @@ var MeetingProvider = ({
2675
2468
  /* @__PURE__ */ new Set()
2676
2469
  );
2677
2470
  const meetingLeftListeners = useRef(/* @__PURE__ */ new Set());
2678
- const roomUpdateListeners = useRef(/* @__PURE__ */ new Set());
2679
2471
  const trackStateListeners = useRef(/* @__PURE__ */ new Set());
2680
2472
  const recordingStartedListeners = useRef(/* @__PURE__ */ new Set());
2681
2473
  const recordingStoppedListeners = useRef(/* @__PURE__ */ new Set());
@@ -2700,9 +2492,6 @@ var MeetingProvider = ({
2700
2492
  onMeetingLeft: () => {
2701
2493
  meetingLeftListeners.current.forEach((fn) => fn());
2702
2494
  },
2703
- onRoomUpdate: (data) => {
2704
- roomUpdateListeners.current.forEach((fn) => fn(data));
2705
- },
2706
2495
  onTrackStateChanged: (track) => {
2707
2496
  trackStateListeners.current.forEach((fn) => fn(track));
2708
2497
  },
@@ -2801,10 +2590,6 @@ var MeetingProvider = ({
2801
2590
  meetingLeftListeners.current.delete(cb);
2802
2591
  };
2803
2592
  },
2804
- onRoomUpdate: (cb) => {
2805
- roomUpdateListeners.current.add(cb);
2806
- return () => roomUpdateListeners.current.delete(cb);
2807
- },
2808
2593
  onTrackStateChanged: (cb) => {
2809
2594
  trackStateListeners.current.add(cb);
2810
2595
  return () => trackStateListeners.current.delete(cb);