I’m encountering a strange bug in Safari where, when I serve MP4 video through PHP (to obfuscate the file beneath the document root with a token-based authentication system), Safari for some reason fires the <video>'s onerror event, and the video never loads (I can’t get any useful information out of the event object sent to onerror — everything is undefined).
When I access the PHP script directly (i.e., the video is not embedded in a page), the video controls appear momentarily before flashing to a QuickTime question mark.
When I access the MP4 file directly, it works as expected.
What’s bizarre is that the embedded video works perfectly in the latest version of Chrome for Mac.
Here are the headers when accessed through PHP:
Connection:Keep-Alive
Content-Disposition:inline; filename="test.mp4"
Content-Length:5558749
Content-Type:video/mp4
Date:Tue, 22 Jun 2010 01:24:25 GMT
Keep-Alive:timeout=10, max=29
Server:Apache/2.2.15 (CentOS) mod_ssl/2.2.15 0.9.8l DAV/2 mod_auth_passthrough/2.1 FrontPage/5.0.2.2635
X-Powered-By:PHP/5.2.13
And here are the headers when test.mp4 is accessed directly:
Accept-Ranges:bytes
Connection:Keep-Alive
Content-Length:5558749
Content-Type:video/mp4
Date:Tue, 22 Jun 2010 01:26:45 GMT
Etag:"1c04757-54d1dd-489944c5a6400"
Keep-Alive:timeout=10, max=30
Last-Modified:Tue, 22 Jun 2010 01:25:36 GMT
Server:Apache/2.2.15 (CentOS) mod_ssl/2.2.15 0.9.8l DAV/2 mod_auth_passthrough/2.1 FrontPage/5.0.2.2635
The only differing headers are: Accept-Ranges (which I don’t think is necessary), Etag, Last-Modified, Content-Disposition, and X-Powered-By.
Not only can Chrome handle the PHP-served video fine, but when I use the same script to load the MP4 through a Flash player, it also works fine. I just can’t figure out what Safari is choking on.
EDIT: Also, when I change the content disposition to “attachment”, Safari will download the MP4 file just fine.
In the interest of anyone who comes across this question, here’s the explanation:
I asked what I thought was an unrelated question about another Safari-specifc HTML5 video problem: Single PHP “exit;” statement prevents HTML5 video in Safari.
Ultimately the problem had nothing to do with a PHP
exitstatement. In fact the problem was that I was using a$_SESSIONvariable to authenticate requests, and Safari uses a separate process to handle video playback that does not have access to the same$_SESSIONdata (unlike, say, Chrome).What was confusing was that both the original Safari process and the playback process requested the video file separately. I was only looking at the original request, which did pass the
$_SESSION-based authentication, so I assumed it wasn’t part of the problem.Anyway, if you are using
$_SESSIONdata to authenticate a request from an HTML5<video>player in Safari, check out the solution.