1. 簡介
在這個程式碼研究室中,您將學習如何在瀏覽器和 Cloud Firestore 中使用 WebRTC API 建構簡單的視訊通訊應用程式來傳送訊號。這款應用程式稱為 FirebaseRTC,可以做為簡易範例,協助您瞭解建構 WebRTC 的應用程式的基本概念。
須知事項
- 使用 WebRTC 在網路應用程式中發起視訊通話
- 使用 Cloud Firestore 簽署遠端派對
事前準備
安裝這個程式碼研究室之前,請先確認已安裝下列項目:
- 隨附於 Node.js 的 npm - 建議使用 Node LTS
2. 建立並設定 Firebase 專案
建立 Firebase 專案
- 在 Firebase 主控台中按一下 [新增專案],然後將 Firebase 專案命名為 FirebaseRTC。
記下 Firebase 專案的專案 ID。
- 按一下 [建立專案]。
您要建構的應用程式會使用兩種網路上的 Firebase 服務:
- 使用 Cloud Firestore 將結構化資料儲存在雲端,並在資料更新時收到即時通知
- 使用 Firebase 代管來託管和提供靜態資產
針對這個特定程式碼研究室,您已在目標專案中設定 Firebase 代管。不過就 Cloud Firestore 而言,我們將逐步引導您進行設定,並使用 Firebase 主控台啟用服務。
啟用 Cloud Firestore
應用程式使用 Cloud Firestore 儲存即時通訊訊息,並接收新的即時通訊訊息。
您需要啟用 Cloud Firestore:
- 在 Firebase 主控台選單的「開發」專區中,按一下 [資料庫]。
- 按一下 Cloud Firestore 窗格中的 [建立資料庫]。
- 選取 [Start in test mode] (啟動測試模式) 選項,並在閱讀安全性規則的免責事項後按一下 [啟用]。
測試模式可確保您在開發期間可自由寫入資料庫。我們會在這個程式碼研究室中讓資料庫更加安全。
3. 取得範例程式碼
透過指令列複製 GitHub 存放區:
git clone https://github.com/webrtc/FirebaseRTC
程式碼範例應該已複製到 FirebaseRTC
目錄中。
請確認您的指令列現在從這個目錄執行:
cd FirebaseRTC
匯入啟動應用程式
在編輯器中開啟 FirebaseRTC
中的檔案,然後按照下方操作說明變更檔案。這個目錄含有程式碼研究室的起始程式碼,當中包含並非功能專用的 WebRTC 應用程式。我們也會讓程式碼在程式碼研究室中執行。
4. 安裝 Firebase 指令列介面
Firebase 指令列介面 (CLI) 可讓您在本機提供網頁應用程式,並將網頁應用程式部署至 Firebase 代管。
- 請執行以下 npm 指令來安裝 CLI:
sh npm -g install firebase-tools
- 執行以下指令,確認 CLI 已正確安裝:
sh firebase --version
確認 Firebase CLI 版本為 6.7.1 以上版本。
- 執行下列指令來授權 Firebase CLI:
sh firebase login
您已設定網頁應用程式範本,以便從應用程式的本機目錄和檔案擷取 Firebase 代管應用程式的設定。但是,您必須將應用程式與 Firebase 專案建立關聯。
執行下列指令,將您的應用程式與 Firebase 專案建立關聯:
sh firebase use --add
當系統提示時,請選取您的專案 ID,然後為您的 Firebase 專案指派別名。
如果您有多個環境 (實際工作環境、暫存等),別名就相當實用。不過,在這個程式碼研究室中,我們僅使用 default
的別名。
按照指令列中的其他操作說明進行。
5. 執行本機伺服器
你現在可以開始使用我們的應用程式了!在本機環境中執行應用程式!
請執行下列 Firebase CLI 指令:
sh firebase serve --only hosting
您的指令列應該會顯示下列回應:
hosting: Local server: http://localhost:5000
我們使用 Firebase 代管模擬器,在本機執行應用程式。網頁應用程式現在可以透過 http://localhost:5000 使用。
- 在 http://localhost:5000 開啟應用程式。
您應該會看到已連結至 Firebase 專案的 FirebaseRTC 副本。
應用程式已自動連結至你的 Firebase 專案。
6. 正在建立新房間
在這個應用程式中,每個視訊會議工作階段稱為聊天室。使用者只要按一下應用程式中的按鈕,即可建立新聊天室。這項操作會產生一組 ID,方便遠端伺服器加入相同的會議室。在 Cloud Firestore 中,每組聊天室的 ID 都會做為金鑰使用。
每間聊天室都含有優惠和答案的 RTCSessionDescriptions
,以及兩項雙方分別擁有的 ICE 候選人。
第一項工作是導入缺少的程式碼,使用呼叫端的初始優惠建立新聊天室。開啟 public/app.js
並找到註解 //
Add code for creating a room here
,然後新增下列程式碼:
const offer = await peerConnection.createOffer();
await peerConnection.setLocalDescription(offer);
const roomWithOffer = {
offer: {
type: offer.type,
sdp: offer.sdp
}
}
const roomRef = await db.collection('rooms').add(roomWithOffer);
const roomId = roomRef.id;
document.querySelector('#currentRoom').innerText = `Current room is ${roomId} - You are the caller!`
第一行會建立一個 RTCSessionDescription
,代表呼叫端的優惠。然後設為本機說明,最後寫入 Cloud Firestore 中的新物件物件。
接著,我們會監聽資料庫變更,並偵測呼叫者在何時加入答案。
roomRef.onSnapshot(async snapshot -> {
console.log('Got updated room:', snapshot.data());
const data = snapshot.data();
if (!peerConnection.currentRemoteDescription && data.answer) {
console.log('Set remote description: ', data.answer);
const answer = new RTCSessionDescription(data.answer)
await peerConnection.setRemoteDescription(answer);
}
});
必須等到呼叫者寫入答案的 RTCSessionDescription
,並將其設為呼叫 RTCPeerConnection
的遠端說明時。
7. 正在加入聊天室
下一步是執行加入現有聊天室的邏輯。使用者可以按一下 [加入聊天室] 按鈕,並輸入聊天室 ID 即可加入。您的工作是實作答案的 RTCSessionDescription
建立作業,並視情況在資料庫中更新聊天室。
const offer = roomSnapshot.data().offer;
await peerConnection.setRemoteDescription(offer);
const answer = await peerConnection.createAnswer();
await peerConnection.setLocalDescription(answer);
const roomWithAnswer = {
answer: {
type: answer.type,
sdp: answer.sdp
}
}
await roomRef.update(roomWithAnswer);
在上述程式碼中,我們首先會從呼叫者擷取優惠,並建立 RTCSessionDescription
做為遠端說明。接著,我們建立答案,並將其設為本機說明,並更新資料庫。資料庫更新會觸發呼叫端的 onSnapshot
回呼,進而根據呼叫者的答案設定遠端說明。如此會完成呼叫者與呼叫者之間的 RTCSessionDescription
物件交換作業。
8.收集 ICE 求職者
來電者和來電者必須能夠彼此交換資訊,通知 WebRTC 如何連線至遠端對等點,呼叫者與來電者才能彼此連線。下一步是實作會監聽 ICE 候選程式碼的程式碼,並新增至資料庫中的集合。找出函式 collectIceCandidates
並新增下列程式碼:
async function collectIceCandidates(roomRef, peerConnection,
localName, remoteName) {
const candidatesCollection = roomRef.collection(localName);
peerConnection.addEventListener('icecandidate', event -> {
if (event.candidate) {
const json = event.candidate.toJSON();
candidatesCollection.add(json);
}
});
roomRef.collection(remoteName).onSnapshot(snapshot -> {
snapshot.docChanges().forEach(change -> {
if (change.type === "added") {
const candidate = new RTCIceCandidate(change.doc.data());
peerConneciton.addIceCandidate(candidate);
}
});
})
}
這個函式會有兩個動作, 他們會從 WebRTC API 收集 ICE 候選項目並新增至資料庫,並監聽遠端對等點新增的 ICE 候選項目,並新增至其 RTCPeerConnection
執行個體。監聽資料庫變更時,請務必篩選掉所有不屬於新的額外項目,因為我們日後可能會不斷新增同一組 ICE 候選項目。
9. 結論
在這個程式碼研究室中,您已瞭解如何使用 Cloud Firestore 實作 WebRTC 信號,以及如何利用這個 API 建立簡易視訊通訊應用程式。
詳情請參閱以下資源: