Javascript 为流媒体服务器正确拆分MPEG-1第3层

Javascript 为流媒体服务器正确拆分MPEG-1第3层,javascript,mp3,audio-streaming,mpeg,Javascript,Mp3,Audio Streaming,Mpeg,我在一个音乐流服务器上工作。现在,我想将MP3文件分块从服务器发送到客户端(通过http范围请求/响应)。我的客户端成功地解码了响应数据,并一块接一块地播放音乐(固定字节大小),但在每个块之间都有一个口吃声音(短但明显) MP3文件的编码版本为MPEG-1和第3层。我读过关于MP3格式的文章,我注意到在第3层中,帧不是独立的(称为位/字节库),它们特别指出: 在最坏的情况下,在能够解码单个帧之前,可能需要9个输入帧 我使用http范围请求的原因是,在签出Spotify网络传输(Chrome开发工

我在一个音乐流服务器上工作。现在,我想将MP3文件分块从服务器发送到客户端(通过http范围请求/响应)。我的客户端成功地解码了响应数据,并一块接一块地播放音乐(固定字节大小),但在每个块之间都有一个口吃声音(短但明显)

MP3文件的编码版本为MPEG-1和第3层。我读过关于MP3格式的文章,我注意到在第3层中,帧不是独立的(称为位/字节库),它们特别指出:

在最坏的情况下,在能够解码单个帧之前,可能需要9个输入帧

我使用http范围请求的原因是,在签出Spotify网络传输(Chrome开发工具)后,我复制了他们的技术来请求部分内容。他们请求的字节长度约为166000,但不是固定的(有时为166287、16682…字节)

问题:

Spotify是否将其文件拆分为近似(非固定)大小的块

如果是这样,我如何正确分割此MPEG-1第3层文件以进行流式传输


现在,我正在客户端使用javascript来播放音频。我使用“AudioContext”类和“decodeAudioData”方法来解码每个块

正如@szatmary所指出的,这就是问题所在。你把这些块当作是完全独立的,但它们不是。这会导致出现故障

您需要做的是边走边解码,并将数据添加到正在解码的缓冲区的末尾。这是规定的方法来做到这一点。MSE使您可以控制如何获取该数据,因此,如果希望通过范围请求获取该数据,您可以

我认为一个更好的建议就是让浏览器来处理它。只需设置音频元素的
src
属性并让它播放即可。浏览器足够智能,可以发出自己的范围请求,如果需要,还可以回退到常规请求。这允许浏览器也处理流控制。您不需要做任何额外的工作,最终将得到一个更优化的解决方案。

Spotify使用。一旦读取了文件头,剩余的块在查找或正常播放期间通过HTTP
Range
请求提供

考虑放弃MP3(非常旧的)而代之以音乐。MSE可以播放
audio/webm codecs=opus
文件,但当前无法播放
audio/ogg
文件。如果需要播放Ogg Opus文件,可以绕过MSE并将WebAssembly与Web音频API一起使用,但需要手动调节解码和输出缓冲区以提高内存效率。你将有更多的控制,但编码更复杂


首先参见

中的块解码示例,是的,您应该在帧边界上分割。因为客户端可以在任何时间点加入流。其次,这些差距可能是不相关的。你怎么把文件放回去?最后,为什么不直接使用HLS或DASH而不是尝试重新发明它呢?现在,我正在客户端使用javascript来播放音频。我使用“AudioContext”类和“decodeAudioData”方法对每个块进行解码,并将解码后的块放入“AudioBufferSourceNode”以启动/播放该音频块。你所说的“间隔可能是无关的”是什么意思?我的意思是,如果解码器正在重置每个块,那么无论在哪里分割,块边界上都会有音频伪影。我强烈建议您使用媒体源扩展而不是这种方法。它的代码少得多,而且设计的目的正是为了做到这一点。包含“decodeAudioData”方法的“AudioContext”只创建一次。另外,我也尝试过这种方法,使用不同的后端实现,我将mp3文件解码为PCM格式,并向客户端发送固定数量的帧来播放音频,播放非常流畅。我一定会查看MediaSource扩展,谢谢你让我知道不同的方法。是绝对需要MP3,还是你可以使用Opus音频文件?谢谢你的建议。我还想控制客户端在服务器端请求的最大字节数,因此我想尝试一下MediaSource(这是我第一次知道)。在没有MediaSource的情况下,您仍然可以控制从服务器发送的数据。因此我设法使用MediaSource逐块流式传输音频,最后,我想问一件关于SourceBuffer的小事情。现在我使用一个SourceBuffer来保存所有的数据段,我想问一下什么时候使用多个SourceBuffer,一个看起来可以正常工作吗?