feat: (for now android only!) method to get current call stats

This commit is contained in:
Andrew 2026-04-30 15:25:06 +07:00
parent 82c1a3f96c
commit 32789468a3
6 changed files with 412 additions and 0 deletions

View file

@ -259,6 +259,10 @@ class LiblinphoneFlutterPlugin : FlutterPlugin, ActivityAware, MethodCallHandler
result.success(linphoneBridge.getDscp().toMap())
}
"getCurrentCallStats" -> {
result.success(linphoneBridge.getCurrentCallStats()?.toMap())
}
else -> {
result.notImplemented()
}

View file

@ -9,6 +9,7 @@ import androidx.core.content.ContextCompat
import org.linphone.core.Account
import org.linphone.core.Call
import org.linphone.core.Core
import org.linphone.core.StreamType
import org.linphone.core.CoreListenerStub
import org.linphone.core.Factory
import org.linphone.core.MediaDirection
@ -413,4 +414,139 @@ class LinphoneBridge(
fun getDscp(): DscpValues {
return DscpValues(core.sipDscp, core.audioDscp, core.videoDscp)
}
data class CallStats(
val recordTs: Long,
val remoteAddress: String,
val currentQuality: Float,
val downloadBandwidth: Float,
val estimatedDownloadBandwidth: Float,
val fecCumulativeLostPacketsNumber: Int,
val fecDownloadBandwidth: Float,
val fecRepairedPacketsNumber: Int,
val fecUploadBandwidth: Float,
val iceState: String,
val jitterBufferSizeMs: Float,
val latePacketsCumulativeNumber: Int,
val localLateRate: Float,
val localLossRate: Float,
val receiverInterarrivalJitter: Float,
val receiverLossRate: Float,
val roundTripDelay: Float,
val rtcpDownloadBandwidth: Float,
val rtcpUploadBandwidth: Float,
val rtpCumPacketLoss: Int,
val rtpDiscarded: Int,
val rtpHwRecv: Int,
val rtpPacketRecv: Int,
val rtpPacketSent: Int,
val rtpRecv: Int,
val rtpSent: Int,
val senderInterarrivalJitter: Float,
val senderLossRate: Float,
val srtpSource: String,
val srtpSuite: String,
val uploadBandwidth: Float,
val upnpState: String,
val zrtpAuthTagAlgo: String,
val zrtpCipherAlgo: String,
val zrtpHashAlgo: String,
val zrtpKeyAgreementAlgo: String,
val zrtpSasAlgo: String,
val isZrtpKeyAgreementAlgoPostQuantum: Boolean,
) {
fun toMap(): Map<String, Any?> {
return mapOf(
"recordTs" to recordTs,
"remoteAddress" to remoteAddress,
"currentQuality" to currentQuality,
"downloadBandwidth" to downloadBandwidth,
"estimatedDownloadBandwidth" to estimatedDownloadBandwidth,
"fecCumulativeLostPacketsNumber" to fecCumulativeLostPacketsNumber,
"fecDownloadBandwidth" to fecDownloadBandwidth,
"fecRepairedPacketsNumber" to fecRepairedPacketsNumber,
"fecUploadBandwidth" to fecUploadBandwidth,
"iceState" to iceState,
"jitterBufferSizeMs" to jitterBufferSizeMs,
"latePacketsCumulativeNumber" to latePacketsCumulativeNumber,
"localLateRate" to localLateRate,
"localLossRate" to localLossRate,
"receiverInterarrivalJitter" to receiverInterarrivalJitter,
"receiverLossRate" to receiverLossRate,
"roundTripDelay" to roundTripDelay,
"rtcpDownloadBandwidth" to rtcpDownloadBandwidth,
"rtcpUploadBandwidth" to rtcpUploadBandwidth,
"rtpCumPacketLoss" to rtpCumPacketLoss,
"rtpDiscarded" to rtpDiscarded,
"rtpHwRecv" to rtpHwRecv,
"rtpPacketRecv" to rtpPacketRecv,
"rtpPacketSent" to rtpPacketSent,
"rtpRecv" to rtpRecv,
"rtpSent" to rtpSent,
"senderInterarrivalJitter" to senderInterarrivalJitter,
"senderLossRate" to senderLossRate,
"srtpSource" to srtpSource,
"srtpSuite" to srtpSuite,
"uploadBandwidth" to uploadBandwidth,
"upnpState" to upnpState,
"zrtpAuthTagAlgo" to zrtpAuthTagAlgo,
"zrtpCipherAlgo" to zrtpCipherAlgo,
"zrtpHashAlgo" to zrtpHashAlgo,
"zrtpKeyAgreementAlgo" to zrtpKeyAgreementAlgo,
"zrtpSasAlgo" to zrtpSasAlgo,
"isZrtpKeyAgreementAlgoPostQuantum" to isZrtpKeyAgreementAlgoPostQuantum,
);
}
}
fun getCurrentCallStats(): CallStats? {
val currentCall = core.currentCall
if (currentCall == null) return null
val stats = currentCall.getStats(StreamType.Audio)
if (stats == null) return null
val recordTs = System.currentTimeMillis()
return CallStats(
recordTs = recordTs,
remoteAddress = currentCall.remoteAddress.asString(),
currentQuality = currentCall.getCurrentQuality(),
downloadBandwidth = stats.downloadBandwidth,
estimatedDownloadBandwidth = stats.estimatedDownloadBandwidth,
fecCumulativeLostPacketsNumber = stats.fecCumulativeLostPacketsNumber,
fecDownloadBandwidth = stats.fecDownloadBandwidth,
fecRepairedPacketsNumber = stats.fecRepairedPacketsNumber,
fecUploadBandwidth = stats.fecUploadBandwidth,
iceState = stats.iceState.name,
jitterBufferSizeMs = stats.jitterBufferSizeMs,
latePacketsCumulativeNumber = stats.latePacketsCumulativeNumber,
localLateRate = stats.localLateRate,
localLossRate = stats.localLossRate,
receiverInterarrivalJitter = stats.receiverInterarrivalJitter,
receiverLossRate = stats.receiverLossRate,
roundTripDelay = stats.roundTripDelay,
rtcpDownloadBandwidth = stats.rtcpDownloadBandwidth,
rtcpUploadBandwidth = stats.rtcpUploadBandwidth,
rtpCumPacketLoss = stats.rtpCumPacketLoss,
rtpDiscarded = stats.rtpDiscarded,
rtpHwRecv = stats.rtpHwRecv,
rtpPacketRecv = stats.rtpPacketRecv,
rtpPacketSent = stats.rtpPacketSent,
rtpRecv = stats.rtpRecv,
rtpSent = stats.rtpSent,
senderInterarrivalJitter = stats.senderInterarrivalJitter,
senderLossRate = stats.senderLossRate,
srtpSource = stats.srtpSource.name,
srtpSuite = stats.srtpSuite.name,
uploadBandwidth = stats.uploadBandwidth,
upnpState = stats.upnpState.name,
zrtpAuthTagAlgo = stats.zrtpAuthTagAlgo,
zrtpCipherAlgo = stats.zrtpCipherAlgo,
zrtpHashAlgo = stats.zrtpHashAlgo,
zrtpKeyAgreementAlgo = stats.zrtpKeyAgreementAlgo,
zrtpSasAlgo = stats.zrtpSasAlgo,
isZrtpKeyAgreementAlgoPostQuantum = stats.isZrtpKeyAgreementAlgoPostQuantum(),
)
}
}