Skip to main content
Version: 0.x.x

Monitoring Transport Stats - React

The getTransportStats() method lets you read a participant's transport-level stats — how much media data is flowing in and out over their transport. It returns the outgoing (uplink) and incoming (downlink) bitrate in kilobits per second (kbps), along with the total bytes sent and received over the transport.

Unlike per-track stats, which describe individual audio or video quality, transport stats describe the pipe itself — the aggregate throughput of the connection. This makes it a lightweight signal for showing connection indicators and detecting network degradation. It can be called for both the local participant and any remote participant.

It is available from the useParticipant hook.

Why It Matters

A participant's call experience depends heavily on how much data their network can move. With getTransportStats() you can:

  • Show a connection indicator (good / fair / poor) next to each participant.
  • Catch problems early — when a participant's bitrate drops sharply, it often signals trouble before their video or audio actually breaks up.
  • React automatically — for example, suggest switching to audio-only when a participant's connection weakens.
  • Track data usage with the running totals of bytes sent and received.

Return Value

getTransportStats() returns a Promise that resolves to an object with two groups — send (the data the participant is uploading) and receive (the data the participant is downloading).

{
send: {
outgoingBitrate: number | null, // current upload rate, in kbps
totalSentBytes: number | null, // total data sent so far, in bytes
},
receive: {
incomingBitrate: number | null, // current download rate, in kbps
totalReceivedBytes: number | null, // total data received so far, in bytes
},
}
FieldUnitDescription
send.outgoingBitratekbpsAggregate send bitrate across all outbound media streams.
send.totalSentBytesbytesCumulative bytes sent by the participant.
receive.incomingBitratekbpsAggregate receive bitrate across all inbound media streams.
receive.totalReceivedBytesbytesCumulative bytes received by the participant.
note

This method returns a snapshot taken at the moment you call it — it is not an event you subscribe to. To keep your UI up to date, call it on a short interval.

Example Usage

Get getTransportStats() from the useParticipant hook by passing the participantId. It works for both the local participant and any remote participant.

import { useParticipant } from "@videosdk.live/react-sdk";

function ParticipantConnection({ participantId }) {
const { getTransportStats } = useParticipant(participantId);

const logStats = async () => {
const stats = await getTransportStats();
// {
// send: { outgoingBitrate: 850, totalSentBytes: 10485760 },
// receive: { incomingBitrate: 1200, totalReceivedBytes: 20971520 },
// }
console.log(stats);
};

// ...
}

Polling for live updates

Because each call returns a one-time snapshot, you poll the method to keep your UI current. Run the loop inside a useEffect so it starts when the component mounts and stops when it unmounts. Instead of a fixed setInterval, fire the next request only after the previous one resolves — this avoids overlapping calls when the network is slow.

import { useEffect, useState } from "react";
import { useParticipant } from "@videosdk.live/react-sdk";

function ParticipantConnection({ participantId }) {
const { getTransportStats } = useParticipant(participantId);
const [bitrate, setBitrate] = useState({ up: 0, down: 0 });

useEffect(() => {
let active = true;

const pollTransportStats = async () => {
while (active) {
try {
const stats = await getTransportStats();
if (active && stats) {
setBitrate({
up: stats.send.outgoingBitrate ?? 0,
down: stats.receive.incomingBitrate ?? 0,
});
}
} catch (err) {
console.error("getTransportStats error", participantId, err);
}

// Wait 1s after each result before firing the next request
await new Promise((resolve) => setTimeout(resolve, 1000));
}
};

pollTransportStats();

// Stop the loop when the component unmounts
return () => {
active = false;
};
}, [getTransportStats, participantId]);

return (
<div>
{bitrate.up} kbps &nbsp; ↓ {bitrate.down} kbps
</div>
);
}
caution

Right after a participant joins — before they start sending or receiving any media — the bitrate and byte values may come back as 0 or null. Treat these as "no data yet" rather than a real measurement, and default them to 0 in your UI as shown above.

API Reference

The API references for all the methods utilized in this guide are provided below.

Got a Question? Ask us on discord