mediasoup-client 3.7.0 → 3.7.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/README.md +85 -112
- package/lib/Consumer.d.ts +1 -1
- package/lib/Consumer.d.ts.map +1 -1
- package/lib/Consumer.js +1 -1
- package/lib/DataConsumer.d.ts +1 -1
- package/lib/DataConsumer.d.ts.map +1 -1
- package/lib/DataConsumer.js +1 -1
- package/lib/DataProducer.d.ts +1 -1
- package/lib/DataProducer.d.ts.map +1 -1
- package/lib/DataProducer.js +1 -1
- package/lib/Device.d.ts +3 -3
- package/lib/Device.d.ts.map +1 -1
- package/lib/Device.js +43 -42
- package/lib/EnhancedEventEmitter.d.ts.map +1 -1
- package/lib/Logger.d.ts.map +1 -1
- package/lib/Producer.d.ts +5 -15
- package/lib/Producer.d.ts.map +1 -1
- package/lib/Producer.js +2 -2
- package/lib/RtpParameters.d.ts.map +1 -1
- package/lib/SctpParameters.d.ts.map +1 -1
- package/lib/Transport.d.ts +14 -10
- package/lib/Transport.d.ts.map +1 -1
- package/lib/Transport.js +71 -53
- package/lib/errors.d.ts.map +1 -1
- package/lib/errors.js +6 -6
- package/lib/handlers/Chrome111.d.ts +4 -4
- package/lib/handlers/Chrome111.d.ts.map +1 -1
- package/lib/handlers/Chrome111.js +64 -57
- package/lib/handlers/Chrome55.d.ts +4 -4
- package/lib/handlers/Chrome55.d.ts.map +1 -1
- package/lib/handlers/Chrome55.js +75 -62
- package/lib/handlers/Chrome67.d.ts +4 -4
- package/lib/handlers/Chrome67.d.ts.map +1 -1
- package/lib/handlers/Chrome67.js +77 -65
- package/lib/handlers/Chrome70.d.ts +4 -4
- package/lib/handlers/Chrome70.d.ts.map +1 -1
- package/lib/handlers/Chrome70.js +68 -60
- package/lib/handlers/Chrome74.d.ts +4 -4
- package/lib/handlers/Chrome74.d.ts.map +1 -1
- package/lib/handlers/Chrome74.js +65 -58
- package/lib/handlers/Edge11.d.ts +1 -1
- package/lib/handlers/Edge11.d.ts.map +1 -1
- package/lib/handlers/Edge11.js +43 -37
- package/lib/handlers/FakeHandler.d.ts +3 -3
- package/lib/handlers/FakeHandler.d.ts.map +1 -1
- package/lib/handlers/FakeHandler.js +19 -22
- package/lib/handlers/Firefox60.d.ts +4 -4
- package/lib/handlers/Firefox60.d.ts.map +1 -1
- package/lib/handlers/Firefox60.js +65 -52
- package/lib/handlers/HandlerInterface.d.ts.map +1 -1
- package/lib/handlers/ReactNative.d.ts +4 -4
- package/lib/handlers/ReactNative.d.ts.map +1 -1
- package/lib/handlers/ReactNative.js +76 -64
- package/lib/handlers/ReactNativeUnifiedPlan.d.ts +4 -4
- package/lib/handlers/ReactNativeUnifiedPlan.d.ts.map +1 -1
- package/lib/handlers/ReactNativeUnifiedPlan.js +65 -58
- package/lib/handlers/Safari11.d.ts +4 -4
- package/lib/handlers/Safari11.d.ts.map +1 -1
- package/lib/handlers/Safari11.js +74 -61
- package/lib/handlers/Safari12.d.ts +4 -4
- package/lib/handlers/Safari12.d.ts.map +1 -1
- package/lib/handlers/Safari12.js +65 -57
- package/lib/handlers/ortc/edgeUtils.d.ts.map +1 -1
- package/lib/handlers/ortc/utils.d.ts.map +1 -1
- package/lib/handlers/ortc/utils.js +2 -2
- package/lib/handlers/sdp/MediaSection.d.ts +5 -5
- package/lib/handlers/sdp/MediaSection.d.ts.map +1 -1
- package/lib/handlers/sdp/MediaSection.js +287 -305
- package/lib/handlers/sdp/RemoteSdp.d.ts +5 -5
- package/lib/handlers/sdp/RemoteSdp.d.ts.map +1 -1
- package/lib/handlers/sdp/RemoteSdp.js +28 -30
- package/lib/handlers/sdp/commonUtils.d.ts +4 -4
- package/lib/handlers/sdp/commonUtils.d.ts.map +1 -1
- package/lib/handlers/sdp/commonUtils.js +41 -46
- package/lib/handlers/sdp/plainRtpUtils.d.ts +2 -2
- package/lib/handlers/sdp/plainRtpUtils.d.ts.map +1 -1
- package/lib/handlers/sdp/plainRtpUtils.js +5 -7
- package/lib/handlers/sdp/planBUtils.d.ts +2 -2
- package/lib/handlers/sdp/planBUtils.d.ts.map +1 -1
- package/lib/handlers/sdp/planBUtils.js +11 -14
- package/lib/handlers/sdp/unifiedPlanUtils.d.ts +2 -2
- package/lib/handlers/sdp/unifiedPlanUtils.d.ts.map +1 -1
- package/lib/handlers/sdp/unifiedPlanUtils.js +11 -14
- package/lib/index.d.ts +1 -1
- package/lib/index.js +1 -1
- package/lib/ortc.d.ts.map +1 -1
- package/lib/ortc.js +90 -92
- package/lib/scalabilityModes.d.ts.map +1 -1
- package/lib/scalabilityModes.js +2 -2
- package/lib/{tests → test}/fakeParameters.d.ts +2 -2
- package/lib/test/fakeParameters.d.ts.map +1 -0
- package/lib/test/fakeParameters.js +645 -0
- package/lib/{tests → test}/test.d.ts.map +1 -1
- package/lib/{tests → test}/test.js +466 -495
- package/lib/test/uaTestCases.d.ts.map +1 -0
- package/lib/{tests → test}/uaTestCases.js +17 -17
- package/lib/types.d.ts.map +1 -1
- package/lib/utils.d.ts.map +1 -1
- package/npm-scripts.mjs +72 -98
- package/package.json +93 -90
- package/lib/tests/fakeParameters.d.ts.map +0 -1
- package/lib/tests/fakeParameters.js +0 -662
- package/lib/tests/uaTestCases.d.ts.map +0 -1
- /package/lib/{tests → test}/test.d.ts +0 -0
- /package/lib/{tests → test}/uaTestCases.d.ts +0 -0
|
@@ -27,7 +27,7 @@ exports.OfferMediaSection = exports.AnswerMediaSection = exports.MediaSection =
|
|
|
27
27
|
const sdpTransform = __importStar(require("sdp-transform"));
|
|
28
28
|
const utils = __importStar(require("../../utils"));
|
|
29
29
|
class MediaSection {
|
|
30
|
-
constructor({ iceParameters, iceCandidates, dtlsParameters, planB = false }) {
|
|
30
|
+
constructor({ iceParameters, iceCandidates, dtlsParameters, planB = false, }) {
|
|
31
31
|
this._mediaObject = {};
|
|
32
32
|
this._planB = planB;
|
|
33
33
|
if (iceParameters) {
|
|
@@ -91,7 +91,7 @@ class MediaSection {
|
|
|
91
91
|
}
|
|
92
92
|
exports.MediaSection = MediaSection;
|
|
93
93
|
class AnswerMediaSection extends MediaSection {
|
|
94
|
-
constructor({ iceParameters, iceCandidates, dtlsParameters, sctpParameters, plainRtpParameters, planB = false, offerMediaObject, offerRtpParameters, answerRtpParameters, codecOptions, extmapAllowMixed = false }) {
|
|
94
|
+
constructor({ iceParameters, iceCandidates, dtlsParameters, sctpParameters, plainRtpParameters, planB = false, offerMediaObject, offerRtpParameters, answerRtpParameters, codecOptions, extmapAllowMixed = false, }) {
|
|
95
95
|
super({ iceParameters, iceCandidates, dtlsParameters, planB });
|
|
96
96
|
this._mediaObject.mid = String(offerMediaObject.mid);
|
|
97
97
|
this._mediaObject.type = offerMediaObject.type;
|
|
@@ -101,211 +101,204 @@ class AnswerMediaSection extends MediaSection {
|
|
|
101
101
|
this._mediaObject.port = 7;
|
|
102
102
|
}
|
|
103
103
|
else {
|
|
104
|
-
this._mediaObject.connection =
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
};
|
|
104
|
+
this._mediaObject.connection = {
|
|
105
|
+
ip: plainRtpParameters.ip,
|
|
106
|
+
version: plainRtpParameters.ipVersion,
|
|
107
|
+
};
|
|
109
108
|
this._mediaObject.port = plainRtpParameters.port;
|
|
110
109
|
}
|
|
111
110
|
switch (offerMediaObject.type) {
|
|
112
111
|
case 'audio':
|
|
113
|
-
case 'video':
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
.rtcpFeedback
|
|
167
|
-
.filter((fb) => fb.type !== 'nack' || fb.parameter);
|
|
168
|
-
codecRtcpFeedback = codecRtcpFeedback
|
|
169
|
-
.filter((fb) => fb.type !== 'nack' || fb.parameter);
|
|
170
|
-
}
|
|
171
|
-
break;
|
|
172
|
-
}
|
|
173
|
-
case 'video/vp8':
|
|
174
|
-
case 'video/vp9':
|
|
175
|
-
case 'video/h264':
|
|
176
|
-
case 'video/h265':
|
|
177
|
-
{
|
|
178
|
-
if (videoGoogleStartBitrate !== undefined) {
|
|
179
|
-
codecParameters['x-google-start-bitrate'] = videoGoogleStartBitrate;
|
|
180
|
-
}
|
|
181
|
-
if (videoGoogleMaxBitrate !== undefined) {
|
|
182
|
-
codecParameters['x-google-max-bitrate'] = videoGoogleMaxBitrate;
|
|
183
|
-
}
|
|
184
|
-
if (videoGoogleMinBitrate !== undefined) {
|
|
185
|
-
codecParameters['x-google-min-bitrate'] = videoGoogleMinBitrate;
|
|
186
|
-
}
|
|
187
|
-
break;
|
|
188
|
-
}
|
|
112
|
+
case 'video': {
|
|
113
|
+
this._mediaObject.direction = 'recvonly';
|
|
114
|
+
this._mediaObject.rtp = [];
|
|
115
|
+
this._mediaObject.rtcpFb = [];
|
|
116
|
+
this._mediaObject.fmtp = [];
|
|
117
|
+
for (const codec of answerRtpParameters.codecs) {
|
|
118
|
+
const rtp = {
|
|
119
|
+
payload: codec.payloadType,
|
|
120
|
+
codec: getCodecName(codec),
|
|
121
|
+
rate: codec.clockRate,
|
|
122
|
+
};
|
|
123
|
+
if (codec.channels > 1) {
|
|
124
|
+
rtp.encoding = codec.channels;
|
|
125
|
+
}
|
|
126
|
+
this._mediaObject.rtp.push(rtp);
|
|
127
|
+
const codecParameters = utils.clone(codec.parameters) ?? {};
|
|
128
|
+
let codecRtcpFeedback = utils.clone(codec.rtcpFeedback) ?? [];
|
|
129
|
+
if (codecOptions) {
|
|
130
|
+
const { opusStereo, opusFec, opusDtx, opusMaxPlaybackRate, opusMaxAverageBitrate, opusPtime, opusNack, videoGoogleStartBitrate, videoGoogleMaxBitrate, videoGoogleMinBitrate, } = codecOptions;
|
|
131
|
+
const offerCodec = offerRtpParameters.codecs.find((c) => c.payloadType === codec.payloadType);
|
|
132
|
+
switch (codec.mimeType.toLowerCase()) {
|
|
133
|
+
case 'audio/opus':
|
|
134
|
+
case 'audio/multiopus': {
|
|
135
|
+
if (opusStereo !== undefined) {
|
|
136
|
+
offerCodec.parameters['sprop-stereo'] = opusStereo ? 1 : 0;
|
|
137
|
+
codecParameters.stereo = opusStereo ? 1 : 0;
|
|
138
|
+
}
|
|
139
|
+
if (opusFec !== undefined) {
|
|
140
|
+
offerCodec.parameters.useinbandfec = opusFec ? 1 : 0;
|
|
141
|
+
codecParameters.useinbandfec = opusFec ? 1 : 0;
|
|
142
|
+
}
|
|
143
|
+
if (opusDtx !== undefined) {
|
|
144
|
+
offerCodec.parameters.usedtx = opusDtx ? 1 : 0;
|
|
145
|
+
codecParameters.usedtx = opusDtx ? 1 : 0;
|
|
146
|
+
}
|
|
147
|
+
if (opusMaxPlaybackRate !== undefined) {
|
|
148
|
+
codecParameters.maxplaybackrate = opusMaxPlaybackRate;
|
|
149
|
+
}
|
|
150
|
+
if (opusMaxAverageBitrate !== undefined) {
|
|
151
|
+
codecParameters.maxaveragebitrate = opusMaxAverageBitrate;
|
|
152
|
+
}
|
|
153
|
+
if (opusPtime !== undefined) {
|
|
154
|
+
offerCodec.parameters.ptime = opusPtime;
|
|
155
|
+
codecParameters.ptime = opusPtime;
|
|
156
|
+
}
|
|
157
|
+
// If opusNack is not set, we must remove NACK support for OPUS.
|
|
158
|
+
// Otherwise it would be enabled for those handlers that artificially
|
|
159
|
+
// announce it in their RTP capabilities.
|
|
160
|
+
if (!opusNack) {
|
|
161
|
+
offerCodec.rtcpFeedback = offerCodec.rtcpFeedback.filter(fb => fb.type !== 'nack' || fb.parameter);
|
|
162
|
+
codecRtcpFeedback = codecRtcpFeedback.filter(fb => fb.type !== 'nack' || fb.parameter);
|
|
163
|
+
}
|
|
164
|
+
break;
|
|
189
165
|
}
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
166
|
+
case 'video/vp8':
|
|
167
|
+
case 'video/vp9':
|
|
168
|
+
case 'video/h264':
|
|
169
|
+
case 'video/h265': {
|
|
170
|
+
if (videoGoogleStartBitrate !== undefined) {
|
|
171
|
+
codecParameters['x-google-start-bitrate'] =
|
|
172
|
+
videoGoogleStartBitrate;
|
|
173
|
+
}
|
|
174
|
+
if (videoGoogleMaxBitrate !== undefined) {
|
|
175
|
+
codecParameters['x-google-max-bitrate'] =
|
|
176
|
+
videoGoogleMaxBitrate;
|
|
177
|
+
}
|
|
178
|
+
if (videoGoogleMinBitrate !== undefined) {
|
|
179
|
+
codecParameters['x-google-min-bitrate'] =
|
|
180
|
+
videoGoogleMinBitrate;
|
|
181
|
+
}
|
|
182
|
+
break;
|
|
198
183
|
}
|
|
199
|
-
fmtp.config += `${key}=${codecParameters[key]}`;
|
|
200
184
|
}
|
|
185
|
+
}
|
|
186
|
+
const fmtp = {
|
|
187
|
+
payload: codec.payloadType,
|
|
188
|
+
config: '',
|
|
189
|
+
};
|
|
190
|
+
for (const key of Object.keys(codecParameters)) {
|
|
201
191
|
if (fmtp.config) {
|
|
202
|
-
|
|
203
|
-
}
|
|
204
|
-
for (const fb of codecRtcpFeedback) {
|
|
205
|
-
this._mediaObject.rtcpFb.push({
|
|
206
|
-
payload: codec.payloadType,
|
|
207
|
-
type: fb.type,
|
|
208
|
-
subtype: fb.parameter
|
|
209
|
-
});
|
|
192
|
+
fmtp.config += ';';
|
|
210
193
|
}
|
|
194
|
+
fmtp.config += `${key}=${codecParameters[key]}`;
|
|
211
195
|
}
|
|
212
|
-
|
|
213
|
-
.
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
if (!found) {
|
|
221
|
-
continue;
|
|
222
|
-
}
|
|
223
|
-
this._mediaObject.ext.push({
|
|
224
|
-
uri: ext.uri,
|
|
225
|
-
value: ext.id
|
|
196
|
+
if (fmtp.config) {
|
|
197
|
+
this._mediaObject.fmtp.push(fmtp);
|
|
198
|
+
}
|
|
199
|
+
for (const fb of codecRtcpFeedback) {
|
|
200
|
+
this._mediaObject.rtcpFb.push({
|
|
201
|
+
payload: codec.payloadType,
|
|
202
|
+
type: fb.type,
|
|
203
|
+
subtype: fb.parameter,
|
|
226
204
|
});
|
|
227
205
|
}
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
206
|
+
}
|
|
207
|
+
this._mediaObject.payloads = answerRtpParameters.codecs
|
|
208
|
+
.map((codec) => codec.payloadType)
|
|
209
|
+
.join(' ');
|
|
210
|
+
this._mediaObject.ext = [];
|
|
211
|
+
for (const ext of answerRtpParameters.headerExtensions) {
|
|
212
|
+
// Don't add a header extension if not present in the offer.
|
|
213
|
+
const found = (offerMediaObject.ext || []).some((localExt) => localExt.uri === ext.uri);
|
|
214
|
+
if (!found) {
|
|
215
|
+
continue;
|
|
232
216
|
}
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
217
|
+
this._mediaObject.ext.push({
|
|
218
|
+
uri: ext.uri,
|
|
219
|
+
value: ext.id,
|
|
220
|
+
});
|
|
221
|
+
}
|
|
222
|
+
// Allow both 1 byte and 2 bytes length header extensions.
|
|
223
|
+
if (extmapAllowMixed &&
|
|
224
|
+
offerMediaObject.extmapAllowMixed === 'extmap-allow-mixed') {
|
|
225
|
+
this._mediaObject.extmapAllowMixed = 'extmap-allow-mixed';
|
|
226
|
+
}
|
|
227
|
+
// Simulcast.
|
|
228
|
+
if (offerMediaObject.simulcast) {
|
|
229
|
+
this._mediaObject.simulcast = {
|
|
230
|
+
dir1: 'recv',
|
|
231
|
+
list1: offerMediaObject.simulcast.list1,
|
|
232
|
+
};
|
|
233
|
+
this._mediaObject.rids = [];
|
|
234
|
+
for (const rid of offerMediaObject.rids || []) {
|
|
235
|
+
if (rid.direction !== 'send') {
|
|
236
|
+
continue;
|
|
249
237
|
}
|
|
238
|
+
this._mediaObject.rids.push({
|
|
239
|
+
id: rid.id,
|
|
240
|
+
direction: 'recv',
|
|
241
|
+
});
|
|
250
242
|
}
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
}
|
|
263
|
-
this._mediaObject.rids.push({
|
|
264
|
-
id: rid.id,
|
|
265
|
-
direction: 'recv'
|
|
266
|
-
});
|
|
243
|
+
}
|
|
244
|
+
// Simulcast (draft version 03).
|
|
245
|
+
else if (offerMediaObject.simulcast_03) {
|
|
246
|
+
// eslint-disable-next-line camelcase
|
|
247
|
+
this._mediaObject.simulcast_03 = {
|
|
248
|
+
value: offerMediaObject.simulcast_03.value.replace(/send/g, 'recv'),
|
|
249
|
+
};
|
|
250
|
+
this._mediaObject.rids = [];
|
|
251
|
+
for (const rid of offerMediaObject.rids || []) {
|
|
252
|
+
if (rid.direction !== 'send') {
|
|
253
|
+
continue;
|
|
267
254
|
}
|
|
255
|
+
this._mediaObject.rids.push({
|
|
256
|
+
id: rid.id,
|
|
257
|
+
direction: 'recv',
|
|
258
|
+
});
|
|
268
259
|
}
|
|
269
|
-
this._mediaObject.rtcpMux = 'rtcp-mux';
|
|
270
|
-
this._mediaObject.rtcpRsize = 'rtcp-rsize';
|
|
271
|
-
if (this._planB && this._mediaObject.type === 'video') {
|
|
272
|
-
this._mediaObject.xGoogleFlag = 'conference';
|
|
273
|
-
}
|
|
274
|
-
break;
|
|
275
260
|
}
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
this._mediaObject.payloads = 'webrtc-datachannel';
|
|
281
|
-
this._mediaObject.sctpPort = sctpParameters.port;
|
|
282
|
-
this._mediaObject.maxMessageSize = sctpParameters.maxMessageSize;
|
|
283
|
-
}
|
|
284
|
-
// Old spec.
|
|
285
|
-
else if (offerMediaObject.sctpmap) {
|
|
286
|
-
this._mediaObject.payloads = sctpParameters.port;
|
|
287
|
-
this._mediaObject.sctpmap =
|
|
288
|
-
{
|
|
289
|
-
app: 'webrtc-datachannel',
|
|
290
|
-
sctpmapNumber: sctpParameters.port,
|
|
291
|
-
maxMessageSize: sctpParameters.maxMessageSize
|
|
292
|
-
};
|
|
293
|
-
}
|
|
294
|
-
break;
|
|
261
|
+
this._mediaObject.rtcpMux = 'rtcp-mux';
|
|
262
|
+
this._mediaObject.rtcpRsize = 'rtcp-rsize';
|
|
263
|
+
if (this._planB && this._mediaObject.type === 'video') {
|
|
264
|
+
this._mediaObject.xGoogleFlag = 'conference';
|
|
295
265
|
}
|
|
266
|
+
break;
|
|
267
|
+
}
|
|
268
|
+
case 'application': {
|
|
269
|
+
// New spec.
|
|
270
|
+
if (typeof offerMediaObject.sctpPort === 'number') {
|
|
271
|
+
this._mediaObject.payloads = 'webrtc-datachannel';
|
|
272
|
+
this._mediaObject.sctpPort = sctpParameters.port;
|
|
273
|
+
this._mediaObject.maxMessageSize = sctpParameters.maxMessageSize;
|
|
274
|
+
}
|
|
275
|
+
// Old spec.
|
|
276
|
+
else if (offerMediaObject.sctpmap) {
|
|
277
|
+
this._mediaObject.payloads = sctpParameters.port;
|
|
278
|
+
this._mediaObject.sctpmap = {
|
|
279
|
+
app: 'webrtc-datachannel',
|
|
280
|
+
sctpmapNumber: sctpParameters.port,
|
|
281
|
+
maxMessageSize: sctpParameters.maxMessageSize,
|
|
282
|
+
};
|
|
283
|
+
}
|
|
284
|
+
break;
|
|
285
|
+
}
|
|
296
286
|
}
|
|
297
287
|
}
|
|
298
288
|
setDtlsRole(role) {
|
|
299
289
|
switch (role) {
|
|
300
|
-
case 'client':
|
|
290
|
+
case 'client': {
|
|
301
291
|
this._mediaObject.setup = 'active';
|
|
302
292
|
break;
|
|
303
|
-
|
|
293
|
+
}
|
|
294
|
+
case 'server': {
|
|
304
295
|
this._mediaObject.setup = 'passive';
|
|
305
296
|
break;
|
|
306
|
-
|
|
297
|
+
}
|
|
298
|
+
case 'auto': {
|
|
307
299
|
this._mediaObject.setup = 'actpass';
|
|
308
300
|
break;
|
|
301
|
+
}
|
|
309
302
|
}
|
|
310
303
|
}
|
|
311
304
|
resume() {
|
|
@@ -328,12 +321,14 @@ class AnswerMediaSection extends MediaSection {
|
|
|
328
321
|
simulcastFormat.paused = !layers[simulcastFormat.scid]?.active;
|
|
329
322
|
}
|
|
330
323
|
}
|
|
331
|
-
this._mediaObject.simulcast.list1 = simulcastStreams
|
|
324
|
+
this._mediaObject.simulcast.list1 = simulcastStreams
|
|
325
|
+
.map(simulcastFormats => simulcastFormats.map(f => `${f.paused ? '~' : ''}${f.scid}`).join(','))
|
|
326
|
+
.join(';');
|
|
332
327
|
}
|
|
333
328
|
}
|
|
334
329
|
exports.AnswerMediaSection = AnswerMediaSection;
|
|
335
330
|
class OfferMediaSection extends MediaSection {
|
|
336
|
-
constructor({ iceParameters, iceCandidates, dtlsParameters, sctpParameters, plainRtpParameters, planB = false, mid, kind, offerRtpParameters, streamId, trackId, oldDataChannelSpec = false }) {
|
|
331
|
+
constructor({ iceParameters, iceCandidates, dtlsParameters, sctpParameters, plainRtpParameters, planB = false, mid, kind, offerRtpParameters, streamId, trackId, oldDataChannelSpec = false, }) {
|
|
337
332
|
super({ iceParameters, iceCandidates, dtlsParameters, planB });
|
|
338
333
|
this._mediaObject.mid = String(mid);
|
|
339
334
|
this._mediaObject.type = kind;
|
|
@@ -348,132 +343,126 @@ class OfferMediaSection extends MediaSection {
|
|
|
348
343
|
this._mediaObject.port = 7;
|
|
349
344
|
}
|
|
350
345
|
else {
|
|
351
|
-
this._mediaObject.connection =
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
};
|
|
346
|
+
this._mediaObject.connection = {
|
|
347
|
+
ip: plainRtpParameters.ip,
|
|
348
|
+
version: plainRtpParameters.ipVersion,
|
|
349
|
+
};
|
|
356
350
|
this._mediaObject.protocol = 'RTP/AVP';
|
|
357
351
|
this._mediaObject.port = plainRtpParameters.port;
|
|
358
352
|
}
|
|
359
353
|
switch (kind) {
|
|
360
354
|
case 'audio':
|
|
361
|
-
case 'video':
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
355
|
+
case 'video': {
|
|
356
|
+
this._mediaObject.direction = 'sendonly';
|
|
357
|
+
this._mediaObject.rtp = [];
|
|
358
|
+
this._mediaObject.rtcpFb = [];
|
|
359
|
+
this._mediaObject.fmtp = [];
|
|
360
|
+
if (!this._planB) {
|
|
361
|
+
this._mediaObject.msid = `${streamId || '-'} ${trackId}`;
|
|
362
|
+
}
|
|
363
|
+
for (const codec of offerRtpParameters.codecs) {
|
|
364
|
+
const rtp = {
|
|
365
|
+
payload: codec.payloadType,
|
|
366
|
+
codec: getCodecName(codec),
|
|
367
|
+
rate: codec.clockRate,
|
|
368
|
+
};
|
|
369
|
+
if (codec.channels > 1) {
|
|
370
|
+
rtp.encoding = codec.channels;
|
|
369
371
|
}
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
if (codec.channels > 1) {
|
|
377
|
-
rtp.encoding = codec.channels;
|
|
378
|
-
}
|
|
379
|
-
this._mediaObject.rtp.push(rtp);
|
|
380
|
-
const fmtp = {
|
|
381
|
-
payload: codec.payloadType,
|
|
382
|
-
config: ''
|
|
383
|
-
};
|
|
384
|
-
for (const key of Object.keys(codec.parameters)) {
|
|
385
|
-
if (fmtp.config) {
|
|
386
|
-
fmtp.config += ';';
|
|
387
|
-
}
|
|
388
|
-
fmtp.config += `${key}=${codec.parameters[key]}`;
|
|
389
|
-
}
|
|
372
|
+
this._mediaObject.rtp.push(rtp);
|
|
373
|
+
const fmtp = {
|
|
374
|
+
payload: codec.payloadType,
|
|
375
|
+
config: '',
|
|
376
|
+
};
|
|
377
|
+
for (const key of Object.keys(codec.parameters)) {
|
|
390
378
|
if (fmtp.config) {
|
|
391
|
-
|
|
392
|
-
}
|
|
393
|
-
for (const fb of codec.rtcpFeedback) {
|
|
394
|
-
this._mediaObject.rtcpFb.push({
|
|
395
|
-
payload: codec.payloadType,
|
|
396
|
-
type: fb.type,
|
|
397
|
-
subtype: fb.parameter
|
|
398
|
-
});
|
|
379
|
+
fmtp.config += ';';
|
|
399
380
|
}
|
|
381
|
+
fmtp.config += `${key}=${codec.parameters[key]}`;
|
|
400
382
|
}
|
|
401
|
-
|
|
402
|
-
.
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
383
|
+
if (fmtp.config) {
|
|
384
|
+
this._mediaObject.fmtp.push(fmtp);
|
|
385
|
+
}
|
|
386
|
+
for (const fb of codec.rtcpFeedback) {
|
|
387
|
+
this._mediaObject.rtcpFb.push({
|
|
388
|
+
payload: codec.payloadType,
|
|
389
|
+
type: fb.type,
|
|
390
|
+
subtype: fb.parameter,
|
|
409
391
|
});
|
|
410
392
|
}
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
393
|
+
}
|
|
394
|
+
this._mediaObject.payloads = offerRtpParameters.codecs
|
|
395
|
+
.map((codec) => codec.payloadType)
|
|
396
|
+
.join(' ');
|
|
397
|
+
this._mediaObject.ext = [];
|
|
398
|
+
for (const ext of offerRtpParameters.headerExtensions) {
|
|
399
|
+
this._mediaObject.ext.push({
|
|
400
|
+
uri: ext.uri,
|
|
401
|
+
value: ext.id,
|
|
402
|
+
});
|
|
403
|
+
}
|
|
404
|
+
this._mediaObject.rtcpMux = 'rtcp-mux';
|
|
405
|
+
this._mediaObject.rtcpRsize = 'rtcp-rsize';
|
|
406
|
+
const encoding = offerRtpParameters.encodings[0];
|
|
407
|
+
const ssrc = encoding.ssrc;
|
|
408
|
+
const rtxSsrc = encoding.rtx && encoding.rtx.ssrc ? encoding.rtx.ssrc : undefined;
|
|
409
|
+
this._mediaObject.ssrcs = [];
|
|
410
|
+
this._mediaObject.ssrcGroups = [];
|
|
411
|
+
if (offerRtpParameters.rtcp.cname) {
|
|
412
|
+
this._mediaObject.ssrcs.push({
|
|
413
|
+
id: ssrc,
|
|
414
|
+
attribute: 'cname',
|
|
415
|
+
value: offerRtpParameters.rtcp.cname,
|
|
416
|
+
});
|
|
417
|
+
}
|
|
418
|
+
if (this._planB) {
|
|
419
|
+
this._mediaObject.ssrcs.push({
|
|
420
|
+
id: ssrc,
|
|
421
|
+
attribute: 'msid',
|
|
422
|
+
value: `${streamId || '-'} ${trackId}`,
|
|
423
|
+
});
|
|
424
|
+
}
|
|
425
|
+
if (rtxSsrc) {
|
|
420
426
|
if (offerRtpParameters.rtcp.cname) {
|
|
421
427
|
this._mediaObject.ssrcs.push({
|
|
422
|
-
id:
|
|
428
|
+
id: rtxSsrc,
|
|
423
429
|
attribute: 'cname',
|
|
424
|
-
value: offerRtpParameters.rtcp.cname
|
|
430
|
+
value: offerRtpParameters.rtcp.cname,
|
|
425
431
|
});
|
|
426
432
|
}
|
|
427
433
|
if (this._planB) {
|
|
428
434
|
this._mediaObject.ssrcs.push({
|
|
429
|
-
id:
|
|
435
|
+
id: rtxSsrc,
|
|
430
436
|
attribute: 'msid',
|
|
431
|
-
value: `${streamId || '-'} ${trackId}
|
|
432
|
-
});
|
|
433
|
-
}
|
|
434
|
-
if (rtxSsrc) {
|
|
435
|
-
if (offerRtpParameters.rtcp.cname) {
|
|
436
|
-
this._mediaObject.ssrcs.push({
|
|
437
|
-
id: rtxSsrc,
|
|
438
|
-
attribute: 'cname',
|
|
439
|
-
value: offerRtpParameters.rtcp.cname
|
|
440
|
-
});
|
|
441
|
-
}
|
|
442
|
-
if (this._planB) {
|
|
443
|
-
this._mediaObject.ssrcs.push({
|
|
444
|
-
id: rtxSsrc,
|
|
445
|
-
attribute: 'msid',
|
|
446
|
-
value: `${streamId || '-'} ${trackId}`
|
|
447
|
-
});
|
|
448
|
-
}
|
|
449
|
-
// Associate original and retransmission SSRCs.
|
|
450
|
-
this._mediaObject.ssrcGroups.push({
|
|
451
|
-
semantics: 'FID',
|
|
452
|
-
ssrcs: `${ssrc} ${rtxSsrc}`
|
|
437
|
+
value: `${streamId || '-'} ${trackId}`,
|
|
453
438
|
});
|
|
454
439
|
}
|
|
455
|
-
|
|
440
|
+
// Associate original and retransmission SSRCs.
|
|
441
|
+
this._mediaObject.ssrcGroups.push({
|
|
442
|
+
semantics: 'FID',
|
|
443
|
+
ssrcs: `${ssrc} ${rtxSsrc}`,
|
|
444
|
+
});
|
|
456
445
|
}
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
// Old spec.
|
|
466
|
-
else {
|
|
467
|
-
this._mediaObject.payloads = sctpParameters.port;
|
|
468
|
-
this._mediaObject.sctpmap =
|
|
469
|
-
{
|
|
470
|
-
app: 'webrtc-datachannel',
|
|
471
|
-
sctpmapNumber: sctpParameters.port,
|
|
472
|
-
maxMessageSize: sctpParameters.maxMessageSize
|
|
473
|
-
};
|
|
474
|
-
}
|
|
475
|
-
break;
|
|
446
|
+
break;
|
|
447
|
+
}
|
|
448
|
+
case 'application': {
|
|
449
|
+
// New spec.
|
|
450
|
+
if (!oldDataChannelSpec) {
|
|
451
|
+
this._mediaObject.payloads = 'webrtc-datachannel';
|
|
452
|
+
this._mediaObject.sctpPort = sctpParameters.port;
|
|
453
|
+
this._mediaObject.maxMessageSize = sctpParameters.maxMessageSize;
|
|
476
454
|
}
|
|
455
|
+
// Old spec.
|
|
456
|
+
else {
|
|
457
|
+
this._mediaObject.payloads = sctpParameters.port;
|
|
458
|
+
this._mediaObject.sctpmap = {
|
|
459
|
+
app: 'webrtc-datachannel',
|
|
460
|
+
sctpmapNumber: sctpParameters.port,
|
|
461
|
+
maxMessageSize: sctpParameters.maxMessageSize,
|
|
462
|
+
};
|
|
463
|
+
}
|
|
464
|
+
break;
|
|
465
|
+
}
|
|
477
466
|
}
|
|
478
467
|
}
|
|
479
468
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
@@ -484,12 +473,10 @@ class OfferMediaSection extends MediaSection {
|
|
|
484
473
|
resume() {
|
|
485
474
|
this._mediaObject.direction = 'sendonly';
|
|
486
475
|
}
|
|
487
|
-
planBReceive({ offerRtpParameters, streamId, trackId }) {
|
|
476
|
+
planBReceive({ offerRtpParameters, streamId, trackId, }) {
|
|
488
477
|
const encoding = offerRtpParameters.encodings[0];
|
|
489
478
|
const ssrc = encoding.ssrc;
|
|
490
|
-
const rtxSsrc =
|
|
491
|
-
? encoding.rtx.ssrc
|
|
492
|
-
: undefined;
|
|
479
|
+
const rtxSsrc = encoding.rtx && encoding.rtx.ssrc ? encoding.rtx.ssrc : undefined;
|
|
493
480
|
const payloads = this._mediaObject.payloads.split(' ');
|
|
494
481
|
for (const codec of offerRtpParameters.codecs) {
|
|
495
482
|
if (payloads.includes(String(codec.payloadType))) {
|
|
@@ -498,7 +485,7 @@ class OfferMediaSection extends MediaSection {
|
|
|
498
485
|
const rtp = {
|
|
499
486
|
payload: codec.payloadType,
|
|
500
487
|
codec: getCodecName(codec),
|
|
501
|
-
rate: codec.clockRate
|
|
488
|
+
rate: codec.clockRate,
|
|
502
489
|
};
|
|
503
490
|
if (codec.channels > 1) {
|
|
504
491
|
rtp.encoding = codec.channels;
|
|
@@ -506,7 +493,7 @@ class OfferMediaSection extends MediaSection {
|
|
|
506
493
|
this._mediaObject.rtp.push(rtp);
|
|
507
494
|
const fmtp = {
|
|
508
495
|
payload: codec.payloadType,
|
|
509
|
-
config: ''
|
|
496
|
+
config: '',
|
|
510
497
|
};
|
|
511
498
|
for (const key of Object.keys(codec.parameters)) {
|
|
512
499
|
if (fmtp.config) {
|
|
@@ -521,12 +508,11 @@ class OfferMediaSection extends MediaSection {
|
|
|
521
508
|
this._mediaObject.rtcpFb.push({
|
|
522
509
|
payload: codec.payloadType,
|
|
523
510
|
type: fb.type,
|
|
524
|
-
subtype: fb.parameter
|
|
511
|
+
subtype: fb.parameter,
|
|
525
512
|
});
|
|
526
513
|
}
|
|
527
514
|
}
|
|
528
|
-
this._mediaObject.payloads += ` ${offerRtpParameters
|
|
529
|
-
.codecs
|
|
515
|
+
this._mediaObject.payloads += ` ${offerRtpParameters.codecs
|
|
530
516
|
.filter((codec) => !this._mediaObject.payloads.includes(codec.payloadType))
|
|
531
517
|
.map((codec) => codec.payloadType)
|
|
532
518
|
.join(' ')}`;
|
|
@@ -535,45 +521,41 @@ class OfferMediaSection extends MediaSection {
|
|
|
535
521
|
this._mediaObject.ssrcs.push({
|
|
536
522
|
id: ssrc,
|
|
537
523
|
attribute: 'cname',
|
|
538
|
-
value: offerRtpParameters.rtcp.cname
|
|
524
|
+
value: offerRtpParameters.rtcp.cname,
|
|
539
525
|
});
|
|
540
526
|
}
|
|
541
527
|
this._mediaObject.ssrcs.push({
|
|
542
528
|
id: ssrc,
|
|
543
529
|
attribute: 'msid',
|
|
544
|
-
value: `${streamId || '-'} ${trackId}
|
|
530
|
+
value: `${streamId || '-'} ${trackId}`,
|
|
545
531
|
});
|
|
546
532
|
if (rtxSsrc) {
|
|
547
533
|
if (offerRtpParameters.rtcp.cname) {
|
|
548
534
|
this._mediaObject.ssrcs.push({
|
|
549
535
|
id: rtxSsrc,
|
|
550
536
|
attribute: 'cname',
|
|
551
|
-
value: offerRtpParameters.rtcp.cname
|
|
537
|
+
value: offerRtpParameters.rtcp.cname,
|
|
552
538
|
});
|
|
553
539
|
}
|
|
554
540
|
this._mediaObject.ssrcs.push({
|
|
555
541
|
id: rtxSsrc,
|
|
556
542
|
attribute: 'msid',
|
|
557
|
-
value: `${streamId || '-'} ${trackId}
|
|
543
|
+
value: `${streamId || '-'} ${trackId}`,
|
|
558
544
|
});
|
|
559
545
|
// Associate original and retransmission SSRCs.
|
|
560
546
|
this._mediaObject.ssrcGroups.push({
|
|
561
547
|
semantics: 'FID',
|
|
562
|
-
ssrcs: `${ssrc} ${rtxSsrc}
|
|
548
|
+
ssrcs: `${ssrc} ${rtxSsrc}`,
|
|
563
549
|
});
|
|
564
550
|
}
|
|
565
551
|
}
|
|
566
|
-
planBStopReceiving({ offerRtpParameters }) {
|
|
552
|
+
planBStopReceiving({ offerRtpParameters, }) {
|
|
567
553
|
const encoding = offerRtpParameters.encodings[0];
|
|
568
554
|
const ssrc = encoding.ssrc;
|
|
569
|
-
const rtxSsrc =
|
|
570
|
-
|
|
571
|
-
: undefined;
|
|
572
|
-
this._mediaObject.ssrcs = this._mediaObject.ssrcs
|
|
573
|
-
.filter((s) => s.id !== ssrc && s.id !== rtxSsrc);
|
|
555
|
+
const rtxSsrc = encoding.rtx && encoding.rtx.ssrc ? encoding.rtx.ssrc : undefined;
|
|
556
|
+
this._mediaObject.ssrcs = this._mediaObject.ssrcs.filter((s) => s.id !== ssrc && s.id !== rtxSsrc);
|
|
574
557
|
if (rtxSsrc) {
|
|
575
|
-
this._mediaObject.ssrcGroups = this._mediaObject.ssrcGroups
|
|
576
|
-
.filter((group) => group.ssrcs !== `${ssrc} ${rtxSsrc}`);
|
|
558
|
+
this._mediaObject.ssrcGroups = this._mediaObject.ssrcGroups.filter((group) => group.ssrcs !== `${ssrc} ${rtxSsrc}`);
|
|
577
559
|
}
|
|
578
560
|
}
|
|
579
561
|
}
|