查看原文
其他

基于HLS格式的低延时互动直播技术

沈悦时 LiveVideoStack 2022-05-22

在不牺牲服务质量(卡顿率、画面清晰度)的前提下,越低的延时能带来越好的互动性用户体验。为达成可扩展性、服务质量、互动性的三赢,Twitch团队研发了基于HLS格式的低延时互动直播技术。本文来自Twitch Principal Research Engineer沈悦时在LiveVideoStackCon 2018大会上的分享,并由LiveVideoStack整理而成。


文 / 沈悦时

整理 / LiveVideoStack


本次分享的内容包括以下几个方面:


1、Twitch.tv的介绍;

2、互动性:互动直播和传统电视的区别;

3、点对点 vs. 广播:延时、可扩展性以及服务质量之间的利弊权衡;

4、推流 vs. 拉流:依然是延时、可扩展性以及服务质量之间的利弊权衡;

5、协议:HLS 加 HTTP Chunked Transfer Encoding;

6、后台:每个环节都得严格遵守纪律;

7、前台:ABR变得更难,瓶颈是带宽估计;

8、总结;


1、Twitch.tv的介绍


Twitch.tv是中国市场以外最大的互动直播平台,它的模式和国内的虎牙、斗鱼直播是类似的。从技术上来说,Twitch对广播产业的价值是最大程度地降低了广播的技术壁垒,只要你家里有个很简单的设备你就可以广播,实现互动的网上直播。



1. Twitch.tv的内容和用户社区



从用户社区上来说,Twitch.tv的用户社区是面向全球范围的,但最多的用户量集中在欧美地区;从直播内容上来说,Twitch.tv的内容和国内的虎牙、斗鱼直播非常相似,主要是以游戏为主。


2. Twitch的成长历程



Twitch于2011年开始创立,大概在2013年开始火起来的,从上图也可以看出,Alexa(评估网站受欢迎程度的第三方网站)通过统计单个用户每天的访问量和每个用户的访问页面次数,Twitch的受欢迎程度是排在全球第32位。这个排名自从2011年创立公司以来节节攀升。


下面这张图是我们2017年统计的真实观看量数据,每天的活动量大概在1500万左右,每月的活动量大约是1亿左右。另外,就在今年,在E3上统计得出Twitch的单个频道访问量超过了1700万,同时在线观众数达到了290万,这也创造了新的记录。



顺便给大家提一下,Twitch上最红的一个主播——Ninja,他是第一个上ESPN杂志头版头条封面的电子竞技玩家。



2、互动性:互动直播和传统电视的区别


在前面也有提到互动直播和传统电视是有很大区别的,主要就在于互动性,而要实现互动性的一个关键技术就是要做到低延时。正因为有了低时延,也导致衍生了一些新的商业模式,比如Twitch 的Extension,就是说低延时可以实现主播和众多观众一起参与游戏。



Extension指的是我们的主播跟观众同时在一起打游戏,在主播直播游戏的过程中,会有一些接口开放给观众,比如上图的场景下,参与游戏的有10个人,主播需要去解救十个人当中的某一个人,要去救谁呢?这个不是由主播来决定的,而是他的观众来投票决定的,因为有了低延时,就能让主播和观众实时互动起来,这是一种全新的商业模式。


 

从心理学上来讲,如果你要实现对话,延时必须在400毫秒以内,不然就进行不下去了,这也说明了低延时对于互动的重要性。下面将从三个方面来介绍我们Twitch是如何做到低延时的。


3、点对点 vs. 广播


首先我们要理清的一点就是点对点和广播是完全两码事,在流媒体中针对应用的利弊权衡是有三个方面的考量因素的:低延时、高可扩展性和高服务质量。对于Twitch,首先是要求有很高的可扩展性,因为它的同时在线人数多,要求单个用户的成本很低,这就是它的高扩展性;同时,它还要求比较高的观看质量,就像看春晚一样,不能总是低清、卡顿的,但往往高的观看质量会牺牲一定的延时;在网上做直播的用DASH、HLS延时往往有30秒到60秒是很平常的,但这也给了很多人误解,认为HLS延时就一定很高,希望本次的分享能够打破这种偏见。


但对于点对点的应用,比如电话会议、Facetime,它是一定要求低延时的,不能超过400毫秒,最好在200毫秒以内;与此同时,它牺牲了可扩展性,比如,今年Facetime给出的最多在线人数是32人,一般的电话会议软件也就不到100人,而像Twitch上比较火的网红一般同时观看人数都有10万左右。而且,点对点在服务质量上是有一定牺牲的,比如连麦的过程中,要求比较高的低延时,对画质、卡顿率就没有那么高的要求了。因此,不能把点对点生搬硬套在互动直播的应用上去。


 

如上图所示的紫线部分,我们Twitch首先要求高的可扩展性,只要能容下足够多的用户,才能生存下去;同时,我们还要提高用户体验,就是希望画质越来越好,卡顿率要很低;在这个基础上,我们同时还想把这个延时降的很低,把传统的线性电视跟点对点的优点结合起来,后续会为大家介绍,为了做到这些我们做了哪些工作。 另外提一下我们Twitch上的大网红Ninja,他是我们Twitch最大的低延时广播频道,低延时是1.2秒。下面先从推流和拉流的区别上来说明一下,中美互动直播的不同。


4、推流 vs. 拉流


对于推流和拉流方式的选择上同样要考虑上述的三个因素,依然是延时、可扩展性以及服务质量之间的利弊权衡。先来看一幅图,就能看出架构的不同:



在中国最常见的就是用RTMP来推流,推流的意思就是说,在主播端,他把内容一帧一帧往转码器里面放,转码后发往源站,源站收到了流后就会不断地往播放器发,也就是说,它有一帧就往外发一帧。RTMP推流有个显著的特点就是低延时且低扩展性。


Twitch采用的是用HLS拉流,在前面同样是用RTMP来将流推到转码器,在转码器里会把一个连续的流切成片,我们Twitch是两秒钟一片,Facebook和YouTube是一秒钟一片,这个也是质量、低延时和HTTP之间请求数量的一个权衡。转码器或源站把连续的RTMP流转码后切成一秒或者两秒的片存在那里,它是不会主动的把流推给播放器的。只有播放器收到一个播放清单(Playlist),它再去向它的最终节点,一层一层的往源站去做请求。对于推流是后台主动做的,而对于拉流是后台被动做的,播放端是主动的。RTMP是一个相对来说,低延时但成本比较高,与此相反,HLS是成本比较低但延时比较高。在这里插一个小故事,Twitch是2011年创业成立的,最开始都采用的是RTMP来推流,在2013年由于用户的增多,我们的钱却亏得越来越多了而大面积裁员。就在那个时候,我们将RTMP换为HLS才扭亏为盈,然后我们那个时候算了一下,如果一台单机服务器,在同样的CPU、内存的情况下,用RTMP推流和HLS拉流来比,它的密度是1:5的关系,用HLS还有个好处就是可以做码率自适应播放(ABR),这个细节等会再解释,它的好处就是让很多的弱网情况下观众有个更好的观看体验,但是有个非常坏的地方就是延迟增加到了10秒,下面再给大家介绍我们为了降低延时做了哪些改进。


5、协议


在协议上,我们采用的是HLS 加 HTTP Chunked Transfer Encoding。

在这里我先介绍一下我们Twitch整个的从端到端的互动直播架构:



直播的延时计算的是从光打到摄像机的那一刻到光从荧幕射到看的人的眼睛里面之间的时间差。在这个过程当中,首先就是主播用OBS推流工具和采集工具将一个RTMP流发送到就近的互联网服务器,再通过我们的主干网把它传到中心的转码服务器,从转码服务器把它切成一秒或者两秒的片,再把它再放到源站上,通过我们内部的骨干网一步一步把它分发,再通过最终节点连接观看者的互联网,最终通过我们自己自建的这个播放器把解码显示出来。在这个流水线当中,转码器和播放器都是我们自己开发的软件,而且我们有自己的私有云,这可能也是中国跟美国不太一样,中国的互动直播平台大多都是用公有云,而美国的互动直播平台基本都是私有云。


HTTP1.1协议里面有个东西叫做Chunked Transfer Encoding,在前面介绍有提到,在RTMP流到转码器后会被截成一个一秒或两秒的片,在所有的分片收好后会放到服务器上等待播放器来请求它。



但其实我们想,当一个分片生产好时,在等待其他的分片都生产好的过程中,这个两秒钟就浪费了,我们完全可以在这个过程中节省出两秒。就是说,当我在这个片刚生产好的时候,就在其他分片还在生产的过程,它就前面的这些已经推给这个播放端了,会达到一个什么效果呢?对于一个Segment来说,它的生产和发送还有它的播放是同步的,如下图所示,内容生产、分发、播放是紧密同步的。如果要达到低延时,如下图中绿色划出部分,每两秒钟的一个片,我都仅仅花两秒钟来下载,它下载的时间是非常整齐划一的。



那么我的毫秒都花在哪儿了呢?在下图中列出了上述架构中几个步骤在采用HTTP Chunked Transfer Encoding和不采用的情况下的时延对比:



除了在转码器部分降低到0.5秒,我们在播放清单和播放器缓冲方面也做了很多的优化工作,最终端到端的延迟降低到了4.45秒。我们Twitch已经上线了,很多网红也在用着低延时,但最重要的是如何把低延时实现出来,下面我将在分后台和前台两个方面来介绍低延时的实现。


6、后台:每个环节都得严格遵守纪律


在前面浏览器的例子中,我们可以看出每两秒钟的一分片,它都要花两秒钟来下载,不能多也不能少,如果它稍微有些波动的话,这个波动就会到你的缓存里面去,就让你的这个时延给增加了,因此,在整个CDN拓扑结构里每个节点它都要非常守纪律,下面有一个后台稳定性检查的例子,统计了一台分发服务器上HTTP请求时间的情况:



另外,给大家提一点的就是,Twitch的直播转码器是我们开发的,而不是采用的FFmpeg,因为FFmpeg不太适合做直播的转码,它可能做离线的转码是OK的,但做直播转码性能不是最优。



直播转码器的功能就是将收进的1080p60的流,然后出去的流是1080p60到160p30,以此来满足不同的网络带宽的用户需求。稍微提一点,对于出去的1080p60的流我们是不做转码的,而是做的转封装。


此外,HLS转码器的输出必须是对齐的分片,为了HLS它能够上下做ABR的切换,要求每个分片的起始的IDR帧在PTS上面一定要对齐的,如果不对齐的话,不同码率切换就不是无缝切换。



最后,对于基于分片和基于帧的实时转码器要有一定的区分,最简单的区分就是基于分片的实时转码器会在最后生成很多帧,而基于帧的实时转码器是收一帧最后生成出一帧。



基于帧的实时转码器会有一个问题,在进行1080p转封装、720p转码、480p转码的过程中都是独立存在的,它互相是不知道对方的。



也就是说,每一帧的PTS和DTS都是自己的,如果时延没有同步的话,会导致IDR帧出来的时间是不一样的,那么这个分片起始帧就不是IDR,那你的片就不能播了。


7、前台:ABR变得更难,瓶颈是带宽估计


在前面介绍的是后台的相关东西,其实HLS低延时真正难的地方在于前台这一块,主要是前台的ABR。播放器的播放过程是,在播放时会不断请求发送分片,转码器会把一片里面的一帧一帧往那边推,推了以后,播放器会收这些帧,收完了以后还再转封装。



ABR有一个公式,会通过当前的带宽大小、播放器缓存情况等等判断请求下一个切片的大小,它会做出一个决策来判断下一个片应该是去播1080p,还是应该下调到480p。在这个过程中,ABR会不断的侦测带宽的大小,判断现在的带宽能否播放当前的码率,是否在下一次需要请求低码率的分片。对于分片下载,计算下载速度是很容易的,当我的一个两秒的视频,下载下来需要0.5秒时,这说明带宽是视频码率的四倍,但带宽的大小预测这一块有个问题就是,在带宽充分的情况下,两秒钟的一个分片永远是花两秒钟来下载的,这就无法计算真实的带宽有多大,如果减小采样间隔,将下载速度打印出来会发现噪音非常的

多,如下图。



所以我们现在就面临这么一个难题,在充足带宽情况下,比如,带宽到底是10Mbps还是20Mbps,这个是我们在做基于HLS低延时的一个最头疼的一个问题。还有更糟糕的情况,在有的播放端会缺乏Streams API的支持,导致无法获取客户端的打印信息。



对于Firefox这个问题是可以解决的,因为我们跟他们团队有合作,从64版开始,他们就会把这个开关打开,那么我们现有的算法应该就可以工作了。


8、总结


总结一下本次分享的几点主要内容:


  1. 低延时的直播能实现主播和观众之间的强互动性,然而具有可扩展的低延时实时广播和点对点的低延时实时通讯是两个完全不同的工程问题;

  2. 推流(RTMP)的优势是低延迟,而拉流(HLS、DASH)的优势是低成本和ABR;

  3. 在不牺牲可扩展性和服务质量的前提下,Twitch仍然使用HLS来实现低延时广播。我们控制整条视频上载、分发的管道,同时对后台和前台做创新性的优化;

  4. HTTP Chunked Transfer Encoding被用在全栈的转码、源站、中间节点、边缘节点以及播放器。这样才能实现中位值<4.5秒的端到端延时,其中包括转码的<0.5秒以及播放器的<2.5秒。



精品文章推荐




线上分享:



技术趋势:


您可能也对以下帖子感兴趣

文章有问题?点此查看未经处理的缓存