什么是 RTC?
RTC 即 Real-Time Communication 的簡稱是一種給行業(yè)提供高并發(fā)、低延時、高清流暢、安全可靠的全場景、全互動、全實時的音視頻服務的終端服務。上面是比較官方的解釋,通俗的來講就是一種能夠?qū)崿F(xiàn)一對一、多對多音視頻通話等眾多功能的服務。目前提供該項服務的服務商有很多例如:聲網(wǎng)、云信、火山引擎、騰訊云等。
背景
目前云音樂旗下 APP 眾多,其中涉及到 RTC 業(yè)務的不在少數(shù),例如:常見的音視頻連麥、PK、派對房,1v1 聊天等。由于業(yè)務線不同,功能不同,開發(fā)者也不同,大家各寫一套,不斷的重復造輪子,因此為了避免重復的開發(fā)工作提升開發(fā)效率,需要有一套通用的RTC框架。
設計思路
在講具體的方案設計之前,先講一下我的設計思路:
- 功能內(nèi)聚 :需要將功能都封裝在一個容器里,對外通過接口提供方法調(diào)用
- 業(yè)務隔離 :不同的業(yè)務需要有不同的功能容器
- 統(tǒng)一調(diào)用 :所有功能容器需要有統(tǒng)一的調(diào)用入口
- 狀態(tài)維護 :需要對狀態(tài)進行精準維護
- 切換無感 :進行功能容器切換時候,無感知
- 核心可控 :對核心鏈路可監(jiān)控,故障預警
基于以上 6 點,大致的架構(gòu)設計如圖所示,這里先不用深究圖中的模塊表示什么,后面會講到,這里只是先了解一下大致的架構(gòu):
image.png
接下來我就來講講具體的實現(xiàn)過程。
方案設計
前言:
RTC 的業(yè)務場景雖然很多,但本質(zhì)上卻相差無幾,都是用戶加入到一個共同的房間,然后在房間內(nèi)進行實時的音視頻通訊。具體到實際項目中大致又可分為兩種:全場景 RTC 和部分場景 RTC。
- 全場景 RTC :整個業(yè)務都是通過 RTC 技術(shù)實現(xiàn)例如:1v1 音視頻通話、派對房等。
- 部分場景 RTC :即整個業(yè)務鏈路中只有一部分使用了 RTC 技術(shù),往往這種業(yè)務會涉及到引擎的切換。
不管是哪一種場景,承載核心功能的引擎都是必不可少的,因此我們首先就從引擎開始著手,另外為了方便描述,后續(xù)便將引擎統(tǒng)一稱作 Player。
1、Player 的封裝
在與 RTC 相關(guān)聯(lián)的業(yè)務中會涉及到不同類型的 Player,例如:主播開播(推流 Player),觀眾觀看直播(拉流 Player)以及 RTC Player等。它們的功能雖然各不相同,但用法卻有相似之處,例如都有啟動 start,終止 stop 等。因此我們可以將不同的 Player 抽象出一個共同的接口 IPlayer 相關(guān)代碼如下:
interface IPlayer<DS : IDataSource, CB : ICallback> {
fun start(ds: DS)
fun stop()
fun setParam(key: String, value: T?)
......
}
其中 IDataSource 和 ICallback 分別是啟動 Player 所需要的數(shù)據(jù)源和回調(diào),后面的文章中也會多次提到,特別是 IDataSource 它是 Player 啟動的源頭就好比打電話時的電話號碼。
在這里遇到的一個問題點就是由于 Player 內(nèi)聚了所有的功能除了有一些通用方法外,也有著屬于自己特有的方法,例如:靜音,音量調(diào)節(jié)等。這些方法眾多而且各不相同無法在 IPlayer 接口中全部列出,即使能全部列出,但隨著業(yè)務的迭代 Player 中的方法肯定會不斷變化,不可能每更改一個方法就改一下接口,這顯然不符合程序設計原則。那么如何將不同的方法抽象化,讓上層通過調(diào)用同一個方法來執(zhí)行不同的操作呢?這里通過:
fun setParam(key: String, value: T?)
來實現(xiàn),其中 key 表示方法的唯一標記,value 表示方法的入?yún)ⅰ_@樣上層只需要通過調(diào)用 setParam 傳入相應的方法標記和方法入?yún)⒓纯烧{(diào)用到對應的方法了。那么如何做到呢?答案也很簡單通過一個中間層建立起一一映射關(guān)系。但是 Player 的類型眾多,要是每寫一個 Player 都要寫一個映射邏輯就太麻煩了。所以這里通過 APT 編譯時注解再結(jié)合 javapoet 自動生成這個中間層并給它命名為 xxxPlayerWrapper 其內(nèi)部生成一個 convert 方法,在這個方法內(nèi)部完成一一映射邏輯。接下來我們看看具體實現(xiàn)過程:
- 首先定義了兩個注解分別作用于具體的 Player 和對應的方法例如:
@Retention(RetentionPolicy.CLASS)
@Target({ElementType.TYPE})
public @interface PlayerClass {
}
@Retention(RetentionPolicy.CLASS)
@Target({ElementType.METHOD})
public @interface PlayerMethod {
String name();
}
@PlayerClass
open class xxxPlayer : IPlayer<xxxDataSource, xxxCallback>() {
@PlayerMethod(name = "key1")
fun method1(v: String) {
....具體實現(xiàn)
}
}
- 一一映射關(guān)系建立:
xxxPlayer 和 xxxPlayerWrapper 之間是一個相互依賴關(guān)系,互為彼此的成員變量。當調(diào)用 xxxPlayer 的接口方法 setParam(key: String, value: T?) 時,會直接調(diào)用到 xxxPlayerWrapper 的 convert 方法,convert 方法會根據(jù) key 來找到其所對應的方法名,最后直接調(diào)用到 Player 的具體方法。
image.png
-
RTC
+關(guān)注
關(guān)注
2文章
616瀏覽量
68495 -
騰訊云
+關(guān)注
關(guān)注
0文章
221瀏覽量
17052
發(fā)布評論請先 登錄
利用愛星物聯(lián)服務腳手架實現(xiàn)定制服務

2010年迪拜五大行業(yè)展|迪拜建材展|緊固件|腳手架|建筑五金|衛(wèi)浴|陶瓷|大理石
2011年沙特建材展|吉達建材展|五大行業(yè)展|緊固件|腳手架|玻璃|門窗|
2011年沙特建材展|吉達建材展|五大行業(yè)展|緊固件|腳手架|玻璃|門窗|
懸挑式腳手架監(jiān)理控制要點
物聯(lián)網(wǎng)腳手架系統(tǒng)能帶來什么益處
科學家研發(fā)可溶解的植入骨折的腳手架材料——特殊繃帶
腳手架掛牌方案需要符合哪些層面的規(guī)定
關(guān)于針對腳手架掛牌的歸納分析
為何需要腳手架掛牌,它的作用是怎樣的
腳手架掛牌的具體流程是怎樣的
腳手架掛牌是什么,有什么作用
關(guān)于腳手架掛牌的有關(guān)定義表述
RTC腳手架的設計與實現(xiàn)(下)

評論