With Azure communication Calling library I tried to get network quality.
const { CallClient, VideoStreamRenderer, LocalVideoStream } = require('@azure/communication-calling');
const { AzureCommunicationTokenCredential } = require('@azure/communication-common');
const { AzureLogger, setLogLevel } = require("@azure/logger");
I tried this 2 codes but I have the same error "feature is not defined".
EDIT : I put feature's code in the subscribeToCall function.
Did I forget to import something?
EDIT FOR MORE DETAILS :
My function to subscribe a call when start or accept.
subscribeToCall = (call) => {
try {
// Subscribe to call's 'stateChanged' event for value changes.
call.on('stateChanged', async () => {
// If ringing / Connected / Disconnected ...
});
call.on('isLocalVideoStartedChanged', () => {
console.log(`------------- isLocalVideoStarted changed: ${call.isLocalVideoStarted}`);
});
call.localVideoStreams.forEach(async (lvs) => {
localVideoStream = lvs;
await displayLocalVideoStream();
});
call.on('localVideoStreamsUpdated', e => {
e.added.forEach(async (lvs) => {
localVideoStream = lvs;
await displayLocalVideoStream();
});
e.removed.forEach(lvs => {
removeLocalVideoStream();
});
});
call.remoteParticipants.forEach(remoteParticipant => {
subscribeToRemoteParticipant(remoteParticipant);
});
// Subscribe to the call's 'remoteParticipantsUpdated' event to be
// notified when new participants are added to the call or removed from the call.
call.on('remoteParticipantsUpdated', e => {
// Subscribe to new remote participants that are added to the call.
e.added.forEach(remoteParticipant => {
subscribeToRemoteParticipant(remoteParticipant)
});
// Unsubscribe from participants that are removed from the call
e.removed.forEach(remoteParticipant => {
console.log('Remote participant removed from the call.');
});
});
// CALL FEATURE TESTS ::::::::
// First example
/*const userFacingDiagnostics = call.feature(Features.UserFacingDiagnostics);
userFacingDiagnostics.media.on("diagnosticChanged", (diagnosticInfo) => {
console.log(diagnosticInfo);
});
userFacingDiagnostics.network.on("diagnosticChanged", (diagnosticInfo) => {
console.log(diagnosticInfo);
});*/
// Second example
/*call.feature(Features.UserFacingDiagnostics).network.on('diagnosticChanged', (diagnosticInfo) => {
if (diagnosticInfo.diagnostic === 'networkReceiveQuality') {
if (diagnosticInfo.value === DiagnosticQuality.Bad) {
console.log("Network quality = BAD");
} else if (diagnosticInfo.value === DiagnosticQuality.Poor) {
console.log("Network quality = POOR");
} else if (diagnosticInfo.value === DiagnosticQuality.Good) {
console.log("Network quality = GOOD");
}
}
});*/
} catch (error) {
console.error(error);
}
}
EDIT 2024/04/24
First example source link : Stackoverflow - Can't load Features.Diagnostics
Second example source link : networkReceiveQuality, UFD
The error "feature is not defined" indicates that the Features
object is not recognized within the scope of your code.
A features object should be used like this:
const callQualityApi = call.api(Features.Diagnostics);
callQualityApi.network.on('diagnosticChanged', diagnosticChangedListener);
callQualityApi.media.on('diagnosticChanged', diagnosticChangedListener);
To enable Call Diagnostics for your Azure Communication Services Resource, follow these steps:
Once you've set up Diagnostic Settings, you can access Call Diagnostics from any Azure Communication Services Resource in your Azure portal.
The sample code below is Azure Communication Services calling SDK in Node.js to set up event handlers and listeners for various call and network diagnostic events. It checks for DiagnosticQuality.Bad
, DiagnosticQuality.Poor
, and DiagnosticQuality.Good
.
const { CallClient, VideoStreamRenderer, LocalVideoStream, Features } = require('@azure/communication-calling');
const { AzureCommunicationTokenCredential } = require('@azure/communication-common');
const { AzureLogger, setLogLevel } = require("@azure/logger");
const subscribeToCall = (call) => {
try {
call.on('stateChanged', async () => {
// If ringing / Connected / Disconnected ...
});
call.on('isLocalVideoStartedChanged', () => {
console.log(`------------- isLocalVideoStarted changed: ${call.isLocalVideoStarted}`);
});
call.localVideoStreams.forEach(async (lvs) => {
localVideoStream = lvs;
await displayLocalVideoStream();
});
call.on('localVideoStreamsUpdated', e => {
e.added.forEach(async (lvs) => {
localVideoStream = lvs;
await displayLocalVideoStream();
});
e.removed.forEach(lvs => {
removeLocalVideoStream();
});
});
call.remoteParticipants.forEach(remoteParticipant => {
subscribeToRemoteParticipant(remoteParticipant);
});
call.on('remoteParticipantsUpdated', e => {
e.added.forEach(remoteParticipant => {
subscribeToRemoteParticipant(remoteParticipant)
});
e.removed.forEach(remoteParticipant => {
console.log('Remote participant removed from the call.');
});
});
call.api(Features.Diagnostics).network.on('diagnosticChanged', (diagnosticInfo) => {
console.log(diagnosticInfo);
});
call.api(Features.UserFacingDiagnostics).network.on('diagnosticChanged', (diagnosticInfo) => {
if (diagnosticInfo.diagnostic === 'networkReceiveQuality') {
if (diagnosticInfo.value === DiagnosticQuality.Bad) {
console.log("Network quality = BAD");
} else if (diagnosticInfo.value === DiagnosticQuality.Poor) {
console.log("Network quality = POOR");
} else if (diagnosticInfo.value === DiagnosticQuality.Good) {
console.log("Network quality = GOOD");
}
}
});
} catch (error) {
console.error(error);
}
}