【问题标题】:audio.duration returns Infinity on Safari when mp3 is served from PHP当从 PHP 提供 mp3 时,audio.duration 在 Safari 上返回 Infinity
【发布时间】:2012-03-09 05:11:40
【问题描述】:

所以,我有一个 php 脚本,可以将我的 mp3 文件发送到 html5 的音频标签。问题是在 Safari 中,audio.duration 标签不起作用并返回无穷大。如果我将音频的 src 直接设置为文件,一切正常。但我不希望我的用户看到文件的路径。

无论如何,这就是我从 PHP 发送标头的方式。

我已经尝试过使用内容范围。这没有帮助。

if (file_exists($filename)) {
  $fp = fopen($filename, 'r');
  $etag = md5(serialize(fstat($fp)));
  fclose($fp);
  header("Content-Transfer-Encoding: binary"); 
  header("Content-Type: audio/mpeg");
  header('Content-Length: ' . (string)(filesize($filename)));
  header('Content-Disposition: inline; filename="' . $filename . '"');
  header('X-Pad: avoid browser bug');
  header('Cache-Control: no-cache');
  header('Etag: ' . $etag);

  //GetContentRange($filelength);

  readfile($filename);
  exit;
}
else {
  header($_SERVER['SERVER_PROTOCOL'].' 404 Not Found', true, 404);
  echo "no file";
}

【问题讨论】:

    标签: php safari mp3 html5-audio


    【解决方案1】:

    我遇到了同样的问题并添加了几个标题。似乎对我有用-

     header("Pragma: public");
     header("Expires: 0"); 
     header("Content-Type: audio/mpeg");
     header('Content-Length: ' . $fsize);
     header('Content-Disposition: inline; filename="' . $track2play . '"');
     header( 'Content-Range: bytes 0-'.$shortlen.'/'.$fsize); 
     header( 'Accept-Ranges: bytes');
     header('X-Pad: avoid browser bug');
     header('Cache-Control: no-cache');
     header('Etag: ' . $etag);
    

    $fsize 是文件大小,$shortlen =$filesize-1...在 Safari 5.1.4 和新 iPad 上测试...

    【讨论】:

      【解决方案2】:

      您的服务器必须启用 Range 请求。这很容易通过以下方式检查 查看您的服务器的响应中是否包含 Accept-Ranges 标题。大多数 HTML5 浏览器都支持寻找新的文件位置 在下载期间,因此服务器必须允许新范围 请求。

      无法接受字节范围请求会导致某些问题 HTML5 浏览器。通常无法从文件中读取持续时间 某些格式要求读取文件的开头和结尾 知道它的持续时间。 Chrome往往是拥有最多的浏览器 如果服务器上未启用 Range 请求,但所有 即使只是您必须等待,浏览器也会有一些问题 让所有媒体在接近结尾之前加载。

      请参阅this post,了解如何在启用范围请求的情况下提供媒体服务的 PHP 示例。

      另外,我注意到你正在使用No-Cache..

      使用服务器响应来禁用媒体的本地缓存可以 导致某些 HTML5 浏览器出现问题。这可能会导致持续时间 媒体不为人知。

      【讨论】:

        【解决方案3】:
        • 今天我浪费了大部分时间来研究这个问题,最后 出来了一个解决方案。 Safari 回归的原因 无穷大的持续时间非常有趣:看起来 Safari 请求服务器两次播放文件。首先它发送一个范围 使用这样的范围标头向服务器请求:(字节:0-1)。
        • 如果服务器没有将响应作为部分内容返回并且如果它 返回整个流,则 safari 浏览器不会设置 audio.duration 标签,这导致文件只播放一次, 它不能再次播放。
        • 我做了一个快速修复,在服务器端检查 header,如果它包含 rangeHeader 则返回它。

          String rangeHeader = request.getHeader("Range"); if(rangeHeader != null) { //just return it }

        【讨论】:

        • 嗨@smurf 我还看到了对音频链接的第一次调用,在 Range 标头中带有“字节 0-1”。但是你能更具体地说一下“退货”是什么意思吗?在这种情况下,它是什么?我可以通过在响应中使用 Content-Range 标头返回一个字节。是这个意思吗?
        • stackoverflow.com/a/55621242/2544072 我想知道完全相同的事情。在这种情况下,“它”是“正确”的 206 响应。有关更多信息,请参阅我在链接中的回答。
        猜你喜欢
        • 1970-01-01
        • 2014-04-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-11-16
        相关资源
        最近更新 更多