簡介
WebRTC(Web即時通信)是目前由Google,Mozilla和Opera支持的一種新的Web標準。它允許瀏覽器之間的點對點通信。其目的是為瀏覽器,移動平台和網路物件Web of Things(WoT)提供更豐富的高質量RTC應用程序,並允許他們通過一組通用的協議進行通信。Web的最後一個主要挑戰是通過語音和視頻實現人與人通信,而無需使用特殊的插件並且無需支付任何費用使用這些服務。
第一個WebRTC實施是由愛立信於2011年5月建立的。 WebRTC定義了用於實時,無插件視頻,音頻和數據通信的開放標準。
目前已經有許多Web服務已經使用RTC,但還是需要下載應用程序或相關插件。
其中包括Skype,Facebook(使用Skype)和Google Hangouts(使用Google Talk插件)。下載、安裝和更新插件的程序可能會很複雜,容易出錯和惱人,並且通常很難說服人們首先安裝插件!
準備工作
一般來說,使用webRTC相關應用程式需要:- 取得音頻(audio)、視頻(video)、其他資料流(data stream)。
- 收集網路訊息(例如:Ip address 和port),並與其他WebRTC client交換此訊息。
- “訊息”通信用於回報錯誤,以及發起或關閉session。
- client必須交換關於media的訊息,例如解析度和編解碼器。
- 音頻、視頻、資料的串流。
WebRTC主要實現三個API:
- MediaStream:允許client(例如:網頁瀏覽器)進入點的串流,例如:來自WebCam或麥克風的串流。
- RTCPeerConnection:啟用音頻或視頻資料的傳輸,並且支持加密和頻寬管理。
- RTCDataChannel:啟用點對點的通訊資料。
理論上,有可能創建一個簡單的WebRTC應用程式,沒有任何服務器元件用於訊息。 在實作中,這樣的應用沒有多大意義,但因為它可以在單個頁面上使用,所以它可以在點與點之間分享資料。
MediaStream
MediaStream表示同步的媒體串流,每個MediaStream都有一個輸入和一個輸出。
getUserMedia方法有三個參數:
- a constraints object
- a success callback method
- a failure callback method
例如:本機端WebCam串流可以在HTML5視頻元素中顯示。
<!DOCTYPE html>
<html>
<head>
<script src="webrtc.js"></script>
<title>WebRTC Test</title>
</head>
<body>
<video id="localVideo" autoplay/>
<script>
window.addEventListener("load", function (evt) {
navigator.getUserMedia({ audio: true, video: true},
function(stream) {
var video = document.getElementById('localVideo');
video.src = window.URL.createObjectURL(stream);
},
function(err) {
console.log("The following error occurred: " + err.name);
}
);
});
</script>
</body></html>
RTCPeerConnection
RTCPeerConnection interface 表示本機端電腦和遠程點之間的WebRTC連接,它用於處理點與點之間的資料有效串流。 雙方(the caller and the called party)需要設定一個屬於自己的RTCPeerConnection實例來表示點與點連接的結束。 一般來說,我們使用RTCPeerConnection串流事件callback來處理音頻/視頻的串流。
例如:將它分配給HTML5視頻。
var peerConn= new RTCPeerConnection();
peerConn.onaddstream = function (evt) {
var videoElem = document.createElement("video");
document.appendChild(videoElem);
videoElem.src = URL.createObjectURL(evt.stream);
};
呼叫的發起者(呼叫者/撥電話的人)需要創建提議並使用信令服務(例如,使用WebSockets的NodeJS服務器應用)將其發送到被叫者(接收者/接電話的人):
navigator.getUserMedia({video: true}, function(stream) {
videoElem.src = URL.createObjectURL(stream);
peerConn.addStream(stream);
peerConn.createOffer(function(offer) {
peerConn.setLocalDescription(new RTCSessionDescription(offer), function() {
// send the offer to a server to be forwarded to the other peer
}, error);
}, error);
});
呼叫者接收到提供並需要的回答的答覆並且建立有效回答,並將其傳送給呼叫者:
navigator.getUserMedia({video: true}, function(stream) {
videoElem.src = URL.createObjectURL(stream);
peerConn.addStream(stream);
peerConn.setRemoteDescription(new RTCSessionDescription(offer), function() {
peerConn.createAnswer(function(answer) {
peerConn.setLocalDescription(new RTCSessionDescription(answer), function() {
// send the answer to a server to be forwarded back to the caller
}, error);
}, error);
}, error);
});
setLocalDescription方法有三個參數:
- a session description
- a success callback system
- an error callback method
RTCPeerConnection and Servers
在實際的應用中,WebRTC需要伺服器,用於以下目的:
- 用戶管理。
- 點與點之間的訊息交流。
- 關於媒體的資料交換,例如格式和視頻分辨率。
- 連接需要穿透NAT gateways 和防火牆。
ICE 框架使用STUN協定和擴展的TURN,使RTCPeerConnection能夠穿越NATgateways和其他網絡特定的細節。ICE是一種連結點與點的框架,例如:兩個視訊視訊聊天室的clients端,ICE嘗試直接通過UDP連結點,並且盡可能降低的延遲。
在這個過程中,STUN伺服器有一個單獨的工作,使NAT後面的點,能夠找到public address和port,Google和Mozilla能夠提供了幾個免費使用的STUN伺服器。 例如,Google STUN伺服器用於得到ICE candidates,然後轉發給其他的點。
在這個過程中,STUN伺服器有一個單獨的工作,使NAT後面的點,能夠找到public address和port,Google和Mozilla能夠提供了幾個免費使用的STUN伺服器。 例如,Google STUN伺服器用於得到ICE candidates,然後轉發給其他的點。
var peerConnCfg = {'iceServers': [{'url': 'stun:stun.l.google.com:19302'}]}, peerConn= new RTCPeerConnection(peerConnCfg), signalingChannel = new WebSocket('ws://my-websocket-server:port/'); peerConn.onicecandidate = function (evt) { // send any ice candidates to the other peer, i.e., evt.candidate signalingChannel.send(JSON.stringify({ "candidate": evt.candidate })); }; signalingChannel.onmessage = function (evt) { var signal = JSON.parse(evt.data); if (signal.sdp) peerConn.setRemoteDescription(new RTCSessionDescription(signal.sdp)); else if (signal.candidate) peerConn.addIceCandidate(new RTCIceCandidate(signal.candidate)); };
訊號頻道表示基於WebSockets,XHR或其他內容的通信頻道,目的是幫助交換點與點間連接初始化中所需的信息。
setRemoteDescription的方法有三個參數:
- a session description
- a success callback method
- an error callback method
RTCDataChannel
RTCDataChannel interface 表示連接點與點之間的雙向資料頻道,並且可以使用RTCPeerConnection.createDataChannel()建立頻道,或者在現有RTCPeerConnection上的類型為RTCDataChannelEvent的data channel事件中接收到該對象,並且一定要使用資料頻道的功能,因為他利用消息傳遞的事件機制進行通訊的。var peerConn= new RTCPeerConnection(), dc = peerConn.createDataChannel("my channel"); dc.onmessage = function (event) { console.log("received: " + event.data); }; dc.onopen = function () { console.log("datachannel open"); }; dc.onclose = function () { console.log("datachannel close"); };