mediasoup-client 3.6.90 → 3.6.92
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/lib/Consumer.d.ts +115 -0
- package/lib/Consumer.d.ts.map +1 -0
- package/lib/Consumer.js +190 -0
- package/lib/DataConsumer.d.ts +93 -0
- package/lib/DataConsumer.d.ts.map +1 -0
- package/lib/DataConsumer.js +162 -0
- package/lib/DataProducer.d.ts +97 -0
- package/lib/DataProducer.d.ts.map +1 -0
- package/lib/DataProducer.js +180 -0
- package/lib/Device.d.ts +92 -0
- package/lib/Device.d.ts.map +1 -0
- package/lib/Device.js +464 -0
- package/lib/EnhancedEventEmitter.d.ts +24 -0
- package/lib/EnhancedEventEmitter.d.ts.map +1 -0
- package/lib/EnhancedEventEmitter.js +70 -0
- package/lib/Logger.d.ts +11 -0
- package/lib/Logger.d.ts.map +1 -0
- package/lib/Logger.js +37 -0
- package/lib/Producer.d.ts +169 -0
- package/lib/Producer.d.ts.map +1 -0
- package/lib/Producer.js +287 -0
- package/lib/RtpParameters.d.ts +306 -0
- package/lib/RtpParameters.d.ts.map +1 -0
- package/lib/RtpParameters.js +6 -0
- package/lib/SctpParameters.d.ts +68 -0
- package/lib/SctpParameters.d.ts.map +1 -0
- package/lib/SctpParameters.js +2 -0
- package/lib/Transport.d.ts +243 -0
- package/lib/Transport.d.ts.map +1 -0
- package/lib/Transport.js +824 -0
- package/lib/errors.d.ts +13 -0
- package/lib/errors.d.ts.map +1 -0
- package/lib/errors.js +39 -0
- package/lib/handlers/Chrome111.d.ts +49 -0
- package/lib/handlers/Chrome111.d.ts.map +1 -0
- package/lib/handlers/Chrome111.js +658 -0
- package/lib/handlers/Chrome55.d.ts +51 -0
- package/lib/handlers/Chrome55.d.ts.map +1 -0
- package/lib/handlers/Chrome55.js +542 -0
- package/lib/handlers/Chrome67.d.ts +51 -0
- package/lib/handlers/Chrome67.d.ts.map +1 -0
- package/lib/handlers/Chrome67.js +598 -0
- package/lib/handlers/Chrome70.d.ts +49 -0
- package/lib/handlers/Chrome70.d.ts.map +1 -0
- package/lib/handlers/Chrome70.js +627 -0
- package/lib/handlers/Chrome74.d.ts +49 -0
- package/lib/handlers/Chrome74.d.ts.map +1 -0
- package/lib/handlers/Chrome74.js +675 -0
- package/lib/handlers/Edge11.d.ts +55 -0
- package/lib/handlers/Edge11.d.ts.map +1 -0
- package/lib/handlers/Edge11.js +447 -0
- package/lib/handlers/FakeHandler.d.ts +49 -0
- package/lib/handlers/FakeHandler.d.ts.map +1 -0
- package/lib/handlers/FakeHandler.js +276 -0
- package/lib/handlers/Firefox60.d.ts +48 -0
- package/lib/handlers/Firefox60.d.ts.map +1 -0
- package/lib/handlers/Firefox60.js +681 -0
- package/lib/handlers/HandlerInterface.d.ts +97 -0
- package/lib/handlers/HandlerInterface.d.ts.map +1 -0
- package/lib/handlers/HandlerInterface.js +10 -0
- package/lib/handlers/ReactNative.d.ts +51 -0
- package/lib/handlers/ReactNative.d.ts.map +1 -0
- package/lib/handlers/ReactNative.js +558 -0
- package/lib/handlers/ReactNativeUnifiedPlan.d.ts +49 -0
- package/lib/handlers/ReactNativeUnifiedPlan.d.ts.map +1 -0
- package/lib/handlers/ReactNativeUnifiedPlan.js +697 -0
- package/lib/handlers/Safari11.d.ts +51 -0
- package/lib/handlers/Safari11.d.ts.map +1 -0
- package/lib/handlers/Safari11.js +592 -0
- package/lib/handlers/Safari12.d.ts +49 -0
- package/lib/handlers/Safari12.d.ts.map +1 -0
- package/lib/handlers/Safari12.js +648 -0
- package/lib/handlers/ortc/edgeUtils.d.ts +11 -0
- package/lib/handlers/ortc/edgeUtils.d.ts.map +1 -0
- package/lib/handlers/ortc/edgeUtils.js +86 -0
- package/lib/handlers/ortc/utils.d.ts +6 -0
- package/lib/handlers/ortc/utils.d.ts.map +1 -0
- package/lib/handlers/ortc/utils.js +20 -0
- package/lib/handlers/sdp/MediaSection.d.ts +68 -0
- package/lib/handlers/sdp/MediaSection.d.ts.map +1 -0
- package/lib/handlers/sdp/MediaSection.js +589 -0
- package/lib/handlers/sdp/RemoteSdp.d.ts +75 -0
- package/lib/handlers/sdp/RemoteSdp.d.ts.map +1 -0
- package/lib/handlers/sdp/RemoteSdp.js +303 -0
- package/lib/handlers/sdp/commonUtils.d.ts +24 -0
- package/lib/handlers/sdp/commonUtils.d.ts.map +1 -0
- package/lib/handlers/sdp/commonUtils.js +224 -0
- package/lib/handlers/sdp/plainRtpUtils.d.ts +14 -0
- package/lib/handlers/sdp/plainRtpUtils.d.ts.map +1 -0
- package/lib/handlers/sdp/plainRtpUtils.js +33 -0
- package/lib/handlers/sdp/planBUtils.d.ts +14 -0
- package/lib/handlers/sdp/planBUtils.d.ts.map +1 -0
- package/lib/handlers/sdp/planBUtils.js +155 -0
- package/lib/handlers/sdp/unifiedPlanUtils.d.ts +12 -0
- package/lib/handlers/sdp/unifiedPlanUtils.d.ts.map +1 -0
- package/lib/handlers/sdp/unifiedPlanUtils.js +131 -0
- package/lib/index.d.ts +14 -1435
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +43 -11884
- package/lib/ortc.d.ts +123 -0
- package/lib/ortc.d.ts.map +1 -0
- package/lib/ortc.js +943 -0
- package/lib/scalabilityModes.d.ts +6 -0
- package/lib/scalabilityModes.d.ts.map +1 -0
- package/lib/scalabilityModes.js +20 -0
- package/lib/tests/fakeParameters.d.ts +20 -0
- package/lib/tests/fakeParameters.d.ts.map +1 -0
- package/lib/tests/fakeParameters.js +659 -0
- package/lib/tests/test.d.ts +6 -0
- package/lib/tests/test.d.ts.map +1 -0
- package/lib/tests/test.js +1297 -0
- package/lib/tests/uaTestCases.d.ts +9 -0
- package/lib/tests/uaTestCases.d.ts.map +1 -0
- package/lib/tests/uaTestCases.js +85 -0
- package/lib/types.d.ts +15 -0
- package/lib/types.d.ts.map +1 -0
- package/lib/types.js +26 -0
- package/lib/utils.d.ts +9 -0
- package/lib/utils.d.ts.map +1 -0
- package/lib/utils.js +20 -0
- package/npm-scripts.mjs +2 -3
- package/package.json +4 -9
- package/lib/index.js.map +0 -1
- package/lib/index.mjs +0 -11860
- package/lib/index.mjs.map +0 -1
package/lib/Transport.js
ADDED
|
@@ -0,0 +1,824 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || function (mod) {
|
|
19
|
+
if (mod && mod.__esModule) return mod;
|
|
20
|
+
var result = {};
|
|
21
|
+
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
|
|
22
|
+
__setModuleDefault(result, mod);
|
|
23
|
+
return result;
|
|
24
|
+
};
|
|
25
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
26
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
27
|
+
};
|
|
28
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
29
|
+
exports.Transport = void 0;
|
|
30
|
+
const awaitqueue_1 = require("awaitqueue");
|
|
31
|
+
const queue_microtask_1 = __importDefault(require("queue-microtask"));
|
|
32
|
+
const Logger_1 = require("./Logger");
|
|
33
|
+
const EnhancedEventEmitter_1 = require("./EnhancedEventEmitter");
|
|
34
|
+
const errors_1 = require("./errors");
|
|
35
|
+
const utils = __importStar(require("./utils"));
|
|
36
|
+
const ortc = __importStar(require("./ortc"));
|
|
37
|
+
const Producer_1 = require("./Producer");
|
|
38
|
+
const Consumer_1 = require("./Consumer");
|
|
39
|
+
const DataProducer_1 = require("./DataProducer");
|
|
40
|
+
const DataConsumer_1 = require("./DataConsumer");
|
|
41
|
+
const logger = new Logger_1.Logger('Transport');
|
|
42
|
+
class ConsumerCreationTask {
|
|
43
|
+
constructor(consumerOptions) {
|
|
44
|
+
this.consumerOptions = consumerOptions;
|
|
45
|
+
this.promise = new Promise((resolve, reject) => {
|
|
46
|
+
this.resolve = resolve;
|
|
47
|
+
this.reject = reject;
|
|
48
|
+
});
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
class Transport extends EnhancedEventEmitter_1.EnhancedEventEmitter {
|
|
52
|
+
constructor({ direction, id, iceParameters, iceCandidates, dtlsParameters, sctpParameters, iceServers, iceTransportPolicy, additionalSettings, proprietaryConstraints, appData, handlerFactory, extendedRtpCapabilities, canProduceByKind }) {
|
|
53
|
+
super();
|
|
54
|
+
// Closed flag.
|
|
55
|
+
this._closed = false;
|
|
56
|
+
// Transport connection state.
|
|
57
|
+
this._connectionState = 'new';
|
|
58
|
+
// Map of Producers indexed by id.
|
|
59
|
+
this._producers = new Map();
|
|
60
|
+
// Map of Consumers indexed by id.
|
|
61
|
+
this._consumers = new Map();
|
|
62
|
+
// Map of DataProducers indexed by id.
|
|
63
|
+
this._dataProducers = new Map();
|
|
64
|
+
// Map of DataConsumers indexed by id.
|
|
65
|
+
this._dataConsumers = new Map();
|
|
66
|
+
// Whether the Consumer for RTP probation has been created.
|
|
67
|
+
this._probatorConsumerCreated = false;
|
|
68
|
+
// AwaitQueue instance to make async tasks happen sequentially.
|
|
69
|
+
this._awaitQueue = new awaitqueue_1.AwaitQueue();
|
|
70
|
+
// Consumer creation tasks awaiting to be processed.
|
|
71
|
+
this._pendingConsumerTasks = [];
|
|
72
|
+
// Consumer creation in progress flag.
|
|
73
|
+
this._consumerCreationInProgress = false;
|
|
74
|
+
// Consumers pending to be paused.
|
|
75
|
+
this._pendingPauseConsumers = new Map();
|
|
76
|
+
// Consumer pause in progress flag.
|
|
77
|
+
this._consumerPauseInProgress = false;
|
|
78
|
+
// Consumers pending to be resumed.
|
|
79
|
+
this._pendingResumeConsumers = new Map();
|
|
80
|
+
// Consumer resume in progress flag.
|
|
81
|
+
this._consumerResumeInProgress = false;
|
|
82
|
+
// Consumers pending to be closed.
|
|
83
|
+
this._pendingCloseConsumers = new Map();
|
|
84
|
+
// Consumer close in progress flag.
|
|
85
|
+
this._consumerCloseInProgress = false;
|
|
86
|
+
// Observer instance.
|
|
87
|
+
this._observer = new EnhancedEventEmitter_1.EnhancedEventEmitter();
|
|
88
|
+
logger.debug('constructor() [id:%s, direction:%s]', id, direction);
|
|
89
|
+
this._id = id;
|
|
90
|
+
this._direction = direction;
|
|
91
|
+
this._extendedRtpCapabilities = extendedRtpCapabilities;
|
|
92
|
+
this._canProduceByKind = canProduceByKind;
|
|
93
|
+
this._maxSctpMessageSize =
|
|
94
|
+
sctpParameters ? sctpParameters.maxMessageSize : null;
|
|
95
|
+
// Clone and sanitize additionalSettings.
|
|
96
|
+
additionalSettings = utils.clone(additionalSettings, {});
|
|
97
|
+
delete additionalSettings.iceServers;
|
|
98
|
+
delete additionalSettings.iceTransportPolicy;
|
|
99
|
+
delete additionalSettings.bundlePolicy;
|
|
100
|
+
delete additionalSettings.rtcpMuxPolicy;
|
|
101
|
+
delete additionalSettings.sdpSemantics;
|
|
102
|
+
this._handler = handlerFactory();
|
|
103
|
+
this._handler.run({
|
|
104
|
+
direction,
|
|
105
|
+
iceParameters,
|
|
106
|
+
iceCandidates,
|
|
107
|
+
dtlsParameters,
|
|
108
|
+
sctpParameters,
|
|
109
|
+
iceServers,
|
|
110
|
+
iceTransportPolicy,
|
|
111
|
+
additionalSettings,
|
|
112
|
+
proprietaryConstraints,
|
|
113
|
+
extendedRtpCapabilities
|
|
114
|
+
});
|
|
115
|
+
this._appData = appData || {};
|
|
116
|
+
this.handleHandler();
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Transport id.
|
|
120
|
+
*/
|
|
121
|
+
get id() {
|
|
122
|
+
return this._id;
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Whether the Transport is closed.
|
|
126
|
+
*/
|
|
127
|
+
get closed() {
|
|
128
|
+
return this._closed;
|
|
129
|
+
}
|
|
130
|
+
/**
|
|
131
|
+
* Transport direction.
|
|
132
|
+
*/
|
|
133
|
+
get direction() {
|
|
134
|
+
return this._direction;
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* RTC handler instance.
|
|
138
|
+
*/
|
|
139
|
+
get handler() {
|
|
140
|
+
return this._handler;
|
|
141
|
+
}
|
|
142
|
+
/**
|
|
143
|
+
* Connection state.
|
|
144
|
+
*/
|
|
145
|
+
get connectionState() {
|
|
146
|
+
return this._connectionState;
|
|
147
|
+
}
|
|
148
|
+
/**
|
|
149
|
+
* App custom data.
|
|
150
|
+
*/
|
|
151
|
+
get appData() {
|
|
152
|
+
return this._appData;
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* App custom data setter.
|
|
156
|
+
*/
|
|
157
|
+
set appData(appData) {
|
|
158
|
+
this._appData = appData;
|
|
159
|
+
}
|
|
160
|
+
get observer() {
|
|
161
|
+
return this._observer;
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Close the Transport.
|
|
165
|
+
*/
|
|
166
|
+
close() {
|
|
167
|
+
if (this._closed) {
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
logger.debug('close()');
|
|
171
|
+
this._closed = true;
|
|
172
|
+
// Stop the AwaitQueue.
|
|
173
|
+
this._awaitQueue.stop();
|
|
174
|
+
// Close the handler.
|
|
175
|
+
this._handler.close();
|
|
176
|
+
// Close all Producers.
|
|
177
|
+
for (const producer of this._producers.values()) {
|
|
178
|
+
producer.transportClosed();
|
|
179
|
+
}
|
|
180
|
+
this._producers.clear();
|
|
181
|
+
// Close all Consumers.
|
|
182
|
+
for (const consumer of this._consumers.values()) {
|
|
183
|
+
consumer.transportClosed();
|
|
184
|
+
}
|
|
185
|
+
this._consumers.clear();
|
|
186
|
+
// Close all DataProducers.
|
|
187
|
+
for (const dataProducer of this._dataProducers.values()) {
|
|
188
|
+
dataProducer.transportClosed();
|
|
189
|
+
}
|
|
190
|
+
this._dataProducers.clear();
|
|
191
|
+
// Close all DataConsumers.
|
|
192
|
+
for (const dataConsumer of this._dataConsumers.values()) {
|
|
193
|
+
dataConsumer.transportClosed();
|
|
194
|
+
}
|
|
195
|
+
this._dataConsumers.clear();
|
|
196
|
+
// Emit observer event.
|
|
197
|
+
this._observer.safeEmit('close');
|
|
198
|
+
}
|
|
199
|
+
/**
|
|
200
|
+
* Get associated Transport (RTCPeerConnection) stats.
|
|
201
|
+
*
|
|
202
|
+
* @returns {RTCStatsReport}
|
|
203
|
+
*/
|
|
204
|
+
async getStats() {
|
|
205
|
+
if (this._closed) {
|
|
206
|
+
throw new errors_1.InvalidStateError('closed');
|
|
207
|
+
}
|
|
208
|
+
return this._handler.getTransportStats();
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Restart ICE connection.
|
|
212
|
+
*/
|
|
213
|
+
async restartIce({ iceParameters }) {
|
|
214
|
+
logger.debug('restartIce()');
|
|
215
|
+
if (this._closed) {
|
|
216
|
+
throw new errors_1.InvalidStateError('closed');
|
|
217
|
+
}
|
|
218
|
+
else if (!iceParameters) {
|
|
219
|
+
throw new TypeError('missing iceParameters');
|
|
220
|
+
}
|
|
221
|
+
// Enqueue command.
|
|
222
|
+
return this._awaitQueue.push(async () => this._handler.restartIce(iceParameters), 'transport.restartIce()');
|
|
223
|
+
}
|
|
224
|
+
/**
|
|
225
|
+
* Update ICE servers.
|
|
226
|
+
*/
|
|
227
|
+
async updateIceServers({ iceServers } = {}) {
|
|
228
|
+
logger.debug('updateIceServers()');
|
|
229
|
+
if (this._closed) {
|
|
230
|
+
throw new errors_1.InvalidStateError('closed');
|
|
231
|
+
}
|
|
232
|
+
else if (!Array.isArray(iceServers)) {
|
|
233
|
+
throw new TypeError('missing iceServers');
|
|
234
|
+
}
|
|
235
|
+
// Enqueue command.
|
|
236
|
+
return this._awaitQueue.push(async () => this._handler.updateIceServers(iceServers), 'transport.updateIceServers()');
|
|
237
|
+
}
|
|
238
|
+
/**
|
|
239
|
+
* Create a Producer.
|
|
240
|
+
*/
|
|
241
|
+
async produce({ track, encodings, codecOptions, codec, stopTracks = true, disableTrackOnPause = true, zeroRtpOnPause = false, appData = {} } = {}) {
|
|
242
|
+
logger.debug('produce() [track:%o]', track);
|
|
243
|
+
if (this._closed) {
|
|
244
|
+
throw new errors_1.InvalidStateError('closed');
|
|
245
|
+
}
|
|
246
|
+
else if (!track) {
|
|
247
|
+
throw new TypeError('missing track');
|
|
248
|
+
}
|
|
249
|
+
else if (this._direction !== 'send') {
|
|
250
|
+
throw new errors_1.UnsupportedError('not a sending Transport');
|
|
251
|
+
}
|
|
252
|
+
else if (!this._canProduceByKind[track.kind]) {
|
|
253
|
+
throw new errors_1.UnsupportedError(`cannot produce ${track.kind}`);
|
|
254
|
+
}
|
|
255
|
+
else if (track.readyState === 'ended') {
|
|
256
|
+
throw new errors_1.InvalidStateError('track ended');
|
|
257
|
+
}
|
|
258
|
+
else if (this.listenerCount('connect') === 0 && this._connectionState === 'new') {
|
|
259
|
+
throw new TypeError('no "connect" listener set into this transport');
|
|
260
|
+
}
|
|
261
|
+
else if (this.listenerCount('produce') === 0) {
|
|
262
|
+
throw new TypeError('no "produce" listener set into this transport');
|
|
263
|
+
}
|
|
264
|
+
else if (appData && typeof appData !== 'object') {
|
|
265
|
+
throw new TypeError('if given, appData must be an object');
|
|
266
|
+
}
|
|
267
|
+
// Enqueue command.
|
|
268
|
+
return this._awaitQueue.push(async () => {
|
|
269
|
+
let normalizedEncodings;
|
|
270
|
+
if (encodings && !Array.isArray(encodings)) {
|
|
271
|
+
throw TypeError('encodings must be an array');
|
|
272
|
+
}
|
|
273
|
+
else if (encodings && encodings.length === 0) {
|
|
274
|
+
normalizedEncodings = undefined;
|
|
275
|
+
}
|
|
276
|
+
else if (encodings) {
|
|
277
|
+
normalizedEncodings = encodings
|
|
278
|
+
.map((encoding) => {
|
|
279
|
+
const normalizedEncoding = { active: true };
|
|
280
|
+
if (encoding.active === false) {
|
|
281
|
+
normalizedEncoding.active = false;
|
|
282
|
+
}
|
|
283
|
+
if (typeof encoding.dtx === 'boolean') {
|
|
284
|
+
normalizedEncoding.dtx = encoding.dtx;
|
|
285
|
+
}
|
|
286
|
+
if (typeof encoding.scalabilityMode === 'string') {
|
|
287
|
+
normalizedEncoding.scalabilityMode = encoding.scalabilityMode;
|
|
288
|
+
}
|
|
289
|
+
if (typeof encoding.scaleResolutionDownBy === 'number') {
|
|
290
|
+
normalizedEncoding.scaleResolutionDownBy = encoding.scaleResolutionDownBy;
|
|
291
|
+
}
|
|
292
|
+
if (typeof encoding.maxBitrate === 'number') {
|
|
293
|
+
normalizedEncoding.maxBitrate = encoding.maxBitrate;
|
|
294
|
+
}
|
|
295
|
+
if (typeof encoding.maxFramerate === 'number') {
|
|
296
|
+
normalizedEncoding.maxFramerate = encoding.maxFramerate;
|
|
297
|
+
}
|
|
298
|
+
if (typeof encoding.adaptivePtime === 'boolean') {
|
|
299
|
+
normalizedEncoding.adaptivePtime = encoding.adaptivePtime;
|
|
300
|
+
}
|
|
301
|
+
if (typeof encoding.priority === 'string') {
|
|
302
|
+
normalizedEncoding.priority = encoding.priority;
|
|
303
|
+
}
|
|
304
|
+
if (typeof encoding.networkPriority === 'string') {
|
|
305
|
+
normalizedEncoding.networkPriority = encoding.networkPriority;
|
|
306
|
+
}
|
|
307
|
+
return normalizedEncoding;
|
|
308
|
+
});
|
|
309
|
+
}
|
|
310
|
+
const { localId, rtpParameters, rtpSender } = await this._handler.send({
|
|
311
|
+
track,
|
|
312
|
+
encodings: normalizedEncodings,
|
|
313
|
+
codecOptions,
|
|
314
|
+
codec
|
|
315
|
+
});
|
|
316
|
+
try {
|
|
317
|
+
// This will fill rtpParameters's missing fields with default values.
|
|
318
|
+
ortc.validateRtpParameters(rtpParameters);
|
|
319
|
+
const { id } = await new Promise((resolve, reject) => {
|
|
320
|
+
this.safeEmit('produce', {
|
|
321
|
+
kind: track.kind,
|
|
322
|
+
rtpParameters,
|
|
323
|
+
appData
|
|
324
|
+
}, resolve, reject);
|
|
325
|
+
});
|
|
326
|
+
const producer = new Producer_1.Producer({
|
|
327
|
+
id,
|
|
328
|
+
localId,
|
|
329
|
+
rtpSender,
|
|
330
|
+
track,
|
|
331
|
+
rtpParameters,
|
|
332
|
+
stopTracks,
|
|
333
|
+
disableTrackOnPause,
|
|
334
|
+
zeroRtpOnPause,
|
|
335
|
+
appData
|
|
336
|
+
});
|
|
337
|
+
this._producers.set(producer.id, producer);
|
|
338
|
+
this.handleProducer(producer);
|
|
339
|
+
// Emit observer event.
|
|
340
|
+
this._observer.safeEmit('newproducer', producer);
|
|
341
|
+
return producer;
|
|
342
|
+
}
|
|
343
|
+
catch (error) {
|
|
344
|
+
this._handler.stopSending(localId)
|
|
345
|
+
.catch(() => { });
|
|
346
|
+
throw error;
|
|
347
|
+
}
|
|
348
|
+
}, 'transport.produce()')
|
|
349
|
+
// This catch is needed to stop the given track if the command above
|
|
350
|
+
// failed due to closed Transport.
|
|
351
|
+
.catch((error) => {
|
|
352
|
+
if (stopTracks) {
|
|
353
|
+
try {
|
|
354
|
+
track.stop();
|
|
355
|
+
}
|
|
356
|
+
catch (error2) { }
|
|
357
|
+
}
|
|
358
|
+
throw error;
|
|
359
|
+
});
|
|
360
|
+
}
|
|
361
|
+
/**
|
|
362
|
+
* Create a Consumer to consume a remote Producer.
|
|
363
|
+
*/
|
|
364
|
+
async consume({ id, producerId, kind, rtpParameters, streamId, appData = {} }) {
|
|
365
|
+
logger.debug('consume()');
|
|
366
|
+
rtpParameters = utils.clone(rtpParameters, undefined);
|
|
367
|
+
if (this._closed) {
|
|
368
|
+
throw new errors_1.InvalidStateError('closed');
|
|
369
|
+
}
|
|
370
|
+
else if (this._direction !== 'recv') {
|
|
371
|
+
throw new errors_1.UnsupportedError('not a receiving Transport');
|
|
372
|
+
}
|
|
373
|
+
else if (typeof id !== 'string') {
|
|
374
|
+
throw new TypeError('missing id');
|
|
375
|
+
}
|
|
376
|
+
else if (typeof producerId !== 'string') {
|
|
377
|
+
throw new TypeError('missing producerId');
|
|
378
|
+
}
|
|
379
|
+
else if (kind !== 'audio' && kind !== 'video') {
|
|
380
|
+
throw new TypeError(`invalid kind '${kind}'`);
|
|
381
|
+
}
|
|
382
|
+
else if (this.listenerCount('connect') === 0 && this._connectionState === 'new') {
|
|
383
|
+
throw new TypeError('no "connect" listener set into this transport');
|
|
384
|
+
}
|
|
385
|
+
else if (appData && typeof appData !== 'object') {
|
|
386
|
+
throw new TypeError('if given, appData must be an object');
|
|
387
|
+
}
|
|
388
|
+
// Ensure the device can consume it.
|
|
389
|
+
const canConsume = ortc.canReceive(rtpParameters, this._extendedRtpCapabilities);
|
|
390
|
+
if (!canConsume) {
|
|
391
|
+
throw new errors_1.UnsupportedError('cannot consume this Producer');
|
|
392
|
+
}
|
|
393
|
+
const consumerCreationTask = new ConsumerCreationTask({
|
|
394
|
+
id,
|
|
395
|
+
producerId,
|
|
396
|
+
kind,
|
|
397
|
+
rtpParameters,
|
|
398
|
+
streamId,
|
|
399
|
+
appData
|
|
400
|
+
});
|
|
401
|
+
// Store the Consumer creation task.
|
|
402
|
+
this._pendingConsumerTasks.push(consumerCreationTask);
|
|
403
|
+
// There is no Consumer creation in progress, create it now.
|
|
404
|
+
(0, queue_microtask_1.default)(() => {
|
|
405
|
+
if (this._closed) {
|
|
406
|
+
return;
|
|
407
|
+
}
|
|
408
|
+
if (this._consumerCreationInProgress === false) {
|
|
409
|
+
this.createPendingConsumers();
|
|
410
|
+
}
|
|
411
|
+
});
|
|
412
|
+
return consumerCreationTask.promise;
|
|
413
|
+
}
|
|
414
|
+
/**
|
|
415
|
+
* Create a DataProducer
|
|
416
|
+
*/
|
|
417
|
+
async produceData({ ordered = true, maxPacketLifeTime, maxRetransmits, label = '', protocol = '', appData = {} } = {}) {
|
|
418
|
+
logger.debug('produceData()');
|
|
419
|
+
if (this._closed) {
|
|
420
|
+
throw new errors_1.InvalidStateError('closed');
|
|
421
|
+
}
|
|
422
|
+
else if (this._direction !== 'send') {
|
|
423
|
+
throw new errors_1.UnsupportedError('not a sending Transport');
|
|
424
|
+
}
|
|
425
|
+
else if (!this._maxSctpMessageSize) {
|
|
426
|
+
throw new errors_1.UnsupportedError('SCTP not enabled by remote Transport');
|
|
427
|
+
}
|
|
428
|
+
else if (this.listenerCount('connect') === 0 && this._connectionState === 'new') {
|
|
429
|
+
throw new TypeError('no "connect" listener set into this transport');
|
|
430
|
+
}
|
|
431
|
+
else if (this.listenerCount('producedata') === 0) {
|
|
432
|
+
throw new TypeError('no "producedata" listener set into this transport');
|
|
433
|
+
}
|
|
434
|
+
else if (appData && typeof appData !== 'object') {
|
|
435
|
+
throw new TypeError('if given, appData must be an object');
|
|
436
|
+
}
|
|
437
|
+
if (maxPacketLifeTime || maxRetransmits) {
|
|
438
|
+
ordered = false;
|
|
439
|
+
}
|
|
440
|
+
// Enqueue command.
|
|
441
|
+
return this._awaitQueue.push(async () => {
|
|
442
|
+
const { dataChannel, sctpStreamParameters } = await this._handler.sendDataChannel({
|
|
443
|
+
ordered,
|
|
444
|
+
maxPacketLifeTime,
|
|
445
|
+
maxRetransmits,
|
|
446
|
+
label,
|
|
447
|
+
protocol
|
|
448
|
+
});
|
|
449
|
+
// This will fill sctpStreamParameters's missing fields with default values.
|
|
450
|
+
ortc.validateSctpStreamParameters(sctpStreamParameters);
|
|
451
|
+
const { id } = await new Promise((resolve, reject) => {
|
|
452
|
+
this.safeEmit('producedata', {
|
|
453
|
+
sctpStreamParameters,
|
|
454
|
+
label,
|
|
455
|
+
protocol,
|
|
456
|
+
appData
|
|
457
|
+
}, resolve, reject);
|
|
458
|
+
});
|
|
459
|
+
const dataProducer = new DataProducer_1.DataProducer({
|
|
460
|
+
id,
|
|
461
|
+
dataChannel,
|
|
462
|
+
sctpStreamParameters,
|
|
463
|
+
appData
|
|
464
|
+
});
|
|
465
|
+
this._dataProducers.set(dataProducer.id, dataProducer);
|
|
466
|
+
this.handleDataProducer(dataProducer);
|
|
467
|
+
// Emit observer event.
|
|
468
|
+
this._observer.safeEmit('newdataproducer', dataProducer);
|
|
469
|
+
return dataProducer;
|
|
470
|
+
}, 'transport.produceData()');
|
|
471
|
+
}
|
|
472
|
+
/**
|
|
473
|
+
* Create a DataConsumer
|
|
474
|
+
*/
|
|
475
|
+
async consumeData({ id, dataProducerId, sctpStreamParameters, label = '', protocol = '', appData = {} }) {
|
|
476
|
+
logger.debug('consumeData()');
|
|
477
|
+
sctpStreamParameters = utils.clone(sctpStreamParameters, undefined);
|
|
478
|
+
if (this._closed) {
|
|
479
|
+
throw new errors_1.InvalidStateError('closed');
|
|
480
|
+
}
|
|
481
|
+
else if (this._direction !== 'recv') {
|
|
482
|
+
throw new errors_1.UnsupportedError('not a receiving Transport');
|
|
483
|
+
}
|
|
484
|
+
else if (!this._maxSctpMessageSize) {
|
|
485
|
+
throw new errors_1.UnsupportedError('SCTP not enabled by remote Transport');
|
|
486
|
+
}
|
|
487
|
+
else if (typeof id !== 'string') {
|
|
488
|
+
throw new TypeError('missing id');
|
|
489
|
+
}
|
|
490
|
+
else if (typeof dataProducerId !== 'string') {
|
|
491
|
+
throw new TypeError('missing dataProducerId');
|
|
492
|
+
}
|
|
493
|
+
else if (this.listenerCount('connect') === 0 && this._connectionState === 'new') {
|
|
494
|
+
throw new TypeError('no "connect" listener set into this transport');
|
|
495
|
+
}
|
|
496
|
+
else if (appData && typeof appData !== 'object') {
|
|
497
|
+
throw new TypeError('if given, appData must be an object');
|
|
498
|
+
}
|
|
499
|
+
// This may throw.
|
|
500
|
+
ortc.validateSctpStreamParameters(sctpStreamParameters);
|
|
501
|
+
// Enqueue command.
|
|
502
|
+
return this._awaitQueue.push(async () => {
|
|
503
|
+
const { dataChannel } = await this._handler.receiveDataChannel({
|
|
504
|
+
sctpStreamParameters,
|
|
505
|
+
label,
|
|
506
|
+
protocol
|
|
507
|
+
});
|
|
508
|
+
const dataConsumer = new DataConsumer_1.DataConsumer({
|
|
509
|
+
id,
|
|
510
|
+
dataProducerId,
|
|
511
|
+
dataChannel,
|
|
512
|
+
sctpStreamParameters,
|
|
513
|
+
appData
|
|
514
|
+
});
|
|
515
|
+
this._dataConsumers.set(dataConsumer.id, dataConsumer);
|
|
516
|
+
this.handleDataConsumer(dataConsumer);
|
|
517
|
+
// Emit observer event.
|
|
518
|
+
this._observer.safeEmit('newdataconsumer', dataConsumer);
|
|
519
|
+
return dataConsumer;
|
|
520
|
+
}, 'transport.consumeData()');
|
|
521
|
+
}
|
|
522
|
+
// This method is guaranteed to never throw.
|
|
523
|
+
async createPendingConsumers() {
|
|
524
|
+
this._consumerCreationInProgress = true;
|
|
525
|
+
this._awaitQueue.push(async () => {
|
|
526
|
+
if (this._pendingConsumerTasks.length === 0) {
|
|
527
|
+
logger.debug('createPendingConsumers() | there is no Consumer to be created');
|
|
528
|
+
return;
|
|
529
|
+
}
|
|
530
|
+
const pendingConsumerTasks = [...this._pendingConsumerTasks];
|
|
531
|
+
// Clear pending Consumer tasks.
|
|
532
|
+
this._pendingConsumerTasks = [];
|
|
533
|
+
// Video Consumer in order to create the probator.
|
|
534
|
+
let videoConsumerForProbator = undefined;
|
|
535
|
+
// Fill options list.
|
|
536
|
+
const optionsList = [];
|
|
537
|
+
for (const task of pendingConsumerTasks) {
|
|
538
|
+
const { id, kind, rtpParameters, streamId } = task.consumerOptions;
|
|
539
|
+
optionsList.push({
|
|
540
|
+
trackId: id,
|
|
541
|
+
kind: kind,
|
|
542
|
+
rtpParameters,
|
|
543
|
+
streamId
|
|
544
|
+
});
|
|
545
|
+
}
|
|
546
|
+
try {
|
|
547
|
+
const results = await this._handler.receive(optionsList);
|
|
548
|
+
for (let idx = 0; idx < results.length; ++idx) {
|
|
549
|
+
const task = pendingConsumerTasks[idx];
|
|
550
|
+
const result = results[idx];
|
|
551
|
+
const { id, producerId, kind, rtpParameters, appData } = task.consumerOptions;
|
|
552
|
+
const { localId, rtpReceiver, track } = result;
|
|
553
|
+
const consumer = new Consumer_1.Consumer({
|
|
554
|
+
id: id,
|
|
555
|
+
localId,
|
|
556
|
+
producerId: producerId,
|
|
557
|
+
rtpReceiver,
|
|
558
|
+
track,
|
|
559
|
+
rtpParameters,
|
|
560
|
+
appData: appData
|
|
561
|
+
});
|
|
562
|
+
this._consumers.set(consumer.id, consumer);
|
|
563
|
+
this.handleConsumer(consumer);
|
|
564
|
+
// If this is the first video Consumer and the Consumer for RTP probation
|
|
565
|
+
// has not yet been created, it's time to create it.
|
|
566
|
+
if (!this._probatorConsumerCreated &&
|
|
567
|
+
!videoConsumerForProbator && kind === 'video') {
|
|
568
|
+
videoConsumerForProbator = consumer;
|
|
569
|
+
}
|
|
570
|
+
// Emit observer event.
|
|
571
|
+
this._observer.safeEmit('newconsumer', consumer);
|
|
572
|
+
task.resolve(consumer);
|
|
573
|
+
}
|
|
574
|
+
}
|
|
575
|
+
catch (error) {
|
|
576
|
+
for (const task of pendingConsumerTasks) {
|
|
577
|
+
task.reject(error);
|
|
578
|
+
}
|
|
579
|
+
}
|
|
580
|
+
// If RTP probation must be handled, do it now.
|
|
581
|
+
if (videoConsumerForProbator) {
|
|
582
|
+
try {
|
|
583
|
+
const probatorRtpParameters = ortc.generateProbatorRtpParameters(videoConsumerForProbator.rtpParameters);
|
|
584
|
+
await this._handler.receive([{
|
|
585
|
+
trackId: 'probator',
|
|
586
|
+
kind: 'video',
|
|
587
|
+
rtpParameters: probatorRtpParameters
|
|
588
|
+
}]);
|
|
589
|
+
logger.debug('createPendingConsumers() | Consumer for RTP probation created');
|
|
590
|
+
this._probatorConsumerCreated = true;
|
|
591
|
+
}
|
|
592
|
+
catch (error) {
|
|
593
|
+
logger.error('createPendingConsumers() | failed to create Consumer for RTP probation:%o', error);
|
|
594
|
+
}
|
|
595
|
+
}
|
|
596
|
+
}, 'transport.createPendingConsumers()')
|
|
597
|
+
.then(() => {
|
|
598
|
+
this._consumerCreationInProgress = false;
|
|
599
|
+
// There are pending Consumer tasks, enqueue their creation.
|
|
600
|
+
if (this._pendingConsumerTasks.length > 0) {
|
|
601
|
+
this.createPendingConsumers();
|
|
602
|
+
}
|
|
603
|
+
})
|
|
604
|
+
// NOTE: We only get here when the await queue is closed.
|
|
605
|
+
.catch(() => { });
|
|
606
|
+
}
|
|
607
|
+
pausePendingConsumers() {
|
|
608
|
+
this._consumerPauseInProgress = true;
|
|
609
|
+
this._awaitQueue.push(async () => {
|
|
610
|
+
if (this._pendingPauseConsumers.size === 0) {
|
|
611
|
+
logger.debug('pausePendingConsumers() | there is no Consumer to be paused');
|
|
612
|
+
return;
|
|
613
|
+
}
|
|
614
|
+
const pendingPauseConsumers = Array.from(this._pendingPauseConsumers.values());
|
|
615
|
+
// Clear pending pause Consumer map.
|
|
616
|
+
this._pendingPauseConsumers.clear();
|
|
617
|
+
try {
|
|
618
|
+
const localIds = pendingPauseConsumers
|
|
619
|
+
.map((consumer) => consumer.localId);
|
|
620
|
+
await this._handler.pauseReceiving(localIds);
|
|
621
|
+
}
|
|
622
|
+
catch (error) {
|
|
623
|
+
logger.error('pausePendingConsumers() | failed to pause Consumers:', error);
|
|
624
|
+
}
|
|
625
|
+
}, 'transport.pausePendingConsumers')
|
|
626
|
+
.then(() => {
|
|
627
|
+
this._consumerPauseInProgress = false;
|
|
628
|
+
// There are pending Consumers to be paused, do it.
|
|
629
|
+
if (this._pendingPauseConsumers.size > 0) {
|
|
630
|
+
this.pausePendingConsumers();
|
|
631
|
+
}
|
|
632
|
+
})
|
|
633
|
+
// NOTE: We only get here when the await queue is closed.
|
|
634
|
+
.catch(() => { });
|
|
635
|
+
}
|
|
636
|
+
resumePendingConsumers() {
|
|
637
|
+
this._consumerResumeInProgress = true;
|
|
638
|
+
this._awaitQueue.push(async () => {
|
|
639
|
+
if (this._pendingResumeConsumers.size === 0) {
|
|
640
|
+
logger.debug('resumePendingConsumers() | there is no Consumer to be resumed');
|
|
641
|
+
return;
|
|
642
|
+
}
|
|
643
|
+
const pendingResumeConsumers = Array.from(this._pendingResumeConsumers.values());
|
|
644
|
+
// Clear pending resume Consumer map.
|
|
645
|
+
this._pendingResumeConsumers.clear();
|
|
646
|
+
try {
|
|
647
|
+
const localIds = pendingResumeConsumers
|
|
648
|
+
.map((consumer) => consumer.localId);
|
|
649
|
+
await this._handler.resumeReceiving(localIds);
|
|
650
|
+
}
|
|
651
|
+
catch (error) {
|
|
652
|
+
logger.error('resumePendingConsumers() | failed to resume Consumers:', error);
|
|
653
|
+
}
|
|
654
|
+
}, 'transport.resumePendingConsumers')
|
|
655
|
+
.then(() => {
|
|
656
|
+
this._consumerResumeInProgress = false;
|
|
657
|
+
// There are pending Consumer to be resumed, do it.
|
|
658
|
+
if (this._pendingResumeConsumers.size > 0) {
|
|
659
|
+
this.resumePendingConsumers();
|
|
660
|
+
}
|
|
661
|
+
})
|
|
662
|
+
// NOTE: We only get here when the await queue is closed.
|
|
663
|
+
.catch(() => { });
|
|
664
|
+
}
|
|
665
|
+
closePendingConsumers() {
|
|
666
|
+
this._consumerCloseInProgress = true;
|
|
667
|
+
this._awaitQueue.push(async () => {
|
|
668
|
+
if (this._pendingCloseConsumers.size === 0) {
|
|
669
|
+
logger.debug('closePendingConsumers() | there is no Consumer to be closed');
|
|
670
|
+
return;
|
|
671
|
+
}
|
|
672
|
+
const pendingCloseConsumers = Array.from(this._pendingCloseConsumers.values());
|
|
673
|
+
// Clear pending close Consumer map.
|
|
674
|
+
this._pendingCloseConsumers.clear();
|
|
675
|
+
try {
|
|
676
|
+
await this._handler.stopReceiving(pendingCloseConsumers.map((consumer) => consumer.localId));
|
|
677
|
+
}
|
|
678
|
+
catch (error) {
|
|
679
|
+
logger.error('closePendingConsumers() | failed to close Consumers:', error);
|
|
680
|
+
}
|
|
681
|
+
}, 'transport.closePendingConsumers')
|
|
682
|
+
.then(() => {
|
|
683
|
+
this._consumerCloseInProgress = false;
|
|
684
|
+
// There are pending Consumer to be resumed, do it.
|
|
685
|
+
if (this._pendingCloseConsumers.size > 0) {
|
|
686
|
+
this.closePendingConsumers();
|
|
687
|
+
}
|
|
688
|
+
})
|
|
689
|
+
// NOTE: We only get here when the await queue is closed.
|
|
690
|
+
.catch(() => { });
|
|
691
|
+
}
|
|
692
|
+
handleHandler() {
|
|
693
|
+
const handler = this._handler;
|
|
694
|
+
handler.on('@connect', ({ dtlsParameters }, callback, errback) => {
|
|
695
|
+
if (this._closed) {
|
|
696
|
+
errback(new errors_1.InvalidStateError('closed'));
|
|
697
|
+
return;
|
|
698
|
+
}
|
|
699
|
+
this.safeEmit('connect', { dtlsParameters }, callback, errback);
|
|
700
|
+
});
|
|
701
|
+
handler.on('@connectionstatechange', (connectionState) => {
|
|
702
|
+
if (connectionState === this._connectionState) {
|
|
703
|
+
return;
|
|
704
|
+
}
|
|
705
|
+
logger.debug('connection state changed to %s', connectionState);
|
|
706
|
+
this._connectionState = connectionState;
|
|
707
|
+
if (!this._closed) {
|
|
708
|
+
this.safeEmit('connectionstatechange', connectionState);
|
|
709
|
+
}
|
|
710
|
+
});
|
|
711
|
+
}
|
|
712
|
+
handleProducer(producer) {
|
|
713
|
+
producer.on('@close', () => {
|
|
714
|
+
this._producers.delete(producer.id);
|
|
715
|
+
if (this._closed) {
|
|
716
|
+
return;
|
|
717
|
+
}
|
|
718
|
+
this._awaitQueue.push(async () => this._handler.stopSending(producer.localId), 'producer @close event')
|
|
719
|
+
.catch((error) => logger.warn('producer.close() failed:%o', error));
|
|
720
|
+
});
|
|
721
|
+
producer.on('@pause', (callback, errback) => {
|
|
722
|
+
this._awaitQueue.push(async () => this._handler.pauseSending(producer.localId), 'producer @pause event')
|
|
723
|
+
.then(callback)
|
|
724
|
+
.catch(errback);
|
|
725
|
+
});
|
|
726
|
+
producer.on('@resume', (callback, errback) => {
|
|
727
|
+
this._awaitQueue.push(async () => this._handler.resumeSending(producer.localId), 'producer @resume event')
|
|
728
|
+
.then(callback)
|
|
729
|
+
.catch(errback);
|
|
730
|
+
});
|
|
731
|
+
producer.on('@replacetrack', (track, callback, errback) => {
|
|
732
|
+
this._awaitQueue.push(async () => this._handler.replaceTrack(producer.localId, track), 'producer @replacetrack event')
|
|
733
|
+
.then(callback)
|
|
734
|
+
.catch(errback);
|
|
735
|
+
});
|
|
736
|
+
producer.on('@setmaxspatiallayer', (spatialLayer, callback, errback) => {
|
|
737
|
+
this._awaitQueue.push(async () => (this._handler.setMaxSpatialLayer(producer.localId, spatialLayer)), 'producer @setmaxspatiallayer event')
|
|
738
|
+
.then(callback)
|
|
739
|
+
.catch(errback);
|
|
740
|
+
});
|
|
741
|
+
producer.on('@setrtpencodingparameters', (params, callback, errback) => {
|
|
742
|
+
this._awaitQueue.push(async () => (this._handler.setRtpEncodingParameters(producer.localId, params)), 'producer @setrtpencodingparameters event')
|
|
743
|
+
.then(callback)
|
|
744
|
+
.catch(errback);
|
|
745
|
+
});
|
|
746
|
+
producer.on('@getstats', (callback, errback) => {
|
|
747
|
+
if (this._closed) {
|
|
748
|
+
return errback(new errors_1.InvalidStateError('closed'));
|
|
749
|
+
}
|
|
750
|
+
this._handler.getSenderStats(producer.localId)
|
|
751
|
+
.then(callback)
|
|
752
|
+
.catch(errback);
|
|
753
|
+
});
|
|
754
|
+
}
|
|
755
|
+
handleConsumer(consumer) {
|
|
756
|
+
consumer.on('@close', () => {
|
|
757
|
+
this._consumers.delete(consumer.id);
|
|
758
|
+
this._pendingPauseConsumers.delete(consumer.id);
|
|
759
|
+
this._pendingResumeConsumers.delete(consumer.id);
|
|
760
|
+
if (this._closed) {
|
|
761
|
+
return;
|
|
762
|
+
}
|
|
763
|
+
// Store the Consumer into the close list.
|
|
764
|
+
this._pendingCloseConsumers.set(consumer.id, consumer);
|
|
765
|
+
// There is no Consumer close in progress, do it now.
|
|
766
|
+
if (this._consumerCloseInProgress === false) {
|
|
767
|
+
this.closePendingConsumers();
|
|
768
|
+
}
|
|
769
|
+
});
|
|
770
|
+
consumer.on('@pause', () => {
|
|
771
|
+
// If Consumer is pending to be resumed, remove from pending resume list.
|
|
772
|
+
if (this._pendingResumeConsumers.has(consumer.id)) {
|
|
773
|
+
this._pendingResumeConsumers.delete(consumer.id);
|
|
774
|
+
}
|
|
775
|
+
// Store the Consumer into the pending list.
|
|
776
|
+
this._pendingPauseConsumers.set(consumer.id, consumer);
|
|
777
|
+
// There is no Consumer pause in progress, do it now.
|
|
778
|
+
(0, queue_microtask_1.default)(() => {
|
|
779
|
+
if (this._closed) {
|
|
780
|
+
return;
|
|
781
|
+
}
|
|
782
|
+
if (this._consumerPauseInProgress === false) {
|
|
783
|
+
this.pausePendingConsumers();
|
|
784
|
+
}
|
|
785
|
+
});
|
|
786
|
+
});
|
|
787
|
+
consumer.on('@resume', () => {
|
|
788
|
+
// If Consumer is pending to be paused, remove from pending pause list.
|
|
789
|
+
if (this._pendingPauseConsumers.has(consumer.id)) {
|
|
790
|
+
this._pendingPauseConsumers.delete(consumer.id);
|
|
791
|
+
}
|
|
792
|
+
// Store the Consumer into the pending list.
|
|
793
|
+
this._pendingResumeConsumers.set(consumer.id, consumer);
|
|
794
|
+
// There is no Consumer resume in progress, do it now.
|
|
795
|
+
(0, queue_microtask_1.default)(() => {
|
|
796
|
+
if (this._closed) {
|
|
797
|
+
return;
|
|
798
|
+
}
|
|
799
|
+
if (this._consumerResumeInProgress === false) {
|
|
800
|
+
this.resumePendingConsumers();
|
|
801
|
+
}
|
|
802
|
+
});
|
|
803
|
+
});
|
|
804
|
+
consumer.on('@getstats', (callback, errback) => {
|
|
805
|
+
if (this._closed) {
|
|
806
|
+
return errback(new errors_1.InvalidStateError('closed'));
|
|
807
|
+
}
|
|
808
|
+
this._handler.getReceiverStats(consumer.localId)
|
|
809
|
+
.then(callback)
|
|
810
|
+
.catch(errback);
|
|
811
|
+
});
|
|
812
|
+
}
|
|
813
|
+
handleDataProducer(dataProducer) {
|
|
814
|
+
dataProducer.on('@close', () => {
|
|
815
|
+
this._dataProducers.delete(dataProducer.id);
|
|
816
|
+
});
|
|
817
|
+
}
|
|
818
|
+
handleDataConsumer(dataConsumer) {
|
|
819
|
+
dataConsumer.on('@close', () => {
|
|
820
|
+
this._dataConsumers.delete(dataConsumer.id);
|
|
821
|
+
});
|
|
822
|
+
}
|
|
823
|
+
}
|
|
824
|
+
exports.Transport = Transport;
|