2010-08-13 18 views
4

所以我有這個問題,我的下載鏈接。基本上我以前的創建下載鏈接的方法是隻有一個form ='link'的表單按鈕,並且該動作是文件的鏈接。這適用於firefox和其他人,但不適用於safari。出於某種原因,當用戶試圖從safari下載文件(excel文件)時,它只會在瀏覽器上顯示一堆ascii字符(我猜它試圖用瀏覽器讀取它)。那麼,我正在尋找另一種解決方案,它似乎使用頭是做到這一點的方式。所以現在我嘗試創建一個form ='post'和action ='download.php'的表單按鈕,其中有一個隱藏字段以及指向該文件的鏈接。它看起來像這樣在PHP中使用標題作爲下載鏈接

function showDownloadWithHeader($link){ 
    echo "<form action='download.php' method='post' >"; 
    echo "<input class='downloadButton' type='submit' value='Download Report'>"; 
    echo "<input type='hidden' name='filename' value='$link'>"; 
    echo "</form>"; 
} 

而在download.php裏我只想要用戶被要求下載文件。

<?php 
    if($_POST['filename'] == '' || empty($_POST['filename'])){ 
     exit; 
    } 

    $filename = $_POST['filename']; //the file is 2 folder down. e.g. data/stack/bla.xlsx 
    $file = $filename; 
    $extension = end(explode('.', $filename)); 
    error_reporting(E_ALL); 
    ini_set("display_errors",1); 
// echo $filename; 
// echo "<br/>"; 
// echo $extension; 
// echo filesize($filename); 
// echo "<br/>"; 
    switch($extension){ 
     case 'xls': 
      $mimeType = 'application/vnd.ms-excel'; 
      break; 
     case 'xlsx': 
      $mimeType = 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'; 
      break; 
    } 
// echo $mimeType; 
    header('Content-Description: File Transfer'); 
    header('Content-Type: ' . $mimeType); 
    header('Content-Disposition: attachment; filename='.basename($file)); 
    header('Content-Transfer-Encoding: binary'); 
    header('Expires: 0'); 
    header('Cache-Control: must-revalidate, post-check=0, pre-check=0'); 
    header('Pragma: public'); 
    header('Content-Length: ' . filesize($file)); 
    ob_clean(); 
    flush(); 
    readfile($filename); 
    exit; 
?> 

我看到php.net下的這個解決方案在readfile()函數下,但它似乎沒有爲我工作。我在本地主機上執行此操作。

+0

它以什麼方式'不工作'?任何錯誤?文件是否存在?你說「這個文件是2個文件夾」,但是你使用'$ filename'原樣? – MrWhite 2010-08-13 18:00:45

+0

$ filename已經考慮到了2個文件夾。 $ filename ='data/orange/orange.xlsx' 它只是向我展示一個空白頁面,並不要求我下載該文件。 – denniss 2010-08-13 18:09:28

回答

5

像這樣的東西很好。

header("Pragma: public", true); 
header("Expires: 0"); // set expiration time 
header("Cache-Control: must-revalidate, post-check=0, pre-check=0"); 
header("Content-Type: application/force-download"); 
header("Content-Type: application/octet-stream"); 
header("Content-Type: application/download"); 
header("Content-Disposition: attachment; filename=".basename($file)); 
header("Content-Transfer-Encoding: binary"); 
header("Content-Length: ".filesize($file)); 
die(file_get_contents($file)); 
+1

什麼是應用程序/強制下載和應用程序/下載?他們不是有效的常見的MIME類型,他們可能會在一些瀏覽器/程序中使用,但通常不會 – 2010-08-13 18:21:40

+0

你是我的救星! – denniss 2010-08-13 18:23:01

+1

它們可能是瀏覽器特定的標題。這段劇本已經在我的圖書館裏呆了一段時間 - 它還沒有讓我失望。 – 2010-08-13 18:33:20

3

如果我理解你正確的腳本工作正常,也就是說,如果瀏覽器識別MIME類型:

'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' 

話,就說明它在瀏覽器(無論它是否顯示正確的是別的東西)

既然你想迫使它在瀏覽器中顯示使用MIME類型,而非下載:

'application/octet-stream' 

這應該適用於所有瀏覽器,並強制下載,而不是在瀏覽器中顯示。