So, I have a php script that sends my mp3 file to the audio tag of html5. The problem is that in Safari, the audio.duration tag does not work and returns infinity. If I set the src of the audio directly to the file everything works fine. But I don't want my users to see the path to the file.
Anyways, this is how I'm sending my headers from the PHP.
I have already tried having the content-ranges. That did not help.
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";
}
I was having the same issue and added a couple headers. Seems to work for me -
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 is file size and $shortlen =$filesize-1...tested on Safari 5.1.4 and on new iPad...
Your server must enable Range requests. This is easy to check for by
seeing if your server's response includes the Accept-Ranges in its
header. Most HTML5 browsers enable seeking to new file positions
during a download, so the server must allow the new Range to be
requested.
Failure to accept byte Range requests will cause problems on some
HTML5 browsers. Often the duration cannot be read from the file as
some formats require that the start and end of the file is read to
know its duration. Chrome tends to be the browser that has most
problems if the Range request is not enabled on the server, but all
browsers will have some issue even if it is only that you have to wait
for all the media to load before jumping close to the end.
See this post for a PHP example of how to serve media with Range Requests enabled.
Also, i noticed you are using No-Cache
..
Using the server response to disable the local cache of media can
cause problems with some HTML5 browsers. This can cause the duration
of the media to be unknown.