无法在 android 个浏览器中使用 php 下载文件

Not able to download files with php in android browsers

使用电脑时文件下载正常。 android 浏览器出现问题。

当我们从 android 默认浏览器下载文件时,该文件已下载但为 0.00 字节,因此技术上不存在(损坏的文件)。

当我们从任何第三方应用程序(如 Opera)下载文件时,它会给出 "file could not be downloaded." 而不是 header 错误。文件可以通过 UC 浏览器和 Chrome 和 Firefox 下载。但是在默认浏览器中仍然报错。

这是我使用的代码:

<?php
require 'php/db.php';
if(isset($_POST['file_id'])&&!empty($_POST['file_id'])){
    download_file($_POST['file_id']);
}
function download_file($id){
    global $con;
    $id = mysqli_real_escape_string($con,htmlentities($id));
    $file="SELECT file_name,file_title,file_size,down FROM files WHERE file_id= $id";
    $result = mysqli_query($con,$file);
    $row = mysqli_fetch_assoc($result);
    $name = $row['file_name'];
    $title = $row['file_title'];
    $size = $row['file_size'];
    $ext = strtoupper(ext($name));  // Function defined bellow
    $down = $row['down'];
    $newname = $title.'.'.$ext;
    $olddir = "files/".$name;
    $down++;

    if(is_file($olddir)) {
        $update_down = "UPDATE files SET down = $down WHERE file_id = '$id'";
        $update_down_result = mysqli_query($con,$update_down);

        header('Pragma: public');   // required
        header('Expires: 0');       // no cache
        header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
        header('Last-Modified: '.gmdate ('D, d M Y H:i:s', filemtime ($olddir)).' GMT');
        header('Cache-Control: private',false);
        header('Content-Type: application/octet-stream');
        header('Content-Disposition: attachment; filename="'.$newname.'"');
        header('Content-Transfer-Encoding: binary');
        header('Content-Length: '.$size);   // provide file size
        header('Connection: close');
        readfile($olddir);

        exit();
    }else header("Location: index.php?msg=Sorry!+File+could+not+be+downloaded");

}

function ext($name){
    $rut = strrev($name);
    $erut = explode('.', $rut);
    return strrev($erut[0]);
}

我们为这个函数提供文件 ID,它会在 PC 上下载文件。

谁能告诉我如何消除错误?这样用户也可以从他们的 android 手机下载文件。

可能 $size == 0;

$size = $row['file_size'];
...
$olddir = "files/".$name;

改为

$olddir = "files/".$name;
$size = filesize($olddir);

并改变

else header("Location: index.php?msg=Sorry!+File+could+not+be+downloaded");

else header("Location: index.php?msg=Sorry!+File+could+not+be+found+on+server: " . $olddir);

我得到了解决方案。 我主要改变了两件事:

  1. 使用 GET 方法而不是 Post 方法。
  2. 使用 Flush 和 ob_clean 函数来清除缓冲区。

downfile.php 的新代码如下:

<?php
    require '../php/db.php';
    ob_start();
    if(isset($_GET['file_id'])&&!empty($_GET['file_id'])){
        download_file($_GET['file_id']);
    }else die("There was an error in downloading file. Please try again later.");

    function download_file($id){
        global $con;
        $id = mysqli_real_escape_string($con,htmlentities($id));

        $file="SELECT file_name,file_title,file_size,down FROM files WHERE file_id= $id";
        $result = mysqli_query($con,$file);
        $row = mysqli_fetch_assoc($result);
        $name = $row['file_name'];
        $title = $row['file_title'];
        $ext = ext($name);
        $down = $row['down'];
        $newname = $title.'.'.$ext;
        $size = $row['file_size'];
        $down++;

        if(is_file($name)) {
            $update_down = "UPDATE files SET down = $down WHERE file_id = '$id'";
            $update_down_result = mysqli_query($con,$update_down);

            header('Content-Description: File Transfer');
            header('Content-Type: application/octet-stream');
            header('Content-Disposition: attachment; filename="'.$newname.'"');
            header('Content-Transfer-Encoding: binary');
            header('Expires: 0');
            header('Cache-Control: must-revalidate');
            header('Pragma: public');
            header('Content-Length: '.$size);
            ob_clean();
            flush();
            readfile($name);
            exit;

        }else header("Location: index.php?msg=Sorry!+File+could+not+found!");

    }

    function ext($name){
        $rut = strrev($name);
        $erut = explode('.', $rut);
        return strrev($erut[0]);
    }

?>

通过这段代码,我也可以在 android 浏览器中下载文件。

希望这可能有所帮助。 :)