Путаница с заголовками PHP - PullRequest
0 голосов
/ 21 ноября 2011

Я бился головой об этом весь день. Время обратиться за помощью.

Итак, у меня есть PHP-скрипт, который является страницей загрузок. У пользователей есть файлы, которые они могут загружать в соответствии с тем, что они заказали.

Это выглядит примерно так (очевидно, что это не настоящий код, но есть кое-что - надеюсь, вы сможете понять суть)

PAGE START
if(post[getorder]){

check order exists, get order filename etc from mysql;
update download attempts in db;

$ctype="application/force-download";
header("Pragma: public"); // required
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Cache-Control: private",false); // required for certain browsers 
header("Content-Type: $ctype");
header("Content-Disposition: attachment; filename=\"".basename($filename)."\";" );
header("Content-Transfer-Encoding: binary");
header("Content-Length: ".filesize($filename));
$handle = fopen($filename, "r");
while ( $contents = fread( $handle, 1024 ) )
{
print (  $contents );
flush();
}
fclose($handle);    
$successmessage = "Your download has begun";                  
}

if($successmessage){
 echo $successmessage;
}

get users order details from db;
display div
 display form with post to post order number to script; 
 end form
end div
END PAGE

Надеюсь, это имеет смысл. Я могу поместить весь код, если это будет более полезным, но это очень старый скрипт, и я подумал, что это может быть удобнее.

Таким образом, если пользователь просто просматривает страницу, сценарий получает информацию о заказе пользователя о любых заказах, которые у него могут быть. Пользователи получают только X попыток загрузки до того, как заказ помечен как завершенный и более недоступный.

Отображает div для каждого доступного заказа, а внутри каждого div - небольшая форма. Если они нажимают на форму, она отправляет номер заказа обратно в тот же сценарий, и в этот момент я надеялся, что он просто обработает файл и продолжит отображать остальную часть страницы. Увы, нет, по-видимому, заголовки управления принудительной загрузкой и после fclose ничего не происходит.

Так что я подумал об этом, и добавил переменную в "if (post ...)" вдоль строк $ sendfile = 1, и прямо в нижней части страницы ...

if ($ sendfile == 1) {делать заголовки}

... в надежде, что страница загрузится правильно перед отправкой файла, и все будут довольны. Опять увы нет. Сначала он обслуживает файл и не перезагружает страницу.

Опять же, надеюсь, мое словосочетание имеет какой-то смысл.

Я читал, что php-скрипт сначала «делает» заголовки, поэтому не имеет значения, куда вы их поместите. Я не знаю, правда ли это, но на основании того, что я вижу, это так.

Я также пытался использовать заголовки после fclose для перенаправления на ту же страницу и использовать простой GET, чтобы скрипт отображал сообщение об успехе. Однако, если я это сделаю, перезагрузка работает, но приглашение загрузки не отображается. Даже если я посплю (10) перед перенаправлением на себя. Он просто ждет и затем перезагружается, но файл не загружается.

Повторная загрузка страницы очень важна, потому что, когда остальная часть страницы повторно получает данные заказа и отображает их, попытки загрузки должны быть увеличены на 1.

Есть ли способ достичь того, что я пытаюсь сделать? Код, который я вырезаю, становится все более хакерским, поэтому любая помощь или предложения будут очень благодарны.

1 Ответ

1 голос
/ 21 ноября 2011

На целевой странице загрузки попробуйте добавить <meta http-equiv="refresh" content="1; url=/download/file/url"> вместо использования заголовков.Это заставит браузер загрузить страницу, а затем через 1 секунду перенаправить на загрузку файла.

Кроме того, если вы обслуживаете что-то, кроме небольших файлов, я рекомендую вам проверить X-Sendfile .

...