WebRTC - API RTCPeerConnection
L'API RTCPeerConnection est le cœur de la connexion peer-to-peer entre chacun des navigateurs. Pour créer les objets RTCPeerConnection, écrivez simplement
var pc = RTCPeerConnection(config);
où l' argument config contient au moins une clé, iceServers. Il s'agit d'un tableau d'objets URL contenant des informations sur les serveurs STUN et TURN, utilisés lors de la recherche des candidats ICE. Vous pouvez trouver une liste des serveurs STUN publics disponibles sur code.google.com
Selon que vous êtes l'appelant ou l'appelé, l'objet RTCPeerConnection est utilisé d'une manière légèrement différente de chaque côté de la connexion.
Voici un exemple du flux de l'utilisateur -
Enregistrez le gestionnaire onicecandidate . Il envoie tous les candidats ICE à l'autre pair, au fur et à mesure qu'ils sont reçus.
Enregistrez le gestionnaire onaddstream . Il gère l'affichage du flux vidéo une fois qu'il est reçu du pair distant.
Enregistrez le gestionnaire de messages . Votre serveur de signalisation doit également avoir un gestionnaire pour les messages reçus de l'autre pair. Si le message contient l' objet RTCSessionDescription , il doit être ajouté à l' objet RTCPeerConnection à l'aide de la méthode setRemoteDescription () . Si le message contient l' objet RTCIceCandidate , il doit être ajouté à l' objet RTCPeerConnection à l'aide de la méthode addIceCandidate () .
Utilisez getUserMedia () pour configurer votre flux multimédia local et ajoutez-le à l' objet RTCPeerConnection à l'aide de la méthode addStream () .
Démarrez le processus de négociation offre / réponse. C'est la seule étape où le flux de l'appelant est différent de celui de l'appelé. L'appelant démarre la négociation à l'aide de la méthode createOffer () et enregistre un rappel qui reçoit l' objet RTCSessionDescription . Ensuite , ce rappel devrait ajouter cette RTCSessionDescription objet à votre RTCPeerConnection objet à l' aide setLocalDescription () . Et enfin, l'appelant doit envoyer cette RTCSessionDescription à l'homologue distant en utilisant le serveur de signalisation. L'appelé, d'autre part, enregistre le même rappel, mais dans la méthode createAnswer () . Notez que le flux de l'appelé est lancé uniquement après la réception de l'offre de l'appelant.
API RTCPeerConnection
Propriétés
RTCPeerConnection.iceConnectionState (read only)- Renvoie une énumération RTCIceConnectionState qui décrit l'état de la connexion. Un événement iceconnectionstatechange est déclenché lorsque cette valeur change. Les valeurs possibles -
new - l'agent ICE attend des candidats distants ou recueille des adresses
checking - l'agent ICE a des candidats distants, mais il n'a pas encore trouvé de connexion
connected - l'agent ICE a trouvé une connexion utilisable, mais vérifie toujours un candidat plus distant pour une meilleure connexion.
completed - l'agent ICE a trouvé une connexion utilisable et a arrêté de tester les candidats distants.
failed - l'agent ICE a vérifié tous les candidats distants mais n'a pas trouvé de correspondance pour au moins un composant.
disconnected - au moins un composant n'est plus en vie.
closed - l'agent ICE est fermé.
RTCPeerConnection.iceGatheringState (read only) - Renvoie une énumération RTCIceGatheringState qui décrit l'état de collecte ICE pour la connexion -
new - l'objet vient d'être créé.
gathering - l'agent ICE est en train de rassembler les candidats
complete l'agent ICE a terminé la collecte.
RTCPeerConnection.localDescription (read only)- Renvoie une RTCSessionDescription décrivant la session locale. Il peut être nul s'il n'a pas encore été défini.
RTCPeerConnection.peerIdentity (read only)- Renvoie une RTCIdentityAssertion. Il se compose d'un idp (nom de domaine) et d'un nom représentant l'identité de l'homologue distant.
RTCPeerConnection.remoteDescription (read only)- Renvoie une RTCSessionDescription décrivant la session distante. Il peut être nul s'il n'a pas encore été défini.
RTCPeerConnection.signalingState (read only)- Renvoie une énumération RTCSignalingState qui décrit l'état de signalisation de la connexion locale. Cet état décrit l'offre SDP. Un événement signalingstatechange est déclenché lorsque cette valeur change. Les valeurs possibles -
stable- L'état initial. Il n'y a pas d'échange d'offre / réponse SDP en cours.
have-local-offer - le côté local de la connexion a appliqué localement une offre SDP.
have-remote-offer - le côté distant de la connexion a appliqué localement une offre SDP.
have-local-pranswer - une offre SDP distante a été appliquée, et une réponse SDP appliquée localement.
have-remote-pranswer - un SDP local a été appliqué et une réponse SDP appliquée à distance.
closed - la connexion est fermée.
Gestionnaires d'événements
S.No. | Gestionnaires d'événements et description |
---|---|
1 | RTCPeerConnection.onaddstream Ce gestionnaire est appelé lorsque l'événement addstream est déclenché. Cet événement est envoyé lorsqu'un MediaStream est ajouté à cette connexion par l'homologue distant. |
2 | RTCPeerConnection.ondatachannel Ce gestionnaire est appelé lorsque l'événement datachannel est déclenché. Cet événement est envoyé lorsqu'un RTCDataChannel est ajouté à cette connexion. |
3 | RTCPeerConnection.onicecandidate Ce gestionnaire est appelé lorsque l'événement icecandidate est déclenché. Cet événement est envoyé lorsqu'un objet RTCIceCandidate est ajouté au script. |
4 | RTCPeerConnection.oniceconnectionstatechange Ce gestionnaire est appelé lorsque l'événement iceconnectionstatechange est déclenché. Cet événement est envoyé lorsque la valeur de iceConnectionState change. |
5 | RTCPeerConnection.onidentityresult Ce gestionnaire est appelé lorsque l'événement identityresult est déclenché. Cet événement est envoyé lorsqu'une assertion d'identité est générée lors de la création d'une offre ou d'une réponse via getIdentityAssertion (). |
6 | RTCPeerConnection.onidpassertionerror Ce gestionnaire est appelé lorsque l'événement idpassertionerror est déclenché. Cet événement est envoyé lorsque l'IdP (Identitry Provider) trouve une erreur lors de la génération d'une assertion d'identité. |
sept | RTCPeerConnection.onidpvalidation Ce gestionnaire est appelé lorsque l'événement idpvalidationerror est déclenché. Cet événement est envoyé lorsque l'IdP (fournisseur d'identité) trouve une erreur lors de la validation d'une assertion d'identité. |
8 | RTCPeerConnection.onnegotiationneeded Ce gestionnaire est appelé lorsque l'événement negociationneeded est déclenché. Cet événement est envoyé par le navigateur pour informer que la négociation sera nécessaire à un moment donné dans le futur. |
9 | RTCPeerConnection.onpeeridentity Ce gestionnaire est appelé lorsque l'événement peeridentity est déclenché. Cet événement est envoyé lorsqu'une identité d'homologue a été définie et vérifiée sur cette connexion. |
dix | RTCPeerConnection.onremovestream Ce gestionnaire est appelé lorsque l'événement signalingstatechange est déclenché. Cet événement est envoyé lorsque la valeur de signalingState change. |
11 | RTCPeerConnection.onsignalingstatechange Ce gestionnaire est appelé lorsque l'événement removestream est déclenché. Cet événement est envoyé lorsqu'un MediaStream est supprimé de cette connexion. |
Méthodes
S.No. | Méthodes et description |
---|---|
1 | RTCPeerConnection() Renvoie un nouvel objet RTCPeerConnection. |
2 | RTCPeerConnection.createOffer() Crée une offre (demande) pour trouver un pair distant. Les deux premiers paramètres de cette méthode sont les rappels de succès et d'erreur. Le troisième paramètre facultatif sont des options, telles que l'activation des flux audio ou vidéo. |
3 | RTCPeerConnection.createAnswer() Crée une réponse à l'offre reçue par l'homologue distant pendant le processus de négociation offre / réponse. Les deux premiers paramètres de cette méthode sont les rappels de succès et d'erreur. Le troisième paramètre facultatif sont des options pour la réponse à créer. |
4 | RTCPeerConnection.setLocalDescription() Modifie la description de la connexion locale. La description définit les propriétés de la connexion. La connexion doit pouvoir prendre en charge les anciennes et les nouvelles descriptions. La méthode prend trois paramètres, objet RTCSessionDescription, callback si le changement de description réussit, callback si le changement de description échoue. |
5 | RTCPeerConnection.setRemoteDescription() Modifie la description de la connexion à distance. La description définit les propriétés de la connexion. La connexion doit pouvoir prendre en charge les anciennes et les nouvelles descriptions. La méthode prend trois paramètres, objet RTCSessionDescription, callback si le changement de description réussit, callback si le changement de description échoue. |
6 | RTCPeerConnection.updateIce() Met à jour le processus de l'agent ICE consistant à envoyer une requête ping aux candidats distants et à rassembler les candidats locaux |
sept | RTCPeerConnection.addIceCandidate() Fournit un candidat distant à l'agent ICE. |
8 | RTCPeerConnection.getConfiguration() Renvoie un objet RTCConfiguration. Il représente la configuration de l'objet RTCPeerConnection. |
9 | RTCPeerConnection.getLocalStreams() Renvoie un tableau de connexion MediaStream locale. |
dix | RTCPeerConnection.getRemoteStreams() Renvoie un tableau de connexions MediaStream distantes. |
11 | RTCPeerConnection.getStreamById() Renvoie MediaStream local ou distant par l'ID donné. |
12 | RTCPeerConnection.addStream() Ajoute un MediaStream en tant que source locale de vidéo ou d’audio. |
13 | RTCPeerConnection.removeStream() Supprime un MediaStream en tant que source locale de vidéo ou audio. |
14 | RTCPeerConnection.close() Ferme une connexion. |
15 | RTCPeerConnection.createDataChannel() Crée un nouveau RTCDataChannel. |
16 | RTCPeerConnection.createDTMFSender() Crée un nouveau RTCDTMFSender, associé à un MediaStreamTrack spécifique. Permet d'envoyer une signalisation téléphonique DTMF (Dual-tone multifréquence) via la connexion. |
17 | RTCPeerConnection.getStats() Crée un nouveau RTCStatsReport qui contient des statistiques concernant la connexion. |
18 | RTCPeerConnection.setIdentityProvider() Définit l'IdP. Prend trois paramètres - le nom, le protocole utilisé pour communiquer et un nom d'utilisateur facultatif. |
19 | RTCPeerConnection.getIdentityAssertion() Recueille une affirmation d'identité. Il n'est pas prévu de traiter cette méthode dans l'application. Vous pouvez donc l'appeler explicitement uniquement pour anticiper le besoin. |
Établir une connexion
Créons maintenant un exemple d'application. Tout d'abord, exécutez le serveur de signalisation que nous avons créé dans le didacticiel «serveur de signalisation» via «serveur de nœuds».
Il y aura deux entrées de texte sur la page, une pour une connexion et une pour un nom d'utilisateur auquel nous voulons nous connecter. Créez un fichier index.html et ajoutez le code suivant -
<html lang = "en">
<head>
<meta charset = "utf-8" />
</head>
<body>
<div>
<input type = "text" id = "loginInput" />
<button id = "loginBtn">Login</button>
</div>
<div>
<input type = "text" id = "otherUsernameInput" />
<button id = "connectToOtherUsernameBtn">Establish connection</button>
</div>
<script src = "client2.js"></script>
</body>
</html>
Vous pouvez voir que nous avons ajouté l'entrée de texte pour une connexion, le bouton de connexion, l'entrée de texte pour l'autre nom d'utilisateur du pair et le bouton de connexion. Créez maintenant un fichier client.js et ajoutez le code suivant -
var connection = new WebSocket('ws://localhost:9090');
var name = "";
var loginInput = document.querySelector('#loginInput');
var loginBtn = document.querySelector('#loginBtn');
var otherUsernameInput = document.querySelector('#otherUsernameInput');
var connectToOtherUsernameBtn = document.querySelector('#connectToOtherUsernameBtn');
var connectedUser, myConnection;
//when a user clicks the login button
loginBtn.addEventListener("click", function(event){
name = loginInput.value;
if(name.length > 0){
send({
type: "login",
name: name
});
}
});
//handle messages from the server
connection.onmessage = function (message) {
console.log("Got message", message.data);
var data = JSON.parse(message.data);
switch(data.type) {
case "login":
onLogin(data.success);
break;
case "offer":
onOffer(data.offer, data.name);
break;
case "answer":
onAnswer(data.answer);
break;
case "candidate":
onCandidate(data.candidate);
break;
default:
break;
}
};
//when a user logs in
function onLogin(success) {
if (success === false) {
alert("oops...try a different username");
} else {
//creating our RTCPeerConnection object
var configuration = {
"iceServers": [{ "url": "stun:stun.1.google.com:19302" }]
};
myConnection = new webkitRTCPeerConnection(configuration);
console.log("RTCPeerConnection object was created");
console.log(myConnection);
//setup ice handling
//when the browser finds an ice candidate we send it to another peer
myConnection.onicecandidate = function (event) {
if (event.candidate) {
send({
type: "candidate",
candidate: event.candidate
});
}
};
}
};
connection.onopen = function () {
console.log("Connected");
};
connection.onerror = function (err) {
console.log("Got error", err);
};
// Alias for sending messages in JSON format
function send(message) {
if (connectedUser) {
message.name = connectedUser;
}
connection.send(JSON.stringify(message));
};
Vous pouvez voir que nous établissons une connexion socket avec notre serveur de signalisation. Lorsqu'un utilisateur clique sur le bouton de connexion, l'application envoie son nom d'utilisateur au serveur. Si la connexion réussit, l'application crée l'objet RTCPeerConnection et configure le gestionnaire onicecandidate qui envoie tous les candidats glacés trouvés à l'autre homologue. Ouvrez maintenant la page et essayez de vous connecter. Vous devriez voir la sortie de console suivante -
L'étape suivante consiste à créer une offre à l'autre pair. Ajoutez le code suivant à votre fichier client.js -
//setup a peer connection with another user
connectToOtherUsernameBtn.addEventListener("click", function () {
var otherUsername = otherUsernameInput.value;
connectedUser = otherUsername;
if (otherUsername.length > 0) {
//make an offer
myConnection.createOffer(function (offer) {
console.log();
send({
type: "offer",
offer: offer
});
myConnection.setLocalDescription(offer);
}, function (error) {
alert("An error has occurred.");
});
}
});
//when somebody wants to call us
function onOffer(offer, name) {
connectedUser = name;
myConnection.setRemoteDescription(new RTCSessionDescription(offer));
myConnection.createAnswer(function (answer) {
myConnection.setLocalDescription(answer);
send({
type: "answer",
answer: answer
});
}, function (error) {
alert("oops...error");
});
}
//when another user answers to our offer
function onAnswer(answer) {
myConnection.setRemoteDescription(new RTCSessionDescription(answer));
}
//when we got ice candidate from another user
function onCandidate(candidate) {
myConnection.addIceCandidate(new RTCIceCandidate(candidate));
}
Vous pouvez voir que lorsqu'un utilisateur clique sur le bouton «Établir la connexion», l'application fait une offre SDP à l'autre pair. Nous avons également défini les gestionnaires onAnswer et onCandidate . Rechargez votre page, ouvrez-la dans deux onglets, connectez-vous avec deux utilisateurs et essayez d'établir une connexion entre eux. Vous devriez voir la sortie de console suivante -
Maintenant, la connexion peer-to-peer est établie. Dans les prochains didacticiels, nous ajouterons des flux vidéo et audio ainsi que la prise en charge du chat textuel.