【问题标题】:HTML5 audio seek is not working properly. Throws Response Content-Length mismatch ExceptionHTML5 音频搜索无法正常工作。引发响应内容长度不匹配异常
【发布时间】:2017-12-14 04:54:37
【问题描述】:

我正在尝试将音频文件流式传输到 Angular 应用程序,其中 html5 音频元素和 src 设置为我的 api 端点(例如 /audio/234)。我的后端是用 .NET Core 2.0 实现的。我已经实现了这种流式传输:.NET Core| MVC pass audio file to html5 player. Enable seeking

如果我没有在音频开始播放时立即搜索到文件结尾,则搜索有效。我使用音频元素的自动播放属性立即开始播放音频元素有足够的数据。因此,在我的情况下,音频元素在我寻找时还没有所有数据,因此它对我的 API 进行了新的 GET。在这种情况下,我的后端日志中有这个异常:

失败:Microsoft.AspNetCore.Server.Kestrel[13] [1] 连接 ID“0HL9V370HAF39”,请求 ID“0HL9V370HAF39:00000001”:应用程序抛出了未处理的异常。 [1] System.InvalidOperationException:响应内容长度不匹配:写入的字节太少(0 of 6126919)。

这是我的音频控制器 GET 方法。

byte[] audioArray = new byte[0];
//Here I load audio file from cloud
long fSize = audioArray.Length;
long startbyte = 0;
long endbyte = fSize - 1;
int statusCode = 200;
var rangeRequest = Request.Headers["Range"].ToString();
_logger.LogWarning(rangeRequest);
if (rangeRequest != "")
{
    string[] range = Request.Headers["Range"].ToString().Split(new char[] { '=', '-' });
    startbyte = Convert.ToInt64(range[1]);
    if (range.Length > 2 && range[2] != "") endbyte = Convert.ToInt64(range[2]);
    if (startbyte != 0 || endbyte != fSize - 1 || range.Length > 2 && range[2] == "")
    { statusCode = 206; }
}

_logger.LogWarning(startbyte.ToString());
long desSize = endbyte - startbyte + 1;
_logger.LogWarning(desSize.ToString());
_logger.LogWarning(fSize.ToString());
Response.StatusCode = statusCode;
Response.ContentType = "audio/mp3";
Response.Headers.Add("Content-Accept", Response.ContentType);
Response.Headers.Add("Content-Length", desSize.ToString());
Response.Headers.Add("Content-Range", string.Format("bytes {0}-{1}/{2}", startbyte, endbyte, fSize));
Response.Headers.Add("Accept-Ranges", "bytes");
Response.Headers.Remove("Cache-Control");
var stream = new MemoryStream(audioArray, (int)startbyte, (int)desSize);

return new FileStreamResult(stream, Response.ContentType)
{
    FileDownloadName = track.Name
};

我错过了一些标题还是什么?

我在 .NET Core 1.1 中没有遇到此异常,但我不确定这只是巧合和/或错误的测试。但是,如果有人知道 .NET Core 中与流相关的内容是否发生了变化,我将不胜感激。

【问题讨论】:

    标签: html angular audio .net-core mp3


    【解决方案1】:

    现在,当我进行更多研究时,我发现了这个:https://docs.microsoft.com/en-us/aspnet/core/aspnetcore-2.0 看起来增强的 HTTP 标头支持 - 标头。它是这样说的

    如果应用程序访问者请求带有 Range Request 标头的内容,ASP.NET 将识别并处理该标头。如果可以部分传递请求的内容,ASP.NET 将适当地跳过并仅返回请求的字节集。你不需要在你的方法中编写任何特殊的处理程序来适应或处理这个特性;它会自动为您处理。

    所以当我迁移到 .NET Core 1.1 到 2.0 时,我需要做的只是一些清理工作,因为这些头文件已经有了处理程序。

    byte[] audioArray = new byte[0];
    //Here I get my MP3 file from cloud
    var stream = new MemoryStream(audioArray);
    return new FileStreamResult(stream, "audio/mp3")
    {
        FileDownloadName = track.Name
    };
    

    【讨论】:

      【解决方案2】:

      问题出在标题中。我不确切知道哪个标头不正确或者我的流初始化不正确,但现在它正在工作。我用了这个https://stackoverflow.com/a/35920244/8081009。我所做的唯一更改将其重命名为 AudioStreamResult。然后我像这样使用它:

      Response.ContentType = "audio/mp3";
      Response.Headers.Add("Content-Accept", Response.ContentType);
      Response.Headers.Remove("Cache-Control");
      var stream = new MemoryStream(audioArray);
      
      return new AudioStreamResult(stream, Response.ContentType)
      {
          FileDownloadName = track.Name
      };
      

      请注意,我将完整流传递给 AudioStreamResult。

      var stream = new MemoryStream(audioArray);
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2014-09-20
        • 1970-01-01
        • 1970-01-01
        • 2018-04-03
        • 2017-12-28
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多