使用getUserMedia、socketio、nodejs和redis的流式音频

使用getUserMedia、socketio、nodejs和redis的流式音频,redis,socket.io,web-audio-api,getusermedia,Redis,Socket.io,Web Audio Api,Getusermedia,我目前正在寻找使用Web Audio API/getUserMedia的onaudioprocess块在用户录制时将音频录制“流”到后端: // (socket call to 'recordInit' called when record button is clicked // not shown here) node.onaudioprocess = function(e) { [...] socket.emit('recordStream', {

我目前正在寻找使用Web Audio API/getUserMedia的onaudioprocess块在用户录制时将音频录制“流”到后端:

  // (socket call to 'recordInit' called when record button is clicked
  // not shown here)

  node.onaudioprocess = function(e) {
     [...]
     socket.emit('recordStream', {
       some_relevant_ids: '123abc',
       pcm_data: convertFloat32ToInt16(e.inputBuffer.getChannelData(0))
     })
  }
我正在使用socketio向nodejs/express后端发送:

var wstream = null;

socket.on('recordInit', function(data) {
  wstream = fs.createWriteStream(data.some_relevant_ids + '.pcm');
})

socket.on('recordStream', function(data) {
  wstream.write(data.pcm_data);
})

socket.on('recordStop', function(data) {
  // close the wstream, convert to mp3 using lame, send to CDN
})
当用户单击“停止录制”按钮时,我向后端发出“recordStop”请求,后端将编译发送的所有pcm数据,将其转换为MP3,并将完成的产品发送到CDN

通过使用文件句柄(wstream)作为全局变量,我已经使整个过程能够很好地适用于单个用户,但我现在希望使它适用于多个同时使用的用户,因此我不能将一个公共变量用于文件句柄。我还担心对recordStream的套接字请求的顺序可能不正确,也许我需要发送一个时间戳(通过前端),并根据时间戳在末尾对recordStream数据包进行排序

TL;博士:我想知道:

  • 最好的方法是什么(存储带有时间戳的PCM数据包,并在最后一起编译)?我目前正在考虑在流媒体期间将其放入Redis,然后在最后根据时间戳按顺序检索所有内容。我不确定这是否是像Redis这样的东西的最佳实践
  • 我试着在每个记录流中打开一个新的wstream句柄,这个句柄基于我在每个请求中传递的“some_related_id”名称。然而,当大量PCM数据写入文件时,在将其转换为MP3时,它不是有效的音频文件。我真的不知道为什么那不起作用

如果有人对此有任何想法,请告诉我。谢谢

您可以在客户端找到我的
.wav
到opus数据包压缩的实现,然后在服务器端返回到
.wav
,您可以选择以
mp3
wav
格式保存录制,但当然,您需要在服务器中安装
ffmpeg