@signalwire/js 4.0.0-rc.1 → 4.0.0-rc.2
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/browser.mjs +283 -156
- package/dist/browser.mjs.map +1 -1
- package/dist/browser.umd.js +283 -155
- package/dist/browser.umd.js.map +1 -1
- package/dist/index.cjs +196 -232
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +69 -3
- package/dist/index.d.cts.map +1 -1
- package/dist/index.d.mts +69 -3
- package/dist/index.d.mts.map +1 -1
- package/dist/index.mjs +121 -158
- package/dist/index.mjs.map +1 -1
- package/dist/operators/index.cjs +1 -1
- package/dist/operators/index.mjs +1 -1
- package/dist/{operators-D6a2J1KA.cjs → operators-B8ipd4Xl.cjs} +561 -1
- package/dist/operators-B8ipd4Xl.cjs.map +1 -0
- package/dist/{operators-CX_lCCJm.mjs → operators-BlUtq-t0.mjs} +166 -2
- package/dist/operators-BlUtq-t0.mjs.map +1 -0
- package/package.json +1 -1
- package/dist/operators-CX_lCCJm.mjs.map +0 -1
- package/dist/operators-D6a2J1KA.cjs.map +0 -1
package/dist/browser.mjs
CHANGED
|
@@ -9015,6 +9015,143 @@ var Destroyable = class {
|
|
|
9015
9015
|
}
|
|
9016
9016
|
};
|
|
9017
9017
|
|
|
9018
|
+
//#endregion
|
|
9019
|
+
//#region src/core/constants.ts
|
|
9020
|
+
const INVITE_VERSION = 1e3;
|
|
9021
|
+
const DEFAULT_ICE_CANDIDATE_TIMEOUT_MS = 600;
|
|
9022
|
+
const DEFAULT_ICE_GATHERING_TIMEOUT_MS = 6e3;
|
|
9023
|
+
const DEFAULT_RECONNECT_CALLS_TIMEOUT_MS = 300 * 1e3;
|
|
9024
|
+
const DEFAULT_CONNECTION_TIMEOUT_MS = 1e4;
|
|
9025
|
+
const DEFAULT_RECONNECT_DELAY_MIN_MS = 100;
|
|
9026
|
+
const DEFAULT_RECONNECT_DELAY_MAX_MS = 3e3;
|
|
9027
|
+
const DEFAULT_DEVICE_DEBOUNCE_TIME_MS = 1500;
|
|
9028
|
+
const DEFAULT_DEVICE_POLLING_INTERVAL_MS = 0;
|
|
9029
|
+
const PREFERENCES_STORAGE_KEY = "sw:preferences";
|
|
9030
|
+
/** Scope value that enables automatic token refresh. */
|
|
9031
|
+
const SAT_REFRESH_SCOPE = "sat:refresh";
|
|
9032
|
+
/** API endpoints for device token operations. */
|
|
9033
|
+
const DEVICE_TOKEN_ENDPOINT = "/api/fabric/subscriber/devices/token";
|
|
9034
|
+
const DEVICE_REFRESH_ENDPOINT = "/api/fabric/subscriber/devices/refresh";
|
|
9035
|
+
/** Default device token TTL in seconds (15 minutes). */
|
|
9036
|
+
const DEVICE_TOKEN_DEFAULT_EXPIRE_IN = 900;
|
|
9037
|
+
/** Buffer time in milliseconds before expiry to trigger refresh. */
|
|
9038
|
+
const DEVICE_TOKEN_REFRESH_BUFFER_MS = 3e4;
|
|
9039
|
+
/** Maximum retry attempts for device token refresh on transient failure. */
|
|
9040
|
+
const DEVICE_TOKEN_REFRESH_MAX_RETRIES = 3;
|
|
9041
|
+
/** Base delay in milliseconds for exponential backoff on refresh retry. */
|
|
9042
|
+
const DEVICE_TOKEN_REFRESH_RETRY_BASE_MS = 1e3;
|
|
9043
|
+
/** Maximum retry attempts for developer credential refresh on transient failure. */
|
|
9044
|
+
const CREDENTIAL_REFRESH_MAX_RETRIES = 5;
|
|
9045
|
+
/** Base delay in milliseconds for exponential backoff on credential refresh retry. */
|
|
9046
|
+
const CREDENTIAL_REFRESH_RETRY_BASE_MS = 1e3;
|
|
9047
|
+
/** Maximum delay in milliseconds for credential refresh backoff. */
|
|
9048
|
+
const CREDENTIAL_REFRESH_MAX_DELAY_MS = 3e4;
|
|
9049
|
+
/** Buffer in milliseconds before token expiry to trigger refresh. */
|
|
9050
|
+
const CREDENTIAL_REFRESH_BUFFER_MS = 5e3;
|
|
9051
|
+
/**
|
|
9052
|
+
* Maximum time the coordinator will wait for `DeviceTokenManager.activate()`
|
|
9053
|
+
* to resolve before treating the activation as failed and falling back to
|
|
9054
|
+
* the developer-provided refresh path. Prevents a wedged HTTP layer from
|
|
9055
|
+
* leaving the session with no active refresh mechanism.
|
|
9056
|
+
*/
|
|
9057
|
+
const CREDENTIAL_ACTIVATE_TIMEOUT_MS = 3e4;
|
|
9058
|
+
/** JSON-RPC error code for requester validation failure (corrupted auth state). */
|
|
9059
|
+
const RPC_ERROR_REQUESTER_VALIDATION_FAILED = -32003;
|
|
9060
|
+
/** JSON-RPC error code for invalid params (e.g., missing authentication block). */
|
|
9061
|
+
const RPC_ERROR_INVALID_PARAMS = -32602;
|
|
9062
|
+
/** JSON-RPC error code for authentication failure (invalid token, missing DPoP, etc.). */
|
|
9063
|
+
const RPC_ERROR_AUTHENTICATION_FAILED = -32002;
|
|
9064
|
+
/** Error names browsers use for a media permission denial (user or policy). */
|
|
9065
|
+
const MEDIA_ACCESS_DENIAL_NAMES = [
|
|
9066
|
+
"NotAllowedError",
|
|
9067
|
+
"SecurityError",
|
|
9068
|
+
"PermissionDeniedError"
|
|
9069
|
+
];
|
|
9070
|
+
/** Default polling interval for RTCPeerConnection.getStats() in milliseconds. */
|
|
9071
|
+
const DEFAULT_STATS_POLLING_INTERVAL_MS = 1e3;
|
|
9072
|
+
/** Number of initial samples used to build a baseline for spike detection. */
|
|
9073
|
+
const DEFAULT_STATS_BASELINE_SAMPLES = 10;
|
|
9074
|
+
/** Duration in ms with no inbound audio packets before emitting a critical issue. */
|
|
9075
|
+
const DEFAULT_STATS_NO_PACKET_THRESHOLD_MS = 2e3;
|
|
9076
|
+
/** Multiplier applied to baseline RTT to detect a warning-level RTT spike. */
|
|
9077
|
+
const DEFAULT_STATS_RTT_SPIKE_MULTIPLIER = 3;
|
|
9078
|
+
/** Packet loss fraction (0-1) above which a warning is emitted. */
|
|
9079
|
+
const DEFAULT_STATS_PACKET_LOSS_THRESHOLD = .05;
|
|
9080
|
+
/** Multiplier applied to baseline jitter to detect a jitter spike. */
|
|
9081
|
+
const DEFAULT_STATS_JITTER_SPIKE_MULTIPLIER = 4;
|
|
9082
|
+
/** Number of seconds of metrics history to retain. */
|
|
9083
|
+
const DEFAULT_STATS_HISTORY_SIZE = 30;
|
|
9084
|
+
/** Maximum keyframe requests allowed within a single burst window. */
|
|
9085
|
+
const DEFAULT_KEYFRAME_MAX_BURST$1 = 3;
|
|
9086
|
+
/** Duration of the keyframe burst window in milliseconds. */
|
|
9087
|
+
const DEFAULT_KEYFRAME_BURST_WINDOW_MS$1 = 3e3;
|
|
9088
|
+
/** Cooldown period in ms after burst limit is reached before allowing more keyframes. */
|
|
9089
|
+
const DEFAULT_KEYFRAME_COOLDOWN_MS$1 = 1e4;
|
|
9090
|
+
/** Minimum time between re-INVITE attempts in milliseconds. */
|
|
9091
|
+
const DEFAULT_REINVITE_DEBOUNCE_TIME_MS = 1e4;
|
|
9092
|
+
/** Maximum number of re-INVITE attempts per call. */
|
|
9093
|
+
const DEFAULT_REINVITE_MAX_ATTEMPTS = 3;
|
|
9094
|
+
/** Timeout for a single re-INVITE attempt in milliseconds. */
|
|
9095
|
+
const DEFAULT_REINVITE_TIMEOUT_MS = 5e3;
|
|
9096
|
+
/** Debounce window in ms to collapse multiple detection signals into one trigger. */
|
|
9097
|
+
const DEFAULT_RECOVERY_DEBOUNCE_TIME_MS = 2e3;
|
|
9098
|
+
/** Cooldown period in ms between recovery attempts. */
|
|
9099
|
+
const DEFAULT_RECOVERY_COOLDOWN_MS = 1e4;
|
|
9100
|
+
/** Grace period in ms before treating ICE 'disconnected' as a failure. */
|
|
9101
|
+
const DEFAULT_ICE_DISCONNECTED_GRACE_PERIOD_MS = 3e3;
|
|
9102
|
+
/** Timeout for a single ICE restart attempt in milliseconds. */
|
|
9103
|
+
const DEFAULT_ICE_RESTART_TIMEOUT_MS$1 = 5e3;
|
|
9104
|
+
/** Maximum recovery attempts before emitting 'max_attempts_reached'. */
|
|
9105
|
+
const DEFAULT_MAX_RECOVERY_ATTEMPTS = 3;
|
|
9106
|
+
/** Upper bound in ms for waiting on iceGatheringState === 'complete' after an ICE restart. */
|
|
9107
|
+
const ICE_GATHERING_COMPLETE_TIMEOUT_MS = 1e4;
|
|
9108
|
+
/** Upper bound in ms for waiting on RTCPeerConnection.connectionState === 'connected' after a recovery ICE restart. */
|
|
9109
|
+
const PEER_CONNECTION_RECOVERY_WAIT_MS = 5e3;
|
|
9110
|
+
/** Polling interval in ms while waiting for RTCPeerConnection.connectionState to transition. */
|
|
9111
|
+
const PEER_CONNECTION_RECOVERY_POLL_MS = 100;
|
|
9112
|
+
/** Polling interval for LocalAudioPipeline.level$ (ms). ~30fps is smooth for meters. */
|
|
9113
|
+
const AUDIO_LEVEL_POLL_INTERVAL_MS = 33;
|
|
9114
|
+
/** RMS level threshold (0..1) above which the local participant is considered speaking. */
|
|
9115
|
+
const VAD_THRESHOLD = .03;
|
|
9116
|
+
/** Hold window in ms below the threshold before speaking$ flips back to false. */
|
|
9117
|
+
const VAD_HOLD_MS = 250;
|
|
9118
|
+
/** Whether to persist device selections to storage by default. */
|
|
9119
|
+
const DEFAULT_PERSIST_DEVICE_SELECTION = true;
|
|
9120
|
+
/** Whether to auto-apply device changes to active calls by default. */
|
|
9121
|
+
const DEFAULT_SYNC_DEVICES_TO_ACTIVE_CALLS = true;
|
|
9122
|
+
/** Storage keys for persisted device selections. */
|
|
9123
|
+
const DEVICE_STORAGE_KEY_AUDIO_INPUT = "sw:device:audioinput";
|
|
9124
|
+
const DEVICE_STORAGE_KEY_AUDIO_OUTPUT = "sw:device:audiooutput";
|
|
9125
|
+
const DEVICE_STORAGE_KEY_VIDEO_INPUT = "sw:device:videoinput";
|
|
9126
|
+
/** Whether to auto-mute video when the tab becomes hidden. */
|
|
9127
|
+
const DEFAULT_AUTO_MUTE_VIDEO_ON_HIDDEN = false;
|
|
9128
|
+
/** Whether to re-enumerate devices when the page becomes visible. */
|
|
9129
|
+
const DEFAULT_REFRESH_DEVICES_ON_VISIBLE = true;
|
|
9130
|
+
/** Whether to check peer connection health when the page becomes visible. */
|
|
9131
|
+
const DEFAULT_CHECK_CONNECTION_ON_VISIBLE = true;
|
|
9132
|
+
/** Whether automatic video degradation on low bandwidth is enabled. */
|
|
9133
|
+
const DEFAULT_ENABLE_AUTO_DEGRADATION = true;
|
|
9134
|
+
/** Bitrate in kbps below which video is automatically disabled. */
|
|
9135
|
+
const DEFAULT_DEGRADATION_BITRATE_THRESHOLD_KBPS = 150;
|
|
9136
|
+
/** Bitrate in kbps above which video is automatically re-enabled (hysteresis). */
|
|
9137
|
+
const DEFAULT_DEGRADATION_RECOVERY_THRESHOLD_KBPS = 300;
|
|
9138
|
+
/** Whether relay-only escalation is enabled as a last-resort recovery tier. */
|
|
9139
|
+
const DEFAULT_ENABLE_RELAY_FALLBACK = true;
|
|
9140
|
+
/** Whether to listen for browser online/offline/connection events. */
|
|
9141
|
+
const DEFAULT_ENABLE_NETWORK_CHANGE_DETECTION = true;
|
|
9142
|
+
/** Whether to intercept server-sent media-timeout hangups and attempt recovery. */
|
|
9143
|
+
const DEFAULT_ENABLE_SERVER_HANGUP_INTERCEPTION = true;
|
|
9144
|
+
/** Default video track constraints applied when video is enabled without explicit constraints. */
|
|
9145
|
+
const DEFAULT_VIDEO_CONSTRAINTS = {
|
|
9146
|
+
width: { ideal: 1280 },
|
|
9147
|
+
height: { ideal: 720 },
|
|
9148
|
+
aspectRatio: 16 / 9
|
|
9149
|
+
};
|
|
9150
|
+
/** Whether stereo Opus is enabled by default. */
|
|
9151
|
+
const DEFAULT_STEREO_AUDIO = false;
|
|
9152
|
+
/** Max average bitrate for stereo Opus in bits per second. */
|
|
9153
|
+
const DEFAULT_STEREO_MAX_AVERAGE_BITRATE = 51e4;
|
|
9154
|
+
|
|
9018
9155
|
//#endregion
|
|
9019
9156
|
//#region src/core/errors.ts
|
|
9020
9157
|
var UnexpectedError = class extends Error {
|
|
@@ -9224,6 +9361,33 @@ var MediaTrackError = class extends Error {
|
|
|
9224
9361
|
this.name = "MediaTrackError";
|
|
9225
9362
|
}
|
|
9226
9363
|
};
|
|
9364
|
+
/** True when a `getUserMedia`/`getDisplayMedia` rejection is a permission denial. */
|
|
9365
|
+
function isMediaAccessDenial(originalError) {
|
|
9366
|
+
return originalError instanceof Error && MEDIA_ACCESS_DENIAL_NAMES.includes(originalError.name);
|
|
9367
|
+
}
|
|
9368
|
+
/**
|
|
9369
|
+
* Failure to acquire local media (camera, microphone, or screen capture)
|
|
9370
|
+
* via `getUserMedia`/`getDisplayMedia`.
|
|
9371
|
+
*
|
|
9372
|
+
* Non-fatal by default: screenshare and additional-device failures never
|
|
9373
|
+
* end the call, and main-connection failures degrade to receive-only when
|
|
9374
|
+
* possible. The wrapping site sets `fatal` to `true` only when the call
|
|
9375
|
+
* cannot continue (receive-only fallback disabled or no receive intent).
|
|
9376
|
+
*/
|
|
9377
|
+
var MediaAccessError = class extends Error {
|
|
9378
|
+
constructor(operation, media, originalError, fatal = false) {
|
|
9379
|
+
super(`Media access ${isMediaAccessDenial(originalError) ? "denied" : "failed"} for ${operation} (${media})`, { cause: originalError instanceof Error ? originalError : void 0 });
|
|
9380
|
+
this.operation = operation;
|
|
9381
|
+
this.media = media;
|
|
9382
|
+
this.originalError = originalError;
|
|
9383
|
+
this.fatal = fatal;
|
|
9384
|
+
this.name = "MediaAccessError";
|
|
9385
|
+
}
|
|
9386
|
+
/** True when the underlying failure is a permission denial (user or policy). */
|
|
9387
|
+
get denied() {
|
|
9388
|
+
return isMediaAccessDenial(this.originalError);
|
|
9389
|
+
}
|
|
9390
|
+
};
|
|
9227
9391
|
var DPoPInitError = class extends Error {
|
|
9228
9392
|
constructor(originalError, message = "Failed to initialize DPoP key pair") {
|
|
9229
9393
|
super(message, { cause: originalError instanceof Error ? originalError : void 0 });
|
|
@@ -9873,137 +10037,6 @@ var DeviceHistoryManager = class {
|
|
|
9873
10037
|
}
|
|
9874
10038
|
};
|
|
9875
10039
|
|
|
9876
|
-
//#endregion
|
|
9877
|
-
//#region src/core/constants.ts
|
|
9878
|
-
const INVITE_VERSION = 1e3;
|
|
9879
|
-
const DEFAULT_ICE_CANDIDATE_TIMEOUT_MS = 600;
|
|
9880
|
-
const DEFAULT_ICE_GATHERING_TIMEOUT_MS = 6e3;
|
|
9881
|
-
const DEFAULT_RECONNECT_CALLS_TIMEOUT_MS = 300 * 1e3;
|
|
9882
|
-
const DEFAULT_CONNECTION_TIMEOUT_MS = 1e4;
|
|
9883
|
-
const DEFAULT_RECONNECT_DELAY_MIN_MS = 100;
|
|
9884
|
-
const DEFAULT_RECONNECT_DELAY_MAX_MS = 3e3;
|
|
9885
|
-
const DEFAULT_DEVICE_DEBOUNCE_TIME_MS = 1500;
|
|
9886
|
-
const DEFAULT_DEVICE_POLLING_INTERVAL_MS = 0;
|
|
9887
|
-
const PREFERENCES_STORAGE_KEY = "sw:preferences";
|
|
9888
|
-
/** Scope value that enables automatic token refresh. */
|
|
9889
|
-
const SAT_REFRESH_SCOPE = "sat:refresh";
|
|
9890
|
-
/** API endpoints for device token operations. */
|
|
9891
|
-
const DEVICE_TOKEN_ENDPOINT = "/api/fabric/subscriber/devices/token";
|
|
9892
|
-
const DEVICE_REFRESH_ENDPOINT = "/api/fabric/subscriber/devices/refresh";
|
|
9893
|
-
/** Default device token TTL in seconds (15 minutes). */
|
|
9894
|
-
const DEVICE_TOKEN_DEFAULT_EXPIRE_IN = 900;
|
|
9895
|
-
/** Buffer time in milliseconds before expiry to trigger refresh. */
|
|
9896
|
-
const DEVICE_TOKEN_REFRESH_BUFFER_MS = 3e4;
|
|
9897
|
-
/** Maximum retry attempts for device token refresh on transient failure. */
|
|
9898
|
-
const DEVICE_TOKEN_REFRESH_MAX_RETRIES = 3;
|
|
9899
|
-
/** Base delay in milliseconds for exponential backoff on refresh retry. */
|
|
9900
|
-
const DEVICE_TOKEN_REFRESH_RETRY_BASE_MS = 1e3;
|
|
9901
|
-
/** Maximum retry attempts for developer credential refresh on transient failure. */
|
|
9902
|
-
const CREDENTIAL_REFRESH_MAX_RETRIES = 5;
|
|
9903
|
-
/** Base delay in milliseconds for exponential backoff on credential refresh retry. */
|
|
9904
|
-
const CREDENTIAL_REFRESH_RETRY_BASE_MS = 1e3;
|
|
9905
|
-
/** Maximum delay in milliseconds for credential refresh backoff. */
|
|
9906
|
-
const CREDENTIAL_REFRESH_MAX_DELAY_MS = 3e4;
|
|
9907
|
-
/** Buffer in milliseconds before token expiry to trigger refresh. */
|
|
9908
|
-
const CREDENTIAL_REFRESH_BUFFER_MS = 5e3;
|
|
9909
|
-
/**
|
|
9910
|
-
* Maximum time the coordinator will wait for `DeviceTokenManager.activate()`
|
|
9911
|
-
* to resolve before treating the activation as failed and falling back to
|
|
9912
|
-
* the developer-provided refresh path. Prevents a wedged HTTP layer from
|
|
9913
|
-
* leaving the session with no active refresh mechanism.
|
|
9914
|
-
*/
|
|
9915
|
-
const CREDENTIAL_ACTIVATE_TIMEOUT_MS = 3e4;
|
|
9916
|
-
/** JSON-RPC error code for requester validation failure (corrupted auth state). */
|
|
9917
|
-
const RPC_ERROR_REQUESTER_VALIDATION_FAILED = -32003;
|
|
9918
|
-
/** JSON-RPC error code for invalid params (e.g., missing authentication block). */
|
|
9919
|
-
const RPC_ERROR_INVALID_PARAMS = -32602;
|
|
9920
|
-
/** JSON-RPC error code for authentication failure (invalid token, missing DPoP, etc.). */
|
|
9921
|
-
const RPC_ERROR_AUTHENTICATION_FAILED = -32002;
|
|
9922
|
-
/** Default polling interval for RTCPeerConnection.getStats() in milliseconds. */
|
|
9923
|
-
const DEFAULT_STATS_POLLING_INTERVAL_MS = 1e3;
|
|
9924
|
-
/** Number of initial samples used to build a baseline for spike detection. */
|
|
9925
|
-
const DEFAULT_STATS_BASELINE_SAMPLES = 10;
|
|
9926
|
-
/** Duration in ms with no inbound audio packets before emitting a critical issue. */
|
|
9927
|
-
const DEFAULT_STATS_NO_PACKET_THRESHOLD_MS = 2e3;
|
|
9928
|
-
/** Multiplier applied to baseline RTT to detect a warning-level RTT spike. */
|
|
9929
|
-
const DEFAULT_STATS_RTT_SPIKE_MULTIPLIER = 3;
|
|
9930
|
-
/** Packet loss fraction (0-1) above which a warning is emitted. */
|
|
9931
|
-
const DEFAULT_STATS_PACKET_LOSS_THRESHOLD = .05;
|
|
9932
|
-
/** Multiplier applied to baseline jitter to detect a jitter spike. */
|
|
9933
|
-
const DEFAULT_STATS_JITTER_SPIKE_MULTIPLIER = 4;
|
|
9934
|
-
/** Number of seconds of metrics history to retain. */
|
|
9935
|
-
const DEFAULT_STATS_HISTORY_SIZE = 30;
|
|
9936
|
-
/** Maximum keyframe requests allowed within a single burst window. */
|
|
9937
|
-
const DEFAULT_KEYFRAME_MAX_BURST$1 = 3;
|
|
9938
|
-
/** Duration of the keyframe burst window in milliseconds. */
|
|
9939
|
-
const DEFAULT_KEYFRAME_BURST_WINDOW_MS$1 = 3e3;
|
|
9940
|
-
/** Cooldown period in ms after burst limit is reached before allowing more keyframes. */
|
|
9941
|
-
const DEFAULT_KEYFRAME_COOLDOWN_MS$1 = 1e4;
|
|
9942
|
-
/** Minimum time between re-INVITE attempts in milliseconds. */
|
|
9943
|
-
const DEFAULT_REINVITE_DEBOUNCE_TIME_MS = 1e4;
|
|
9944
|
-
/** Maximum number of re-INVITE attempts per call. */
|
|
9945
|
-
const DEFAULT_REINVITE_MAX_ATTEMPTS = 3;
|
|
9946
|
-
/** Timeout for a single re-INVITE attempt in milliseconds. */
|
|
9947
|
-
const DEFAULT_REINVITE_TIMEOUT_MS = 5e3;
|
|
9948
|
-
/** Debounce window in ms to collapse multiple detection signals into one trigger. */
|
|
9949
|
-
const DEFAULT_RECOVERY_DEBOUNCE_TIME_MS = 2e3;
|
|
9950
|
-
/** Cooldown period in ms between recovery attempts. */
|
|
9951
|
-
const DEFAULT_RECOVERY_COOLDOWN_MS = 1e4;
|
|
9952
|
-
/** Grace period in ms before treating ICE 'disconnected' as a failure. */
|
|
9953
|
-
const DEFAULT_ICE_DISCONNECTED_GRACE_PERIOD_MS = 3e3;
|
|
9954
|
-
/** Timeout for a single ICE restart attempt in milliseconds. */
|
|
9955
|
-
const DEFAULT_ICE_RESTART_TIMEOUT_MS$1 = 5e3;
|
|
9956
|
-
/** Maximum recovery attempts before emitting 'max_attempts_reached'. */
|
|
9957
|
-
const DEFAULT_MAX_RECOVERY_ATTEMPTS = 3;
|
|
9958
|
-
/** Upper bound in ms for waiting on iceGatheringState === 'complete' after an ICE restart. */
|
|
9959
|
-
const ICE_GATHERING_COMPLETE_TIMEOUT_MS = 1e4;
|
|
9960
|
-
/** Upper bound in ms for waiting on RTCPeerConnection.connectionState === 'connected' after a recovery ICE restart. */
|
|
9961
|
-
const PEER_CONNECTION_RECOVERY_WAIT_MS = 5e3;
|
|
9962
|
-
/** Polling interval in ms while waiting for RTCPeerConnection.connectionState to transition. */
|
|
9963
|
-
const PEER_CONNECTION_RECOVERY_POLL_MS = 100;
|
|
9964
|
-
/** Polling interval for LocalAudioPipeline.level$ (ms). ~30fps is smooth for meters. */
|
|
9965
|
-
const AUDIO_LEVEL_POLL_INTERVAL_MS = 33;
|
|
9966
|
-
/** RMS level threshold (0..1) above which the local participant is considered speaking. */
|
|
9967
|
-
const VAD_THRESHOLD = .03;
|
|
9968
|
-
/** Hold window in ms below the threshold before speaking$ flips back to false. */
|
|
9969
|
-
const VAD_HOLD_MS = 250;
|
|
9970
|
-
/** Whether to persist device selections to storage by default. */
|
|
9971
|
-
const DEFAULT_PERSIST_DEVICE_SELECTION = true;
|
|
9972
|
-
/** Whether to auto-apply device changes to active calls by default. */
|
|
9973
|
-
const DEFAULT_SYNC_DEVICES_TO_ACTIVE_CALLS = true;
|
|
9974
|
-
/** Storage keys for persisted device selections. */
|
|
9975
|
-
const DEVICE_STORAGE_KEY_AUDIO_INPUT = "sw:device:audioinput";
|
|
9976
|
-
const DEVICE_STORAGE_KEY_AUDIO_OUTPUT = "sw:device:audiooutput";
|
|
9977
|
-
const DEVICE_STORAGE_KEY_VIDEO_INPUT = "sw:device:videoinput";
|
|
9978
|
-
/** Whether to auto-mute video when the tab becomes hidden. */
|
|
9979
|
-
const DEFAULT_AUTO_MUTE_VIDEO_ON_HIDDEN = false;
|
|
9980
|
-
/** Whether to re-enumerate devices when the page becomes visible. */
|
|
9981
|
-
const DEFAULT_REFRESH_DEVICES_ON_VISIBLE = true;
|
|
9982
|
-
/** Whether to check peer connection health when the page becomes visible. */
|
|
9983
|
-
const DEFAULT_CHECK_CONNECTION_ON_VISIBLE = true;
|
|
9984
|
-
/** Whether automatic video degradation on low bandwidth is enabled. */
|
|
9985
|
-
const DEFAULT_ENABLE_AUTO_DEGRADATION = true;
|
|
9986
|
-
/** Bitrate in kbps below which video is automatically disabled. */
|
|
9987
|
-
const DEFAULT_DEGRADATION_BITRATE_THRESHOLD_KBPS = 150;
|
|
9988
|
-
/** Bitrate in kbps above which video is automatically re-enabled (hysteresis). */
|
|
9989
|
-
const DEFAULT_DEGRADATION_RECOVERY_THRESHOLD_KBPS = 300;
|
|
9990
|
-
/** Whether relay-only escalation is enabled as a last-resort recovery tier. */
|
|
9991
|
-
const DEFAULT_ENABLE_RELAY_FALLBACK = true;
|
|
9992
|
-
/** Whether to listen for browser online/offline/connection events. */
|
|
9993
|
-
const DEFAULT_ENABLE_NETWORK_CHANGE_DETECTION = true;
|
|
9994
|
-
/** Whether to intercept server-sent media-timeout hangups and attempt recovery. */
|
|
9995
|
-
const DEFAULT_ENABLE_SERVER_HANGUP_INTERCEPTION = true;
|
|
9996
|
-
/** Default video track constraints applied when video is enabled without explicit constraints. */
|
|
9997
|
-
const DEFAULT_VIDEO_CONSTRAINTS = {
|
|
9998
|
-
width: { ideal: 1280 },
|
|
9999
|
-
height: { ideal: 720 },
|
|
10000
|
-
aspectRatio: 16 / 9
|
|
10001
|
-
};
|
|
10002
|
-
/** Whether stereo Opus is enabled by default. */
|
|
10003
|
-
const DEFAULT_STEREO_AUDIO = false;
|
|
10004
|
-
/** Max average bitrate for stereo Opus in bits per second. */
|
|
10005
|
-
const DEFAULT_STEREO_MAX_AVERAGE_BITRATE = 51e4;
|
|
10006
|
-
|
|
10007
10040
|
//#endregion
|
|
10008
10041
|
//#region src/utils/time.ts
|
|
10009
10042
|
function fromSecToMs(seconds) {
|
|
@@ -14051,12 +14084,21 @@ var SelfParticipant = class extends Participant {
|
|
|
14051
14084
|
noise_suppression: true
|
|
14052
14085
|
});
|
|
14053
14086
|
}
|
|
14054
|
-
/**
|
|
14087
|
+
/**
|
|
14088
|
+
* Starts sharing the local screen.
|
|
14089
|
+
*
|
|
14090
|
+
* The call is unaffected when acquisition fails.
|
|
14091
|
+
*
|
|
14092
|
+
* @throws The raw `getDisplayMedia` error. A dismissed picker or a
|
|
14093
|
+
* permission denial rejects with a `NotAllowedError` `DOMException` —
|
|
14094
|
+
* inspect `error.name` to tell benign cancels apart from real failures.
|
|
14095
|
+
*/
|
|
14055
14096
|
async startScreenShare() {
|
|
14056
14097
|
try {
|
|
14057
14098
|
await this.vertoManager.addScreenMedia();
|
|
14058
14099
|
} catch (error) {
|
|
14059
14100
|
logger$24.error("[Participant.startScreenShare] Screen share error:", error);
|
|
14101
|
+
throw error;
|
|
14060
14102
|
}
|
|
14061
14103
|
}
|
|
14062
14104
|
/** Observable of the current screen share status. */
|
|
@@ -14071,12 +14113,20 @@ var SelfParticipant = class extends Participant {
|
|
|
14071
14113
|
async stopScreenShare() {
|
|
14072
14114
|
return this.vertoManager.removeScreenMedia();
|
|
14073
14115
|
}
|
|
14074
|
-
/**
|
|
14116
|
+
/**
|
|
14117
|
+
* Adds an additional media input device to the call.
|
|
14118
|
+
*
|
|
14119
|
+
* The call is unaffected when acquisition fails.
|
|
14120
|
+
*
|
|
14121
|
+
* @throws The raw `getUserMedia` error (e.g. `NotAllowedError` on
|
|
14122
|
+
* permission denial) — inspect `error.name` to decide how to react.
|
|
14123
|
+
*/
|
|
14075
14124
|
async addAdditionalDevice(options) {
|
|
14076
14125
|
try {
|
|
14077
14126
|
await this.vertoManager.addInputDevice(options);
|
|
14078
14127
|
} catch (error) {
|
|
14079
|
-
logger$24.error("[Participant.
|
|
14128
|
+
logger$24.error("[Participant.addAdditionalDevice] Additional device error:", error);
|
|
14129
|
+
throw error;
|
|
14080
14130
|
}
|
|
14081
14131
|
}
|
|
14082
14132
|
/** Removes an additional media input device by ID. */
|
|
@@ -15708,7 +15758,7 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
15708
15758
|
logger$17.debug(`[RTCPeerConnectionController] ${kind} input device selected:`, deviceInfo?.label);
|
|
15709
15759
|
} catch (error) {
|
|
15710
15760
|
logger$17.error(`[RTCPeerConnectionController] Failed to select ${kind} input device:`, error);
|
|
15711
|
-
this._errors$.next(
|
|
15761
|
+
this._errors$.next(new MediaTrackError("updateSelectedInputDevice", kind, error));
|
|
15712
15762
|
throw error;
|
|
15713
15763
|
}
|
|
15714
15764
|
};
|
|
@@ -15930,7 +15980,7 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
15930
15980
|
case "main":
|
|
15931
15981
|
default: return {
|
|
15932
15982
|
...options,
|
|
15933
|
-
offerToReceiveAudio: true,
|
|
15983
|
+
offerToReceiveAudio: this.options.receiveAudio ?? true,
|
|
15934
15984
|
offerToReceiveVideo: this.options.receiveVideo ?? Boolean(this.inputVideoDeviceConstraints)
|
|
15935
15985
|
};
|
|
15936
15986
|
}
|
|
@@ -16084,13 +16134,14 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16084
16134
|
*/
|
|
16085
16135
|
async acceptInbound(mediaOverrides) {
|
|
16086
16136
|
if (mediaOverrides) {
|
|
16087
|
-
const { audio, video, receiveAudio, receiveVideo } = mediaOverrides;
|
|
16137
|
+
const { audio, video, receiveAudio, receiveVideo, fallbackToReceiveOnly } = mediaOverrides;
|
|
16088
16138
|
this.options = {
|
|
16089
16139
|
...this.options,
|
|
16090
16140
|
...audio !== void 0 ? { audio } : {},
|
|
16091
16141
|
...video !== void 0 ? { video } : {},
|
|
16092
16142
|
...receiveAudio !== void 0 ? { receiveAudio } : {},
|
|
16093
|
-
...receiveVideo !== void 0 ? { receiveVideo } : {}
|
|
16143
|
+
...receiveVideo !== void 0 ? { receiveVideo } : {},
|
|
16144
|
+
...fallbackToReceiveOnly !== void 0 ? { fallbackToReceiveOnly } : {}
|
|
16094
16145
|
};
|
|
16095
16146
|
this.transceiverController?.updateOptions({
|
|
16096
16147
|
receiveAudio: this.receiveAudio,
|
|
@@ -16247,7 +16298,19 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16247
16298
|
}
|
|
16248
16299
|
async setupLocalTracks() {
|
|
16249
16300
|
logger$17.debug("[RTCPeerConnectionController] Setting up local tracks/transceivers.");
|
|
16250
|
-
|
|
16301
|
+
if (this.hasNoLocalMediaToSend()) {
|
|
16302
|
+
if (!this.receiveAudio && !this.receiveVideo) throw new InvalidParams("Call requests no media: enable audio/video or receiveAudio/receiveVideo");
|
|
16303
|
+
logger$17.debug("[RTCPeerConnectionController] No local media requested; negotiating receive-only.");
|
|
16304
|
+
this.setupReceiveOnlyTransceivers();
|
|
16305
|
+
return;
|
|
16306
|
+
}
|
|
16307
|
+
let localStream;
|
|
16308
|
+
try {
|
|
16309
|
+
localStream = this.localStream ?? await this.localStreamController.buildLocalStream();
|
|
16310
|
+
} catch (error) {
|
|
16311
|
+
this.handleLocalMediaFailure(error);
|
|
16312
|
+
return;
|
|
16313
|
+
}
|
|
16251
16314
|
if (this.transceiverController?.useAddStream ?? false) {
|
|
16252
16315
|
logger$17.warn("[RTCPeerConnectionController] Using deprecated addStream API to add local stream.");
|
|
16253
16316
|
this.peerConnection?.addStream(localStream);
|
|
@@ -16274,6 +16337,48 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16274
16337
|
}
|
|
16275
16338
|
}
|
|
16276
16339
|
}
|
|
16340
|
+
/** True for a main connection with no local media to send. */
|
|
16341
|
+
hasNoLocalMediaToSend() {
|
|
16342
|
+
const hasInputStreams = Boolean(this.options.inputAudioStream ?? this.options.inputVideoStream);
|
|
16343
|
+
return this.propose === "main" && !this.localStream && !hasInputStreams && !this.inputAudioDeviceConstraints && !this.inputVideoDeviceConstraints;
|
|
16344
|
+
}
|
|
16345
|
+
/** The media kinds this connection wants to send: 'audiovideo' | 'video' | 'audio'. */
|
|
16346
|
+
get requestedMediaKinds() {
|
|
16347
|
+
const wantsAudio = Boolean(this.inputAudioDeviceConstraints);
|
|
16348
|
+
const wantsVideo = Boolean(this.inputVideoDeviceConstraints);
|
|
16349
|
+
if (wantsAudio && wantsVideo) return "audiovideo";
|
|
16350
|
+
return wantsVideo ? "video" : "audio";
|
|
16351
|
+
}
|
|
16352
|
+
/**
|
|
16353
|
+
* Handle a local media acquisition failure with a typed, semantically
|
|
16354
|
+
* accurate MediaAccessError created at the acquisition site:
|
|
16355
|
+
* - Auxiliary connections (screenshare / additional-device) throw a
|
|
16356
|
+
* non-fatal error — VertoManager surfaces it and the call is unaffected.
|
|
16357
|
+
* - The main connection degrades to receive-only when allowed (default),
|
|
16358
|
+
* otherwise fails with a fatal error.
|
|
16359
|
+
*/
|
|
16360
|
+
handleLocalMediaFailure(error) {
|
|
16361
|
+
if (this.propose === "screenshare") throw new MediaAccessError("startScreenShare", "screen", error, false);
|
|
16362
|
+
if (this.propose === "additional-device") throw new MediaAccessError("addInputDevice", this.requestedMediaKinds, error, false);
|
|
16363
|
+
const canReceive = this.receiveAudio || this.receiveVideo;
|
|
16364
|
+
if (!((this.options.fallbackToReceiveOnly ?? true) && canReceive)) throw new MediaAccessError("acquireLocalMedia", this.requestedMediaKinds, error, true);
|
|
16365
|
+
logger$17.warn("[RTCPeerConnectionController] Local media unavailable; continuing receive-only:", error);
|
|
16366
|
+
this._errors$.next(new MediaAccessError("acquireLocalMedia", this.requestedMediaKinds, error, false));
|
|
16367
|
+
this.setupReceiveOnlyTransceivers();
|
|
16368
|
+
}
|
|
16369
|
+
/**
|
|
16370
|
+
* Negotiate receive-only m-lines when there are no local tracks to send.
|
|
16371
|
+
* Only offer-type connections add transceivers — answer-type connections
|
|
16372
|
+
* reuse the transceivers created from the remote offer.
|
|
16373
|
+
*/
|
|
16374
|
+
setupReceiveOnlyTransceivers() {
|
|
16375
|
+
if (this.type !== "offer") return;
|
|
16376
|
+
if (this.transceiverController?.useAddTransceivers ?? false) {
|
|
16377
|
+
this.peerConnection?.addTransceiver("audio", { direction: this.receiveAudio ? "recvonly" : "inactive" });
|
|
16378
|
+
this.peerConnection?.addTransceiver("video", { direction: this.receiveVideo ? "recvonly" : "inactive" });
|
|
16379
|
+
}
|
|
16380
|
+
if (!this.isNegotiating) this.negotiationNeeded$.next();
|
|
16381
|
+
}
|
|
16277
16382
|
async getUserMedia(constraints) {
|
|
16278
16383
|
return (this.options.webRTCApiProvider?.mediaDevices ?? navigator.mediaDevices).getUserMedia(constraints);
|
|
16279
16384
|
}
|
|
@@ -16310,7 +16415,7 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16310
16415
|
stream = await this.getUserMedia({ audio: constraints });
|
|
16311
16416
|
} catch (error) {
|
|
16312
16417
|
logger$17.error("[RTCPeerConnectionController] Failed to re-acquire mic for pipeline restore:", error);
|
|
16313
|
-
this._errors$.next(
|
|
16418
|
+
this._errors$.next(new MediaTrackError("restoreAudioPipelineInput", "audio", error));
|
|
16314
16419
|
return;
|
|
16315
16420
|
}
|
|
16316
16421
|
const newTrack = stream.getAudioTracks().at(0);
|
|
@@ -16372,7 +16477,7 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16372
16477
|
logger$17.debug(`[RTCPeerConnectionController] ${track.kind} track added:`, track.id);
|
|
16373
16478
|
} catch (error) {
|
|
16374
16479
|
logger$17.error(`[RTCPeerConnectionController] Failed to add ${track.kind} track:`, error);
|
|
16375
|
-
this._errors$.next(
|
|
16480
|
+
this._errors$.next(new MediaTrackError("addLocalTrack", track.kind, error));
|
|
16376
16481
|
throw error;
|
|
16377
16482
|
}
|
|
16378
16483
|
}
|
|
@@ -16397,7 +16502,7 @@ var RTCPeerConnectionController = class extends Destroyable {
|
|
|
16397
16502
|
logger$17.debug(`[RTCPeerConnectionController] ${sender.track?.kind} track removed:`, trackId);
|
|
16398
16503
|
} catch (error) {
|
|
16399
16504
|
logger$17.error(`[RTCPeerConnectionController] Failed to remove ${sender.track?.kind} track:`, error);
|
|
16400
|
-
this._errors$.next(
|
|
16505
|
+
this._errors$.next(new MediaTrackError("removeLocalTrack", sender.track?.kind ?? "unknown", error));
|
|
16401
16506
|
throw error;
|
|
16402
16507
|
}
|
|
16403
16508
|
}
|
|
@@ -17006,6 +17111,7 @@ var WebRTCVertoManager = class extends VertoManager {
|
|
|
17006
17111
|
inputVideoStream: options.inputVideoStream,
|
|
17007
17112
|
receiveAudio: options.receiveAudio,
|
|
17008
17113
|
receiveVideo: options.receiveVideo,
|
|
17114
|
+
fallbackToReceiveOnly: options.fallbackToReceiveOnly,
|
|
17009
17115
|
webRTCApiProvider: this.webRTCApiProvider,
|
|
17010
17116
|
preferredVideoCodecs: options.preferredVideoCodecs,
|
|
17011
17117
|
preferredAudioCodecs: options.preferredAudioCodecs,
|
|
@@ -17232,9 +17338,11 @@ var WebRTCVertoManager = class extends VertoManager {
|
|
|
17232
17338
|
await this.initAdditionalPeerConnection("screenshare", options);
|
|
17233
17339
|
}
|
|
17234
17340
|
async initAdditionalPeerConnection(propose, options) {
|
|
17341
|
+
const isScreenShare = propose === "screenshare";
|
|
17342
|
+
let firstPeerConnectionError;
|
|
17235
17343
|
let rtcPeerConnController = null;
|
|
17236
17344
|
try {
|
|
17237
|
-
this._screenShareStatus$.next("starting");
|
|
17345
|
+
if (isScreenShare) this._screenShareStatus$.next("starting");
|
|
17238
17346
|
rtcPeerConnController = new RTCPeerConnectionController({
|
|
17239
17347
|
...options,
|
|
17240
17348
|
...this.RTCPeerConnectionConfig,
|
|
@@ -17242,21 +17350,27 @@ var WebRTCVertoManager = class extends VertoManager {
|
|
|
17242
17350
|
webRTCApiProvider: this.webRTCApiProvider
|
|
17243
17351
|
}, void 0, this.deviceController);
|
|
17244
17352
|
this.setupLocalDescriptionHandler(rtcPeerConnController);
|
|
17245
|
-
if (
|
|
17353
|
+
if (isScreenShare) this._screenShareId = rtcPeerConnController.id;
|
|
17246
17354
|
this._rtcPeerConnectionsMap.set(rtcPeerConnController.id, rtcPeerConnController);
|
|
17247
17355
|
this._rtcPeerConnections$.next(Array.from(this._rtcPeerConnectionsMap.values()));
|
|
17248
17356
|
this.subscribeTo(rtcPeerConnController.errors$, (error) => {
|
|
17249
|
-
|
|
17357
|
+
firstPeerConnectionError ??= error;
|
|
17358
|
+
this.onError?.(error, { fatal: false });
|
|
17250
17359
|
});
|
|
17251
17360
|
await (0, import_cjs$15.firstValueFrom)(rtcPeerConnController.connectionState$.pipe((0, import_cjs$15.filter)((state) => state === "connected"), (0, import_cjs$15.take)(1), (0, import_cjs$15.timeout)(this._screenShareTimeoutMs), (0, import_cjs$15.takeUntil)(this.destroyed$)));
|
|
17252
|
-
this._screenShareStatus$.next("started");
|
|
17253
|
-
logger$16.info(
|
|
17361
|
+
if (isScreenShare) this._screenShareStatus$.next("started");
|
|
17362
|
+
logger$16.info(`[WebRTCManager] Additional peer connection connected (${propose}).`);
|
|
17254
17363
|
return rtcPeerConnController.id;
|
|
17255
17364
|
} catch (error) {
|
|
17256
17365
|
logger$16.warn("[WebRTCManager] Error initializing additional peer connection:", error);
|
|
17257
|
-
this.onError?.(error instanceof Error ? error : new Error(String(error), { cause: error }));
|
|
17258
17366
|
if (rtcPeerConnController) rtcPeerConnController.destroy();
|
|
17259
|
-
this._screenShareStatus$.next("none");
|
|
17367
|
+
if (isScreenShare) this._screenShareStatus$.next("none");
|
|
17368
|
+
if (firstPeerConnectionError) throw firstPeerConnectionError instanceof MediaAccessError && firstPeerConnectionError.originalError instanceof Error ? firstPeerConnectionError.originalError : firstPeerConnectionError;
|
|
17369
|
+
if (error instanceof import_cjs$15.EmptyError) {
|
|
17370
|
+
logger$16.debug("[WebRTCManager] Additional peer connection aborted before connecting.");
|
|
17371
|
+
return;
|
|
17372
|
+
}
|
|
17373
|
+
throw error instanceof Error ? error : new Error(String(error), { cause: error });
|
|
17260
17374
|
}
|
|
17261
17375
|
}
|
|
17262
17376
|
async removeInputDevices(id) {
|
|
@@ -19197,6 +19311,7 @@ function inferCallErrorKind(error) {
|
|
|
19197
19311
|
if (error instanceof RPCTimeoutError) return "timeout";
|
|
19198
19312
|
if (error instanceof JSONRPCError) return "signaling";
|
|
19199
19313
|
if (error instanceof MediaTrackError) return "media";
|
|
19314
|
+
if (error instanceof MediaAccessError) return "media";
|
|
19200
19315
|
if (error instanceof WebSocketConnectionError || error instanceof TransportConnectionError) return "network";
|
|
19201
19316
|
return "internal";
|
|
19202
19317
|
}
|
|
@@ -19213,6 +19328,7 @@ const RECOVERABLE_RPC_CODES = new Set([
|
|
|
19213
19328
|
function isFatalError(error) {
|
|
19214
19329
|
if (error instanceof VertoPongError) return false;
|
|
19215
19330
|
if (error instanceof MediaTrackError) return false;
|
|
19331
|
+
if (error instanceof MediaAccessError) return error.fatal;
|
|
19216
19332
|
if (error instanceof RPCTimeoutError) return false;
|
|
19217
19333
|
if (error instanceof JSONRPCError && RECOVERABLE_RPC_CODES.has(error.code)) return false;
|
|
19218
19334
|
return true;
|
|
@@ -19238,10 +19354,10 @@ var CallFactory = class {
|
|
|
19238
19354
|
return {
|
|
19239
19355
|
vertoManager: new WebRTCVertoManager(callInstance, this.attachManager, this.deviceController, this.webRTCApiProvider, {
|
|
19240
19356
|
nodeId: options.nodeId,
|
|
19241
|
-
onError: (error) => {
|
|
19357
|
+
onError: (error, options$1) => {
|
|
19242
19358
|
const callError = {
|
|
19243
19359
|
kind: inferCallErrorKind(error),
|
|
19244
|
-
fatal: isFatalError(error),
|
|
19360
|
+
fatal: options$1?.fatal ?? isFatalError(error),
|
|
19245
19361
|
error,
|
|
19246
19362
|
callId: callInstance.id
|
|
19247
19363
|
};
|
|
@@ -19704,6 +19820,17 @@ var PendingRPC = class PendingRPC {
|
|
|
19704
19820
|
//#region src/managers/ClientSessionManager.ts
|
|
19705
19821
|
var import_cjs$7 = require_cjs();
|
|
19706
19822
|
const logger$9 = getLogger();
|
|
19823
|
+
/**
|
|
19824
|
+
* Decide whether an error emitted on `call.errors$` during dial should
|
|
19825
|
+
* abort the dial. A non-fatal MediaAccessError means the call degraded to
|
|
19826
|
+
* receive-only and still connects — everything else rejects `dial()` with
|
|
19827
|
+
* the real cause.
|
|
19828
|
+
*
|
|
19829
|
+
* Pure function — exported for unit testing.
|
|
19830
|
+
*/
|
|
19831
|
+
function shouldAbortDial(callError) {
|
|
19832
|
+
return callError.fatal || !(callError.error instanceof MediaAccessError);
|
|
19833
|
+
}
|
|
19707
19834
|
const getAddressSearchURI = (options) => {
|
|
19708
19835
|
const to = options.to?.split("?")[0];
|
|
19709
19836
|
const from$9 = options.from?.startsWith("subscriber://") ? options.from.replace("subscriber://", "") : options.from;
|
|
@@ -20130,7 +20257,7 @@ var ClientSessionManager = class extends Destroyable {
|
|
|
20130
20257
|
to: destinationURI,
|
|
20131
20258
|
...options
|
|
20132
20259
|
});
|
|
20133
|
-
await (0, import_cjs$7.firstValueFrom)((0, import_cjs$7.race)(callSession.selfId$.pipe((0, import_cjs$7.filter)((id) => Boolean(id)), (0, import_cjs$7.take)(1), (0, import_cjs$7.timeout)(this.callCreateTimeout)), callSession.errors$.pipe((0, import_cjs$7.take)(1), (0, import_cjs$7.switchMap)((callError) => (0, import_cjs$7.throwError)(() => callError.error)))));
|
|
20260
|
+
await (0, import_cjs$7.firstValueFrom)((0, import_cjs$7.race)(callSession.selfId$.pipe((0, import_cjs$7.filter)((id) => Boolean(id)), (0, import_cjs$7.take)(1), (0, import_cjs$7.timeout)(this.callCreateTimeout)), callSession.errors$.pipe((0, import_cjs$7.filter)(shouldAbortDial), (0, import_cjs$7.take)(1), (0, import_cjs$7.switchMap)((callError) => (0, import_cjs$7.throwError)(() => callError.error)))));
|
|
20134
20261
|
this._calls$.next({
|
|
20135
20262
|
[`${callSession.id}`]: callSession,
|
|
20136
20263
|
...this._calls$.value
|
|
@@ -21842,7 +21969,7 @@ var SignalWire = class extends Destroyable {
|
|
|
21842
21969
|
logger$1.warn("[SignalWire] Failed to initialize VisibilityController:", error);
|
|
21843
21970
|
}
|
|
21844
21971
|
try {
|
|
21845
|
-
this._diagnosticsCollector = new DiagnosticsCollector({ sdkVersion: "4.0.0-rc.
|
|
21972
|
+
this._diagnosticsCollector = new DiagnosticsCollector({ sdkVersion: "4.0.0-rc.2" });
|
|
21846
21973
|
} catch (error) {
|
|
21847
21974
|
logger$1.warn("[SignalWire] Failed to initialize DiagnosticsCollector:", error);
|
|
21848
21975
|
}
|
|
@@ -22377,7 +22504,7 @@ var StaticCredentialProvider = class {
|
|
|
22377
22504
|
/**
|
|
22378
22505
|
* Library version from package.json, injected at build time.
|
|
22379
22506
|
*/
|
|
22380
|
-
const version = "4.0.0-rc.
|
|
22507
|
+
const version = "4.0.0-rc.2";
|
|
22381
22508
|
/**
|
|
22382
22509
|
* Flag indicating the library has been loaded and is ready to use.
|
|
22383
22510
|
* For UMD builds: `window.SignalWire.ready`
|
|
@@ -22399,7 +22526,7 @@ const ready = true;
|
|
|
22399
22526
|
*/
|
|
22400
22527
|
const emitReadyEvent = () => {
|
|
22401
22528
|
if (typeof window !== "undefined") {
|
|
22402
|
-
const event = new CustomEvent("signalwire:js:ready", { detail: { version: "4.0.0-rc.
|
|
22529
|
+
const event = new CustomEvent("signalwire:js:ready", { detail: { version: "4.0.0-rc.2" } });
|
|
22403
22530
|
window.dispatchEvent(event);
|
|
22404
22531
|
}
|
|
22405
22532
|
};
|
|
@@ -22423,5 +22550,5 @@ emitReadyEvent();
|
|
|
22423
22550
|
if (typeof process === "undefined") globalThis.process = { env: { NODE_ENV: "production" } };
|
|
22424
22551
|
|
|
22425
22552
|
//#endregion
|
|
22426
|
-
export { Address, CallCreateError, ClientPreferences, CollectionFetchError, DPoPInitError, DeviceTokenError, EmbedTokenCredentialProvider, InvalidCredentialsError, MediaTrackError, MessageParseError, OverconstrainedFallbackError, Participant, PreflightError, RecoveryError, SelfCapabilities, SelfParticipant, SignalWire, StaticCredentialProvider, TokenRefreshError, UnexpectedError, User, VertoPongError, WebRTCCall, embeddableCall, getLogger, isSelfParticipant, ready, setDebugOptions, setLogLevel, setLogger, version };
|
|
22553
|
+
export { Address, CallCreateError, ClientPreferences, CollectionFetchError, DPoPInitError, DeviceTokenError, EmbedTokenCredentialProvider, InvalidCredentialsError, MediaAccessError, MediaTrackError, MessageParseError, OverconstrainedFallbackError, Participant, PreflightError, RecoveryError, SelfCapabilities, SelfParticipant, SignalWire, StaticCredentialProvider, TokenRefreshError, UnexpectedError, User, VertoPongError, WebRTCCall, embeddableCall, getLogger, isSelfParticipant, ready, setDebugOptions, setLogLevel, setLogger, version };
|
|
22427
22554
|
//# sourceMappingURL=browser.mjs.map
|