412 - Precondition Failed for files delivered with X-SendFile

1.5k views Asked by At

I got a weird behavior with larger video files that are delivered to user with X-SendFile. The server responds with 412 - Precondition Failed.

If i disable the X-SendFile everything is ok, so it's got to be related to that.

Some code:

$finfo = finfo_open(FILEINFO_MIME_TYPE);
$mime =  finfo_file($finfo, $file_path);

header("Content-type: ". $mime);
finfo_close($finfo);
header('Content-length: '.filesize($file_path));
header('Content-Disposition: inline; filename="'.basename($file_path).'"');
header('X-Sendfile: ' . $file_path );

The headers:

Request  URL:[redacted]/8c1ab69235fef2009731481d728a3c37.mp4
Request Method:GET
Status Code:412 Precondition Failed
Remote Address:192.168.100.100:80

Request:

Accept:*/*
Accept-Encoding:identity;q=1, *;q=0
Accept-Language:en-US,en;q=0.8,ro;q=0.6,de;q=0.4
Cache-Control:max-age=0
Connection:keep-alive
Cookie:PHPSESSID=rlva81b8gl98flv3r37dd0jtu4
Host:datasolutions.eleap.loc
If-Match:"57e7e64-545404121a47c"
Range:bytes=92078080-
Referer:[redacted]/8c1ab69235fef2009731481d728a3c37.mp4
User-Agent:Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36

Response:

Cache-Control:no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Connection:close
Content-Disposition:inline; filename="8c1ab69235fef2009731481d728a3c37.mp4"
Content-length:0
Content-Type:video/mp4
Date:Wed, 04 Jan 2017 11:08:23 GMT
Expires:Thu, 19 Nov 1981 08:52:00 GMT
Pragma:no-cache
Server:Apache/2.4.20 (Ubuntu)
X-Sendfile:[redacted]/8c1ab69235fef2009731481d728a3c37.mp4

I couldn't find any hint about what is the cause of this, maybe one of you guys has a clue. Thank you.

UPDATE: this only happens in Chrome.

2

There are 2 answers

0
Jim On

I'm having a similar issue (not using X-Send) when loading an mp4. I found that when I downgrade Chrome to the previous version (54) the issue goes away. The new version 55 that came out a few weeks ago seems to have introduced this problem.

1
olkid On

I just solved "412 Precondition Failed" on a group of web servers using mod_xsendfile 0.12 & Apache/mod_perl setup to deliver mp3 audio files.

Apache was setting a weak ETag on the outbound header. Chrome version >= 55 was using the ETag to check for file freshness via an HTTP_IF_MATCH header and xsendfile was responding with a 412.

My fix was to turn off ETags for the particular directory.

<Directory />
  Header unset Etag
  FileETag none
</Directory>

Alternatively, you can edit the parameters used to compute the ETag (ex. remove the INode parameter to work across a cluster of servers).

A short explanation of the details can be found here: http://joshua.schachter.org/2006/11/apache-etags

Apache Docs: http://httpd.apache.org/docs/2.2/mod/core.html#fileetag

Entity Tags: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/ETag