@observertc/observer-js 0.42.5 → 0.42.7
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/ObservedCall.d.ts +5 -4
- package/lib/ObservedCall.d.ts.map +1 -1
- package/lib/ObservedCall.js +15 -13
- package/lib/ObservedClient.d.ts +8 -2
- package/lib/ObservedClient.d.ts.map +1 -1
- package/lib/ObservedClient.js +30 -8
- package/lib/ObservedPeerConnection.d.ts +1 -0
- package/lib/ObservedPeerConnection.d.ts.map +1 -1
- package/lib/ObservedPeerConnection.js +43 -22
- package/lib/Observer.js +2 -3
- package/lib/common/CalculatedScore.d.ts +1 -0
- package/lib/common/CalculatedScore.d.ts.map +1 -1
- package/lib/common/CalculatedScore.js +9 -2
- package/package.json +1 -1
- package/src/ObservedCall.ts +22 -14
- package/src/ObservedClient.ts +35 -7
- package/src/ObservedPeerConnection.ts +48 -25
- package/src/Observer.ts +2 -2
- package/src/common/CalculatedScore.ts +9 -1
package/lib/ObservedCall.d.ts
CHANGED
|
@@ -40,19 +40,20 @@ export declare class ObservedCall<AppData extends Record<string, unknown> = Reco
|
|
|
40
40
|
readonly sfuStreamIdToOutboundAudioTrack: Map<string | number, ObservedOutboundAudioTrack>;
|
|
41
41
|
readonly sfuStreamIdToOutboundVideoTrack: Map<string | number, ObservedOutboundVideoTrack>;
|
|
42
42
|
private _closed;
|
|
43
|
-
private _updated;
|
|
44
|
-
ended?: number;
|
|
45
43
|
started?: number;
|
|
44
|
+
ended?: number;
|
|
45
|
+
observationUpdated: number;
|
|
46
|
+
observationEnded?: number;
|
|
47
|
+
readonly observationStarted: number;
|
|
46
48
|
constructor(_model: ObservedCallModel, observer: Observer, appData: AppData);
|
|
47
49
|
get serviceId(): string;
|
|
48
50
|
get reports(): import("./ReportsCollector").ReportsCollector;
|
|
49
51
|
get roomId(): string;
|
|
50
52
|
get callId(): string;
|
|
51
|
-
get updated(): number;
|
|
52
53
|
get clients(): ReadonlyMap<string, ObservedClient>;
|
|
53
54
|
get score(): CalculatedScore | undefined;
|
|
54
55
|
get closed(): boolean;
|
|
55
|
-
close(
|
|
56
|
+
close(): void;
|
|
56
57
|
addEventReport(params: PartialBy<Omit<CallEventReport, 'serviceId' | 'roomId' | 'callId'>, 'timestamp'>): void;
|
|
57
58
|
createClient<ClientAppData extends Record<string, unknown> = Record<string, unknown>>(config: ObservedClientModel & {
|
|
58
59
|
appData: ClientAppData;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ObservedCall.d.ts","sourceRoot":"","sources":["../src/ObservedCall.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,QAAQ,CAAC;AACtC,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvE,OAAO,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAEtC,OAAO,EAAa,SAAS,EAAE,MAAM,gBAAgB,CAAC;AACtD,OAAO,EAAE,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAEhE,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,0BAA0B,EAAE,MAAM,8BAA8B,CAAC;AAC1E,OAAO,EAAE,0BAA0B,EAAE,MAAM,8BAA8B,CAAC;AAC1E,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAE3D,MAAM,MAAM,iBAAiB,GAAG;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;CACf,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG;IAChC,MAAM,EAAE,EAAE,CAAC;IACX,SAAS,EAAE,CAAC,cAAc,CAAC,CAAC;IAC5B,SAAS,EAAE,CAAC,IAAI,CAAC,eAAe,EAAE,QAAQ,GAAG,WAAW,GAAG,QAAQ,CAAC,CAAC,CAAC;IACtE,KAAK,EAAE,EAAE,CAAC;IACV,KAAK,EAAE,EAAE,CAAC;CACV,CAAA;AAED,MAAM,CAAC,OAAO,WAAW,YAAY;IACpC,EAAE,CAAC,CAAC,SAAS,MAAM,kBAAkB,EAAE,KAAK,EAAE,CAAC,EAAE,QAAQ,EAAE,CAAC,GAAG,IAAI,EAAE,kBAAkB,CAAC,CAAC,CAAC,KAAK,IAAI,GAAG,IAAI,CAAC;IAC3G,GAAG,CAAC,CAAC,SAAS,MAAM,kBAAkB,EAAE,KAAK,EAAE,CAAC,EAAE,QAAQ,EAAE,CAAC,GAAG,IAAI,EAAE,kBAAkB,CAAC,CAAC,CAAC,KAAK,IAAI,GAAG,IAAI,CAAC;IAC5G,IAAI,CAAC,CAAC,SAAS,MAAM,kBAAkB,EAAE,KAAK,EAAE,CAAC,EAAE,QAAQ,EAAE,CAAC,GAAG,IAAI,EAAE,kBAAkB,CAAC,CAAC,CAAC,KAAK,IAAI,GAAG,IAAI,CAAC;IAC7G,IAAI,CAAC,CAAC,SAAS,MAAM,kBAAkB,EAAE,KAAK,EAAE,CAAC,EAAE,GAAG,IAAI,EAAE,kBAAkB,CAAC,CAAC,CAAC,GAAG,OAAO,CAAC;CAC5F;AAED,qBAAa,YAAY,CAAC,OAAO,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAE,SAAQ,YAAY;
|
|
1
|
+
{"version":3,"file":"ObservedCall.d.ts","sourceRoot":"","sources":["../src/ObservedCall.ts"],"names":[],"mappings":"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"}
|
package/lib/ObservedCall.js
CHANGED
|
@@ -29,8 +29,8 @@ class ObservedCall extends events_1.EventEmitter {
|
|
|
29
29
|
this.sfuStreamIdToOutboundAudioTrack = new Map();
|
|
30
30
|
this.sfuStreamIdToOutboundVideoTrack = new Map();
|
|
31
31
|
this._closed = false;
|
|
32
|
-
this.
|
|
33
|
-
this.
|
|
32
|
+
this.observationUpdated = Date.now();
|
|
33
|
+
this.observationStarted = Date.now();
|
|
34
34
|
this.setMaxListeners(Infinity);
|
|
35
35
|
}
|
|
36
36
|
get serviceId() {
|
|
@@ -48,9 +48,6 @@ class ObservedCall extends events_1.EventEmitter {
|
|
|
48
48
|
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
|
|
49
49
|
return this._model.callId;
|
|
50
50
|
}
|
|
51
|
-
get updated() {
|
|
52
|
-
return this._updated;
|
|
53
|
-
}
|
|
54
51
|
get clients() {
|
|
55
52
|
return this._clients;
|
|
56
53
|
}
|
|
@@ -84,17 +81,12 @@ class ObservedCall extends events_1.EventEmitter {
|
|
|
84
81
|
get closed() {
|
|
85
82
|
return this._closed;
|
|
86
83
|
}
|
|
87
|
-
close(
|
|
84
|
+
close() {
|
|
88
85
|
if (this._closed)
|
|
89
86
|
return;
|
|
90
87
|
this._closed = true;
|
|
91
|
-
if (timestamp) {
|
|
92
|
-
this.ended = timestamp;
|
|
93
|
-
}
|
|
94
|
-
else if (!this.ended) {
|
|
95
|
-
this.ended = Date.now();
|
|
96
|
-
}
|
|
97
88
|
Array.from(this._clients.values()).forEach((client) => client.close());
|
|
89
|
+
this.observationEnded = Date.now();
|
|
98
90
|
this.emit('close');
|
|
99
91
|
}
|
|
100
92
|
addEventReport(params) {
|
|
@@ -108,7 +100,17 @@ class ObservedCall extends events_1.EventEmitter {
|
|
|
108
100
|
const { appData, createClientJoinedReport, createClientLeftReport, joinedTimestamp = Date.now() } = config, model = __rest(config, ["appData", "createClientJoinedReport", "createClientLeftReport", "joinedTimestamp"]);
|
|
109
101
|
const result = new ObservedClient_1.ObservedClient(model, this, appData);
|
|
110
102
|
const onUpdate = ({ sample }) => {
|
|
111
|
-
this.
|
|
103
|
+
this.observationUpdated = Date.now();
|
|
104
|
+
if (result.joined) {
|
|
105
|
+
if (this.started === undefined || result.joined < this.started) {
|
|
106
|
+
this.started = result.joined;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
if (result.left) {
|
|
110
|
+
if (this.ended === undefined || result.left > this.ended) {
|
|
111
|
+
this.ended = result.left;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
112
114
|
this.emit('update');
|
|
113
115
|
this.processor.process(sample);
|
|
114
116
|
};
|
package/lib/ObservedClient.d.ts
CHANGED
|
@@ -30,6 +30,8 @@ export type ObservedClientEvents = {
|
|
|
30
30
|
}
|
|
31
31
|
];
|
|
32
32
|
close: [];
|
|
33
|
+
joined: [];
|
|
34
|
+
left: [];
|
|
33
35
|
newpeerconnection: [ObservedPeerConnection];
|
|
34
36
|
iceconnectionstatechange: [
|
|
35
37
|
{
|
|
@@ -95,8 +97,8 @@ export declare class ObservedClient<AppData extends Record<string, unknown> = Re
|
|
|
95
97
|
private _closed;
|
|
96
98
|
private _acceptedSamples;
|
|
97
99
|
private _timeZoneOffsetInHours?;
|
|
98
|
-
|
|
99
|
-
|
|
100
|
+
private _joined?;
|
|
101
|
+
private _left?;
|
|
100
102
|
lastStatsTimestamp?: number;
|
|
101
103
|
score?: CalculatedScore;
|
|
102
104
|
usingTURN: boolean;
|
|
@@ -136,6 +138,10 @@ export declare class ObservedClient<AppData extends Record<string, unknown> = Re
|
|
|
136
138
|
ωpendingMediaTrackTimestamps: PendingMediaTrackTimestamp[];
|
|
137
139
|
constructor(_model: ObservedClientModel, call: ObservedCall, appData: AppData);
|
|
138
140
|
getSfu<T extends Record<string, unknown> = Record<string, unknown>>(): ObservedSfu<T> | undefined;
|
|
141
|
+
get joined(): number | undefined;
|
|
142
|
+
set joined(value: number | undefined);
|
|
143
|
+
get left(): number | undefined;
|
|
144
|
+
set left(value: number | undefined);
|
|
139
145
|
get sfu(): ObservedSfu | undefined;
|
|
140
146
|
get coordinates(): {
|
|
141
147
|
latitude: number;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ObservedClient.d.ts","sourceRoot":"","sources":["../src/ObservedClient.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"ObservedClient.d.ts","sourceRoot":"","sources":["../src/ObservedClient.ts"],"names":[],"mappings":"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"}
|
package/lib/ObservedClient.js
CHANGED
|
@@ -70,6 +70,24 @@ class ObservedClient extends events_1.EventEmitter {
|
|
|
70
70
|
return;
|
|
71
71
|
return sfu;
|
|
72
72
|
}
|
|
73
|
+
get joined() {
|
|
74
|
+
return this._joined;
|
|
75
|
+
}
|
|
76
|
+
set joined(value) {
|
|
77
|
+
this._joined = value;
|
|
78
|
+
if (this._joined) {
|
|
79
|
+
this.emit('joined');
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
get left() {
|
|
83
|
+
return this._left;
|
|
84
|
+
}
|
|
85
|
+
set left(value) {
|
|
86
|
+
this._left = value;
|
|
87
|
+
if (this._left) {
|
|
88
|
+
this.emit('left');
|
|
89
|
+
}
|
|
90
|
+
}
|
|
73
91
|
get sfu() {
|
|
74
92
|
if (!this.sfuId)
|
|
75
93
|
return;
|
|
@@ -188,7 +206,7 @@ class ObservedClient extends events_1.EventEmitter {
|
|
|
188
206
|
this._addAndEmitIssue(issue);
|
|
189
207
|
}
|
|
190
208
|
accept(sample) {
|
|
191
|
-
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18, _19, _20, _21, _22, _23, _24, _25
|
|
209
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18, _19, _20, _21, _22, _23, _24, _25;
|
|
192
210
|
if (this._closed)
|
|
193
211
|
throw new Error(`Client ${this.clientId} is closed`);
|
|
194
212
|
if (sample.clientId && sample.clientId !== 'NULL' && sample.clientId !== this.clientId) {
|
|
@@ -286,8 +304,8 @@ class ObservedClient extends events_1.EventEmitter {
|
|
|
286
304
|
extensionType: extensionStats.type,
|
|
287
305
|
});
|
|
288
306
|
}
|
|
289
|
-
for (let
|
|
290
|
-
const { timestamp } =
|
|
307
|
+
for (let _26 of (_p = sample.customCallEvents) !== null && _p !== void 0 ? _p : []) {
|
|
308
|
+
const { timestamp } = _26, callEvent = __rest(_26, ["timestamp"]);
|
|
291
309
|
switch (callEvent.name) {
|
|
292
310
|
case CallEventType_1.CallEventType.CLIENT_JOINED: {
|
|
293
311
|
const lastJoined = this.joined;
|
|
@@ -673,8 +691,8 @@ class ObservedClient extends events_1.EventEmitter {
|
|
|
673
691
|
this.inboundVideoBitrate = 0;
|
|
674
692
|
let sumRttInMs = 0;
|
|
675
693
|
let anyPeerConnectionUsingTurn = false;
|
|
676
|
-
let minPcScore
|
|
677
|
-
let maxPcScore
|
|
694
|
+
let minPcScore;
|
|
695
|
+
let maxPcScore;
|
|
678
696
|
for (const peerConnection of this._peerConnections.values()) {
|
|
679
697
|
if (peerConnection.closed)
|
|
680
698
|
continue;
|
|
@@ -692,11 +710,15 @@ class ObservedClient extends events_1.EventEmitter {
|
|
|
692
710
|
this.availableOutgoingBitrate += (_24 = peerConnection.availableOutgoingBitrate) !== null && _24 !== void 0 ? _24 : 0;
|
|
693
711
|
sumRttInMs += (_25 = peerConnection.avgRttInMs) !== null && _25 !== void 0 ? _25 : 0;
|
|
694
712
|
anyPeerConnectionUsingTurn || (anyPeerConnectionUsingTurn = peerConnection.usingTURN);
|
|
695
|
-
|
|
696
|
-
|
|
713
|
+
if (peerConnection.score) {
|
|
714
|
+
if (minPcScore === undefined || peerConnection.score.score < minPcScore)
|
|
715
|
+
minPcScore = peerConnection.score.score;
|
|
716
|
+
if (maxPcScore === undefined || peerConnection.score.score > maxPcScore)
|
|
717
|
+
maxPcScore = peerConnection.score.score;
|
|
718
|
+
}
|
|
697
719
|
}
|
|
698
720
|
this.score = {
|
|
699
|
-
score: minPcScore,
|
|
721
|
+
score: minPcScore !== null && minPcScore !== void 0 ? minPcScore : -1,
|
|
700
722
|
remarks: [{
|
|
701
723
|
severity: 'none',
|
|
702
724
|
text: `Min and max score of all peer connections: ${minPcScore}, ${maxPcScore}`,
|
|
@@ -46,6 +46,7 @@ export declare class ObservedPeerConnection extends EventEmitter {
|
|
|
46
46
|
closedTimestamp?: number;
|
|
47
47
|
private _elapsedTimeSinceLastUpdate?;
|
|
48
48
|
private _statsTimestamp?;
|
|
49
|
+
private _stabilityScores;
|
|
49
50
|
ωpendingIssuesForScores: ClientIssue[];
|
|
50
51
|
score?: CalculatedScore;
|
|
51
52
|
totalInboundPacketsLost: number;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ObservedPeerConnection.d.ts","sourceRoot":"","sources":["../src/ObservedPeerConnection.ts"],"names":[],"mappings":";AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,QAAQ,CAAC;AACtC,OAAO,EAAE,uBAAuB,EAAE,MAAM,+BAA+B,CAAC;AACxE,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,EAAE,eAAe,EAAiC,MAAM,+BAA+B,CAAC;AAC/F,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAC5C,OAAO,EAAE,mBAAmB,EAAE,MAAM,uBAAuB,CAAC;AAC5D,OAAO,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAC3C,OAAO,EAAE,yBAAyB,EAAE,8BAA8B,EAAE,MAAM,6BAA6B,CAAC;AACxG,OAAO,EAAE,yBAAyB,EAAE,8BAA8B,EAAE,MAAM,6BAA6B,CAAC;AACxG,OAAO,EAAE,0BAA0B,EAAE,+BAA+B,EAAE,MAAM,8BAA8B,CAAC;AAC3G,OAAO,EAAE,0BAA0B,EAAE,+BAA+B,EAAE,MAAM,8BAA8B,CAAC;AAC3G,OAAO,EAAE,eAAe,
|
|
1
|
+
{"version":3,"file":"ObservedPeerConnection.d.ts","sourceRoot":"","sources":["../src/ObservedPeerConnection.ts"],"names":[],"mappings":"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"}
|
|
@@ -16,6 +16,7 @@ class ObservedPeerConnection extends events_1.EventEmitter {
|
|
|
16
16
|
this.client = client;
|
|
17
17
|
this.created = Date.now();
|
|
18
18
|
this.visited = true;
|
|
19
|
+
this._stabilityScores = [];
|
|
19
20
|
this.ωpendingIssuesForScores = [];
|
|
20
21
|
this.totalInboundPacketsLost = 0;
|
|
21
22
|
this.totalInboundPacketsReceived = 0;
|
|
@@ -352,31 +353,51 @@ class ObservedPeerConnection extends events_1.EventEmitter {
|
|
|
352
353
|
this._updateQualityScore(trackScores);
|
|
353
354
|
}
|
|
354
355
|
_updateQualityScore(trackScores) {
|
|
355
|
-
var _a, _b, _c, _d;
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
356
|
+
var _a, _b, _c, _d, _e, _f, _g;
|
|
357
|
+
// Packet Jitter measured in seconds
|
|
358
|
+
// we use RTT and lost packets to calculate the base score for the connection
|
|
359
|
+
const rttInMs = (_a = this.avgRttInMs) !== null && _a !== void 0 ? _a : 0;
|
|
360
|
+
const latencyFactor = rttInMs < 150 ? 1.0 : (0, CalculatedScore_1.getRttScore)(rttInMs);
|
|
361
|
+
const totalPackets = Math.max(1, ((_b = this.totalInboundPacketsReceived) !== null && _b !== void 0 ? _b : 0) + ((_c = this.totalOutboundPacketsSent) !== null && _c !== void 0 ? _c : 0));
|
|
362
|
+
const lostPackets = ((_d = this.totalInboundPacketsLost) !== null && _d !== void 0 ? _d : 0) + ((_e = this.deltaOutboundPacketsSent) !== null && _e !== void 0 ? _e : 0);
|
|
363
|
+
const deliveryFactor = 1.0 - ((lostPackets) / (lostPackets + totalPackets));
|
|
364
|
+
// let's push the actual stability score
|
|
365
|
+
const stabilityScore = Math.pow(((latencyFactor * 0.5) + (deliveryFactor * 0.5)), 2);
|
|
366
|
+
this._stabilityScores.push(stabilityScore);
|
|
367
|
+
if (10 < this._stabilityScores.length) {
|
|
368
|
+
this._stabilityScores.shift();
|
|
369
|
+
}
|
|
370
|
+
else if (this._stabilityScores.length < 5) {
|
|
371
|
+
return;
|
|
372
|
+
}
|
|
373
|
+
let counter = 0;
|
|
374
|
+
let weight = 0;
|
|
375
|
+
let totalScore = 0;
|
|
376
|
+
for (const score of this._stabilityScores) {
|
|
377
|
+
weight += 1;
|
|
378
|
+
counter += weight;
|
|
379
|
+
totalScore += weight * score;
|
|
380
|
+
}
|
|
381
|
+
const weightedStabilityScore = totalScore / counter;
|
|
382
|
+
let sumTrackScores = 0;
|
|
383
|
+
for (const trackScore of trackScores) {
|
|
384
|
+
sumTrackScores += trackScore.score;
|
|
385
|
+
}
|
|
386
|
+
const avgTrackScores = sumTrackScores / trackScores.length;
|
|
361
387
|
const score = {
|
|
362
388
|
remarks: [{
|
|
363
389
|
severity: 'none',
|
|
364
|
-
text: `
|
|
390
|
+
text: `Peer Connection stability score: ${weightedStabilityScore}`,
|
|
391
|
+
},
|
|
392
|
+
{
|
|
393
|
+
severity: 'none',
|
|
394
|
+
text: `Avg. Track score: ${avgTrackScores}`,
|
|
365
395
|
}],
|
|
366
|
-
score:
|
|
367
|
-
timestamp: (
|
|
396
|
+
score: Math.floor((weightedStabilityScore + avgTrackScores) * 5),
|
|
397
|
+
timestamp: (_f = this._statsTimestamp) !== null && _f !== void 0 ? _f : Date.now(),
|
|
368
398
|
};
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
sumTrackScores += trackScore.score;
|
|
372
|
-
}
|
|
373
|
-
score.score += sumTrackScores / trackScores.length;
|
|
374
|
-
score.remarks.push({
|
|
375
|
-
severity: 'none',
|
|
376
|
-
text: `Track scores: ${sumTrackScores / trackScores.length}`,
|
|
377
|
-
});
|
|
378
|
-
for (const pendingScore of this.ωpendingIssuesForScores) {
|
|
379
|
-
switch (pendingScore.severity) {
|
|
399
|
+
for (const pendingIssue of this.ωpendingIssuesForScores) {
|
|
400
|
+
switch (pendingIssue.severity) {
|
|
380
401
|
case 'critical':
|
|
381
402
|
score.score = 0.0;
|
|
382
403
|
break;
|
|
@@ -388,8 +409,8 @@ class ObservedPeerConnection extends events_1.EventEmitter {
|
|
|
388
409
|
break;
|
|
389
410
|
}
|
|
390
411
|
score.remarks.push({
|
|
391
|
-
severity:
|
|
392
|
-
text: (
|
|
412
|
+
severity: pendingIssue.severity,
|
|
413
|
+
text: (_g = pendingIssue.description) !== null && _g !== void 0 ? _g : 'Issue occurred',
|
|
393
414
|
});
|
|
394
415
|
}
|
|
395
416
|
this.ωpendingIssuesForScores = [];
|
package/lib/Observer.js
CHANGED
|
@@ -64,7 +64,6 @@ class Observer extends events_1.EventEmitter {
|
|
|
64
64
|
this.reports.on('reports', onReports);
|
|
65
65
|
}
|
|
66
66
|
createObservedCall(config) {
|
|
67
|
-
var _a;
|
|
68
67
|
if (this._closed) {
|
|
69
68
|
throw new Error('Attempted to create a call source on a closed observer');
|
|
70
69
|
}
|
|
@@ -77,10 +76,10 @@ class Observer extends events_1.EventEmitter {
|
|
|
77
76
|
call.once('close', () => {
|
|
78
77
|
var _a;
|
|
79
78
|
this._observedCalls.delete(call.callId);
|
|
80
|
-
reportCallEnded && this.reports.addCallEventReport((0, callEventReports_1.createCallEndedEventReport)(call.serviceId, call.roomId, call.callId, (_a = call.
|
|
79
|
+
reportCallEnded && this.reports.addCallEventReport((0, callEventReports_1.createCallEndedEventReport)(call.serviceId, call.roomId, call.callId, (_a = call.observationEnded) !== null && _a !== void 0 ? _a : Date.now()));
|
|
81
80
|
});
|
|
82
81
|
this._observedCalls.set(call.callId, call);
|
|
83
|
-
reportCallStarted && this.reports.addCallEventReport((0, callEventReports_1.createCallStartedEventReport)(call.serviceId, call.roomId, call.callId,
|
|
82
|
+
reportCallStarted && this.reports.addCallEventReport((0, callEventReports_1.createCallStartedEventReport)(call.serviceId, call.roomId, call.callId, call.observationStarted));
|
|
84
83
|
this.emit('newcall', call);
|
|
85
84
|
return call;
|
|
86
85
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CalculatedScore.d.ts","sourceRoot":"","sources":["../../src/common/CalculatedScore.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAC;AACtD,OAAO,EAAE,yBAAyB,EAAE,MAAM,8BAA8B,CAAC;AACzE,OAAO,EAAE,yBAAyB,EAAE,MAAM,8BAA8B,CAAC;AACzE,OAAO,EAAE,0BAA0B,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,0BAA0B,EAAE,MAAM,+BAA+B,CAAC;AAE3E,MAAM,MAAM,iBAAiB,GAAG;IAC/B,QAAQ,EAAE,MAAM,GAAG,OAAO,GAAG,OAAO,GAAG,UAAU,CAAC;IAClD,IAAI,EAAE,MAAM,CAAC;CACb,CAAA;AAED,MAAM,MAAM,eAAe,GAAG;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,iBAAiB,EAAE,CAAC;IAC7B,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB,CAAA;AAmBD,eAAO,MAAM,UAAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAmBtB,CAAC;AAEF,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,yBAAyB,GAAG,0BAA0B,EAAE,SAAS,EAAE,WAAW,EAAE,GAAG,eAAe,GAAG,SAAS,CAiE5J;AAED,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,yBAAyB,GAAG,0BAA0B,EAAE,SAAS,EAAE,WAAW,EAAE,GAAG,eAAe,GAAG,SAAS,CA0C5J;AAED,wBAAgB,mBAAmB,CAClC,EAAE,SAAS,EAAE,OAAO,EAAE,WAAW,EAAE,EACnC;IAAE,SAAS,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,GACzD,MAAM,CASR"}
|
|
1
|
+
{"version":3,"file":"CalculatedScore.d.ts","sourceRoot":"","sources":["../../src/common/CalculatedScore.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAC;AACtD,OAAO,EAAE,yBAAyB,EAAE,MAAM,8BAA8B,CAAC;AACzE,OAAO,EAAE,yBAAyB,EAAE,MAAM,8BAA8B,CAAC;AACzE,OAAO,EAAE,0BAA0B,EAAE,MAAM,+BAA+B,CAAC;AAC3E,OAAO,EAAE,0BAA0B,EAAE,MAAM,+BAA+B,CAAC;AAE3E,MAAM,MAAM,iBAAiB,GAAG;IAC/B,QAAQ,EAAE,MAAM,GAAG,OAAO,GAAG,OAAO,GAAG,UAAU,CAAC;IAClD,IAAI,EAAE,MAAM,CAAC;CACb,CAAA;AAED,MAAM,MAAM,eAAe,GAAG;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,iBAAiB,EAAE,CAAC;IAC7B,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB,CAAA;AAmBD,eAAO,MAAM,UAAU;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAmBtB,CAAC;AAEF,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,yBAAyB,GAAG,0BAA0B,EAAE,SAAS,EAAE,WAAW,EAAE,GAAG,eAAe,GAAG,SAAS,CAiE5J;AAED,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,yBAAyB,GAAG,0BAA0B,EAAE,SAAS,EAAE,WAAW,EAAE,GAAG,eAAe,GAAG,SAAS,CA0C5J;AAED,wBAAgB,mBAAmB,CAClC,EAAE,SAAS,EAAE,OAAO,EAAE,WAAW,EAAE,EACnC;IAAE,SAAS,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,GACzD,MAAM,CASR;AAED,wBAAgB,WAAW,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM,CAM7C"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.calculateLatencyMOS = exports.calculateBaseAudioScore = exports.calculateBaseVideoScore = exports.BPP_RANGES = void 0;
|
|
3
|
+
exports.getRttScore = exports.calculateLatencyMOS = exports.calculateBaseAudioScore = exports.calculateBaseVideoScore = exports.BPP_RANGES = void 0;
|
|
4
4
|
// every track calculates its own score and stores
|
|
5
5
|
// the latest CalculatedScore in a score property also emits as an event 'score'
|
|
6
6
|
// every peer connection collects the scores and calculates its own score based on RTT, and stores it in the score property similar to track
|
|
@@ -109,7 +109,7 @@ function calculateBaseAudioScore(track, newIssues) {
|
|
|
109
109
|
score.score = 1.0;
|
|
110
110
|
score.remarks.push({
|
|
111
111
|
severity: 'none',
|
|
112
|
-
text: 'Bitrate is too low for audio',
|
|
112
|
+
text: 'Bitrate is too low for good quality audio',
|
|
113
113
|
});
|
|
114
114
|
}
|
|
115
115
|
else if (track.bitrate < 16000) {
|
|
@@ -153,3 +153,10 @@ function calculateLatencyMOS({ avgJitter, rttInMs, packetsLoss }) {
|
|
|
153
153
|
return 1 + ((0.035) * rFactor) + ((0.000007) * rFactor * (rFactor - 60) * (100 - rFactor));
|
|
154
154
|
}
|
|
155
155
|
exports.calculateLatencyMOS = calculateLatencyMOS;
|
|
156
|
+
function getRttScore(x) {
|
|
157
|
+
// logarithmic version: 1.0 at 150 and 0.1 at 300
|
|
158
|
+
return (-1.2984 * Math.log(x)) + 7.5059;
|
|
159
|
+
// exponential version: 1.0 at 150 and 0.1 at 300
|
|
160
|
+
// return Math.exp(-0.01536 * x);
|
|
161
|
+
}
|
|
162
|
+
exports.getRttScore = getRttScore;
|
package/package.json
CHANGED
package/src/ObservedCall.ts
CHANGED
|
@@ -46,9 +46,14 @@ export class ObservedCall<AppData extends Record<string, unknown> = Record<strin
|
|
|
46
46
|
public readonly sfuStreamIdToOutboundAudioTrack = new Map<string | number, ObservedOutboundAudioTrack>();
|
|
47
47
|
public readonly sfuStreamIdToOutboundVideoTrack = new Map<string | number, ObservedOutboundVideoTrack>();
|
|
48
48
|
private _closed = false;
|
|
49
|
-
|
|
49
|
+
// this changes as clients emitting their joined event, as the call starts when the first client joins
|
|
50
|
+
public started?: number;
|
|
51
|
+
// this changes as clients emitting their left event, as the call ends when the last client leaves
|
|
50
52
|
public ended?: number;
|
|
51
|
-
|
|
53
|
+
|
|
54
|
+
public observationUpdated = Date.now();
|
|
55
|
+
public observationEnded?: number;
|
|
56
|
+
public readonly observationStarted = Date.now();
|
|
52
57
|
|
|
53
58
|
public constructor(
|
|
54
59
|
private readonly _model: ObservedCallModel,
|
|
@@ -78,10 +83,6 @@ export class ObservedCall<AppData extends Record<string, unknown> = Record<strin
|
|
|
78
83
|
return this._model.callId!;
|
|
79
84
|
}
|
|
80
85
|
|
|
81
|
-
public get updated() {
|
|
82
|
-
return this._updated;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
86
|
public get clients(): ReadonlyMap<string, ObservedClient> {
|
|
86
87
|
return this._clients;
|
|
87
88
|
}
|
|
@@ -119,17 +120,13 @@ export class ObservedCall<AppData extends Record<string, unknown> = Record<strin
|
|
|
119
120
|
return this._closed;
|
|
120
121
|
}
|
|
121
122
|
|
|
122
|
-
public close(
|
|
123
|
+
public close() {
|
|
123
124
|
if (this._closed) return;
|
|
124
125
|
this._closed = true;
|
|
125
126
|
|
|
126
|
-
if (timestamp) {
|
|
127
|
-
this.ended = timestamp;
|
|
128
|
-
} else if (!this.ended) {
|
|
129
|
-
this.ended = Date.now();
|
|
130
|
-
}
|
|
131
|
-
|
|
132
127
|
Array.from(this._clients.values()).forEach((client) => client.close());
|
|
128
|
+
|
|
129
|
+
this.observationEnded = Date.now();
|
|
133
130
|
|
|
134
131
|
this.emit('close');
|
|
135
132
|
}
|
|
@@ -165,7 +162,18 @@ export class ObservedCall<AppData extends Record<string, unknown> = Record<strin
|
|
|
165
162
|
|
|
166
163
|
const result = new ObservedClient(model, this, appData);
|
|
167
164
|
const onUpdate = ({ sample }: { sample: ClientSample }) => {
|
|
168
|
-
this.
|
|
165
|
+
this.observationUpdated = Date.now();
|
|
166
|
+
if (result.joined) {
|
|
167
|
+
if (this.started === undefined || result.joined < this.started) {
|
|
168
|
+
this.started = result.joined;
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
if (result.left) {
|
|
172
|
+
if (this.ended === undefined || result.left > this.ended) {
|
|
173
|
+
this.ended = result.left;
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
|
|
169
177
|
this.emit('update');
|
|
170
178
|
|
|
171
179
|
this.processor.process(sample);
|
package/src/ObservedClient.ts
CHANGED
|
@@ -35,6 +35,8 @@ export type ObservedClientEvents = {
|
|
|
35
35
|
elapsedTimeInMs: number,
|
|
36
36
|
}],
|
|
37
37
|
close: [],
|
|
38
|
+
joined: [],
|
|
39
|
+
left: [],
|
|
38
40
|
newpeerconnection: [ObservedPeerConnection],
|
|
39
41
|
iceconnectionstatechange: [{
|
|
40
42
|
peerConnection: ObservedPeerConnection,
|
|
@@ -97,8 +99,8 @@ export class ObservedClient<AppData extends Record<string, unknown> = Record<str
|
|
|
97
99
|
private _timeZoneOffsetInHours?: number;
|
|
98
100
|
|
|
99
101
|
// the timestamp of the CLIENT_JOINED event
|
|
100
|
-
|
|
101
|
-
|
|
102
|
+
private _joined?: number;
|
|
103
|
+
private _left?: number;
|
|
102
104
|
public lastStatsTimestamp?: number;
|
|
103
105
|
|
|
104
106
|
public score?: CalculatedScore;
|
|
@@ -159,6 +161,30 @@ export class ObservedClient<AppData extends Record<string, unknown> = Record<str
|
|
|
159
161
|
return sfu as ObservedSfu<T>;
|
|
160
162
|
}
|
|
161
163
|
|
|
164
|
+
public get joined() {
|
|
165
|
+
return this._joined;
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
public set joined(value: number | undefined) {
|
|
169
|
+
this._joined = value;
|
|
170
|
+
|
|
171
|
+
if (this._joined) {
|
|
172
|
+
this.emit('joined');
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
public get left() {
|
|
177
|
+
return this._left;
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
public set left(value: number | undefined) {
|
|
181
|
+
this._left = value;
|
|
182
|
+
|
|
183
|
+
if (this._left) {
|
|
184
|
+
this.emit('left');
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
|
|
162
188
|
public get sfu(): ObservedSfu | undefined {
|
|
163
189
|
if (!this.sfuId) return;
|
|
164
190
|
|
|
@@ -1018,8 +1044,8 @@ export class ObservedClient<AppData extends Record<string, unknown> = Record<str
|
|
|
1018
1044
|
let sumRttInMs = 0;
|
|
1019
1045
|
let anyPeerConnectionUsingTurn = false;
|
|
1020
1046
|
|
|
1021
|
-
let minPcScore
|
|
1022
|
-
let maxPcScore
|
|
1047
|
+
let minPcScore: number | undefined;
|
|
1048
|
+
let maxPcScore: number | undefined;
|
|
1023
1049
|
|
|
1024
1050
|
for (const peerConnection of this._peerConnections.values()) {
|
|
1025
1051
|
if (peerConnection.closed) continue;
|
|
@@ -1041,12 +1067,14 @@ export class ObservedClient<AppData extends Record<string, unknown> = Record<str
|
|
|
1041
1067
|
|
|
1042
1068
|
anyPeerConnectionUsingTurn ||= peerConnection.usingTURN;
|
|
1043
1069
|
|
|
1044
|
-
|
|
1045
|
-
|
|
1070
|
+
if (peerConnection.score) {
|
|
1071
|
+
if (minPcScore === undefined || peerConnection.score.score < minPcScore) minPcScore = peerConnection.score.score;
|
|
1072
|
+
if (maxPcScore === undefined || peerConnection.score.score > maxPcScore) maxPcScore = peerConnection.score.score;
|
|
1073
|
+
}
|
|
1046
1074
|
}
|
|
1047
1075
|
|
|
1048
1076
|
this.score = {
|
|
1049
|
-
score: minPcScore,
|
|
1077
|
+
score: minPcScore ?? -1,
|
|
1050
1078
|
remarks: [ {
|
|
1051
1079
|
severity: 'none',
|
|
1052
1080
|
text: `Min and max score of all peer connections: ${minPcScore}, ${maxPcScore}`,
|
|
@@ -9,7 +9,7 @@ import { ObservedInboundAudioTrack, ObservedInboundAudioTrackModel } from './Obs
|
|
|
9
9
|
import { ObservedInboundVideoTrack, ObservedInboundVideoTrackModel } from './ObservedInboundVideoTrack';
|
|
10
10
|
import { ObservedOutboundAudioTrack, ObservedOutboundAudioTrackModel } from './ObservedOutboundAudioTrack';
|
|
11
11
|
import { ObservedOutboundVideoTrack, ObservedOutboundVideoTrackModel } from './ObservedOutboundVideoTrack';
|
|
12
|
-
import { CalculatedScore,
|
|
12
|
+
import { CalculatedScore, getRttScore } from './common/CalculatedScore';
|
|
13
13
|
import { ClientIssue } from './monitors/CallSummary';
|
|
14
14
|
|
|
15
15
|
export type ObservedPeerConnectionEvents = {
|
|
@@ -50,7 +50,8 @@ export class ObservedPeerConnection extends EventEmitter {
|
|
|
50
50
|
|
|
51
51
|
private _elapsedTimeSinceLastUpdate?: number;
|
|
52
52
|
private _statsTimestamp?: number;
|
|
53
|
-
|
|
53
|
+
private _stabilityScores: number[] = [];
|
|
54
|
+
|
|
54
55
|
public ωpendingIssuesForScores: ClientIssue[] = [];
|
|
55
56
|
|
|
56
57
|
public score?: CalculatedScore;
|
|
@@ -499,34 +500,55 @@ export class ObservedPeerConnection extends EventEmitter {
|
|
|
499
500
|
}
|
|
500
501
|
|
|
501
502
|
private _updateQualityScore(trackScores: CalculatedScore[]) {
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
const
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
503
|
+
// Packet Jitter measured in seconds
|
|
504
|
+
// we use RTT and lost packets to calculate the base score for the connection
|
|
505
|
+
const rttInMs = this.avgRttInMs ?? 0;
|
|
506
|
+
const latencyFactor = rttInMs < 150 ? 1.0 : getRttScore(rttInMs);
|
|
507
|
+
const totalPackets = Math.max(1, (this.totalInboundPacketsReceived ?? 0) + (this.totalOutboundPacketsSent ?? 0));
|
|
508
|
+
const lostPackets = (this.totalInboundPacketsLost ?? 0) + (this.deltaOutboundPacketsSent ?? 0);
|
|
509
|
+
const deliveryFactor = 1.0 - ((lostPackets) / (lostPackets + totalPackets));
|
|
510
|
+
// let's push the actual stability score
|
|
511
|
+
const stabilityScore = ((latencyFactor * 0.5) + (deliveryFactor * 0.5)) ** 2;
|
|
512
|
+
|
|
513
|
+
this._stabilityScores.push(stabilityScore);
|
|
514
|
+
if (10 < this._stabilityScores.length) {
|
|
515
|
+
this._stabilityScores.shift();
|
|
516
|
+
} else if (this._stabilityScores.length < 5) {
|
|
517
|
+
return;
|
|
518
|
+
}
|
|
519
|
+
let counter = 0;
|
|
520
|
+
let weight = 0;
|
|
521
|
+
let totalScore = 0;
|
|
522
|
+
|
|
523
|
+
for (const score of this._stabilityScores) {
|
|
524
|
+
weight += 1;
|
|
525
|
+
counter += weight;
|
|
526
|
+
totalScore += weight * score;
|
|
527
|
+
}
|
|
528
|
+
const weightedStabilityScore = totalScore / counter;
|
|
516
529
|
let sumTrackScores = 0;
|
|
517
530
|
|
|
518
531
|
for (const trackScore of trackScores) {
|
|
519
532
|
sumTrackScores += trackScore.score;
|
|
520
533
|
}
|
|
521
534
|
|
|
522
|
-
|
|
523
|
-
score.remarks.push({
|
|
524
|
-
severity: 'none',
|
|
525
|
-
text: `Track scores: ${sumTrackScores / trackScores.length}`,
|
|
526
|
-
});
|
|
535
|
+
const avgTrackScores = sumTrackScores / trackScores.length;
|
|
527
536
|
|
|
528
|
-
|
|
529
|
-
|
|
537
|
+
const score: CalculatedScore = {
|
|
538
|
+
remarks: [ {
|
|
539
|
+
severity: 'none',
|
|
540
|
+
text: `Peer Connection stability score: ${weightedStabilityScore}`,
|
|
541
|
+
},
|
|
542
|
+
{
|
|
543
|
+
severity: 'none',
|
|
544
|
+
text: `Avg. Track score: ${avgTrackScores}`,
|
|
545
|
+
} ],
|
|
546
|
+
score: Math.floor((weightedStabilityScore + avgTrackScores) * 5),
|
|
547
|
+
timestamp: this._statsTimestamp ?? Date.now(),
|
|
548
|
+
};
|
|
549
|
+
|
|
550
|
+
for (const pendingIssue of this.ωpendingIssuesForScores) {
|
|
551
|
+
switch (pendingIssue.severity) {
|
|
530
552
|
case 'critical':
|
|
531
553
|
score.score = 0.0;
|
|
532
554
|
break;
|
|
@@ -538,10 +560,11 @@ export class ObservedPeerConnection extends EventEmitter {
|
|
|
538
560
|
break;
|
|
539
561
|
}
|
|
540
562
|
score.remarks.push({
|
|
541
|
-
severity:
|
|
542
|
-
text:
|
|
563
|
+
severity: pendingIssue.severity,
|
|
564
|
+
text: pendingIssue.description ?? 'Issue occurred',
|
|
543
565
|
});
|
|
544
566
|
}
|
|
567
|
+
|
|
545
568
|
this.ωpendingIssuesForScores = [];
|
|
546
569
|
this.score = score;
|
|
547
570
|
|
package/src/Observer.ts
CHANGED
|
@@ -130,7 +130,7 @@ export class Observer extends EventEmitter {
|
|
|
130
130
|
call.serviceId,
|
|
131
131
|
call.roomId,
|
|
132
132
|
call.callId,
|
|
133
|
-
call.
|
|
133
|
+
call.observationEnded ?? Date.now(),
|
|
134
134
|
));
|
|
135
135
|
});
|
|
136
136
|
|
|
@@ -139,7 +139,7 @@ export class Observer extends EventEmitter {
|
|
|
139
139
|
call.serviceId,
|
|
140
140
|
call.roomId,
|
|
141
141
|
call.callId,
|
|
142
|
-
call.
|
|
142
|
+
call.observationStarted,
|
|
143
143
|
));
|
|
144
144
|
|
|
145
145
|
this.emit('newcall', call);
|
|
@@ -132,7 +132,7 @@ export function calculateBaseAudioScore(track: ObservedInboundAudioTrack | Obser
|
|
|
132
132
|
score.score = 1.0;
|
|
133
133
|
score.remarks.push({
|
|
134
134
|
severity: 'none',
|
|
135
|
-
text: 'Bitrate is too low for audio',
|
|
135
|
+
text: 'Bitrate is too low for good quality audio',
|
|
136
136
|
});
|
|
137
137
|
} else if (track.bitrate < 16000) {
|
|
138
138
|
score.score = 2.8;
|
|
@@ -177,4 +177,12 @@ export function calculateLatencyMOS(
|
|
|
177
177
|
rFactor -= (packetsLoss * 2.5);
|
|
178
178
|
|
|
179
179
|
return 1 + ((0.035) * rFactor) + ((0.000007) * rFactor * (rFactor - 60) * (100 - rFactor));
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
export function getRttScore(x: number): number {
|
|
183
|
+
// logarithmic version: 1.0 at 150 and 0.1 at 300
|
|
184
|
+
return (-1.2984 * Math.log(x)) + 7.5059;
|
|
185
|
+
|
|
186
|
+
// exponential version: 1.0 at 150 and 0.1 at 300
|
|
187
|
+
// return Math.exp(-0.01536 * x);
|
|
180
188
|
}
|