Signatur
Beschreibung
Die Eigenschaft remoteCertificateId eines RTCTransportStats-Objekts (Typ "transport") ist ein String. Er verweist auf das RTCCertificateStats-Objekt im selben RTCStatsReport, das das Zertifikat der entfernten Gegenstelle beschreibt. Dieses Zertifikat hat die Gegenstelle beim DTLS-Handshake über den zugehörigen RTCIceTransport bzw. RTCDtlsTransport vorgelegt.
Die ID ist nur ein Verweis und enthält das Zertifikat nicht selbst. Um an die Details zu kommen, schlägt man sie im Bericht nach, z. B. mit report.get(stats.remoteCertificateId). Das Ergebnis liefert unter anderem fingerprint, fingerprintAlgorithm und base64Certificate. So lässt sich etwa prüfen, ob der Fingerabdruck der Gegenstelle mit dem Wert aus der SDP (a=fingerprint) übereinstimmt. Das hilft auch beim Aufspüren von Sicherheitsproblemen und bei der Protokollierung.
Das Gegenstück ist localCertificateId. Es verweist auf das eigene Zertifikat. Beide Eigenschaften sind erst gesetzt, wenn der DTLS-Handshake erfolgreich war, also wenn dtlsState den Wert "connected" hat.
Rückgabewert
RTCCertificateStats-Eintrags im selben RTCStatsReport. Ist noch keine DTLS-Verbindung aufgebaut, fehlt die Eigenschaft (undefined).Beispiele
ID des entfernten Zertifikats auslesen
// pc ist eine bestehende, verbundene RTCPeerConnection
const report = await pc.getStats();
for (const stats of report.values()) {
if (stats.type === 'transport') {
console.log('DTLS-Zustand:', stats.dtlsState);
console.log('Remote-Zertifikat-ID:', stats.remoteCertificateId);
}
}
Fingerabdruck der Gegenstelle ermitteln
const getRemoteFingerprint = async (pc) => {
const report = await pc.getStats();
const transport = [...report.values()].find((s) => s.type === 'transport');
if (!transport?.remoteCertificateId) {
return null; // DTLS noch nicht verbunden
}
const cert = report.get(transport.remoteCertificateId);
return `${cert.fingerprintAlgorithm} ${cert.fingerprint}`;
};
console.log(await getRemoteFingerprint(pc));
Fingerabdruck mit der Remote-SDP abgleichen
const verifyRemoteFingerprint = async (pc) => {
const report = await pc.getStats();
const transport = [...report.values()].find((s) => s.type === 'transport');
const cert = transport?.remoteCertificateId
? report.get(transport.remoteCertificateId)
: undefined;
if (!cert) return false;
// Fingerabdruck aus der SDP der Gegenstelle lesen
const match = pc.remoteDescription?.sdp.match(/a=fingerprint:(\S+) (\S+)/);
if (!match) return false;
return match[1].toLowerCase() === cert.fingerprintAlgorithm.toLowerCase()
&& match[2].toUpperCase() === cert.fingerprint.toUpperCase();
};
console.log('Fingerabdruck stimmt:', await verifyRemoteFingerprint(pc));
// Wichtig · Fallstricke
- Erst nach dem DTLS-Handshake verfügbar: Vorher (bei
dtlsStategleich"new"oder"connecting") fehlt die Eigenschaft. Prüfe daher immer aufundefined. - Die ID ist undurchsichtig: Ihr Format hängt vom Browser ab und kann sich zwischen zwei
getStats()-Aufrufen ändern. Verwende sie nur innerhalb desselben Berichts fürreport.get(). - Zertifikatsketten: Das referenzierte
RTCCertificateStatskann überissuerCertificateIdauf weitere Zertifikate verweisen. - Datenschutz:
base64Certificateenthält das vollständige Zertifikat der Gegenstelle. Übertrage es nicht ungeprüft an Telemetrie-Server. - Kompatibilität: Chromium-Browser unterstützen die Eigenschaft schon lange. In Firefox und Safari kam sie erst in neueren Versionen hinzu. Bei Bundling mehrerer Medien über einen Transport gibt es meist nur einen
transport-Eintrag.