>백엔드 개발 >PHP 튜토리얼 >원격 파일을 다운로드하는 PHP 소스 코드 소개

원격 파일을 다운로드하는 PHP 소스 코드 소개

不言
不言앞으로
2019-03-16 11:36:352799검색

이 글은 PHP에서 원격 파일을 다운로드하기 위한 소스 코드를 소개합니다. 필요한 친구들이 참고할 수 있기를 바랍니다.

최근에 PDF 형식의 파일을 다운로드하는 데 문제가 발생했습니다. 다운로드 후 파일을 읽거나 다운로드할 수 없습니다.

일반적인 아이디어는 먼저 원격 위치에서 파일을 다운로드한 다음 사용자의 파일을 읽고 다운로드하는 것입니다. 로컬 컴퓨터에 저장한 후 파일을 삭제하세요. 소스 코드를 직접 붙여넣으세요

원격 파일 이름을 지정할 때 영어 숫자 조합을 사용하는 것이 가장 좋습니다. 중국어 이름을 사용하지 않으면 예상치 못한 문제가 발생합니다.

압축다운로드도 포함되어 있으니 자세한 내용은 소스코드를 참고해서 공부해주세요

<?php
set_time_limit(0);
//允许下载的url
$allowed_url = [
    &#39;&#39;,
    &#39;&#39;,
    &#39;&#39;]; // 允许的url
//$file_urls = post(&#39;file_urls&#39;);
$file_urls = &#39;&#39;;//远程文件路径

$file_url_arr = explode(&#39;,&#39;, $file_urls);
$file_url_arr = array_unique($file_url_arr); // 过滤相同url

//foreach ($file_url_arr as $key => $val) {
//    $url_arr = parse_url($val);
//    if (!isset($url_arr[&#39;host&#39;]) || !in_array($url_arr[&#39;host&#39;], $allowed_url)) {
//        unset($file_url_arr[$key]);
//    }
//}
if (empty($file_url_arr)) {
    $output = array(
        &#39;status&#39; => 2,
        &#39;code&#39; => 999,
        &#39;error&#39; => &#39;未找到合法url&#39;,
    );
    exit(json_encode($output));
}

$download_dir = ROOT.&#39;download&#39;.DIRECTORY_SEPARATOR;
if(!file_exists($download_dir)) mkdir($download_dir, 0777, true);
$tmp_dir = $download_dir.time().rand(100, 999).DIRECTORY_SEPARATOR; // 文件临时存放目录

$downloader = new fileDownloader();

if($file_url_arr && !empty($file_url_arr)) $downloader->download($tmp_dir, $file_url_arr); // 下载文件

$file_lists = scandir($tmp_dir);
$file_lists = array_diff($file_lists, [&#39;.&#39;, &#39;..&#39;]);
$file_lists = array_values($file_lists); // 重置索引
if(empty($file_lists)){
    $output = array(
        &#39;status&#39; => 2,
        &#39;code&#39; => 999,
        &#39;error&#39; => &#39;无下载文件&#39;,
    );
    exit(json_encode($output));
}

//if (count($file_lists) > 1) { // 如果是多个文件就压缩
//    $file_name = $downloader->compress($tmp_dir, $subject_title);
//} else {
    $file_name = $file_lists[0]; // 如果是单个文件就直接输出
//}

$file_headers = get_headers($file_urls, 1);
header("Cache-Control: public");
header("Content-Description: File Transfer");
//header(&#39;Content-disposition: attachment; filename=&#39;.basename($file_name)); //文件名
header(&#39;Content-Type: &#39;.$file_headers[&#39;Content-Type&#39;]); //zip
header("Content-Transfer-Encoding: binary"); //二进制文件
header(&#39;Content-Length: &#39;. filesize($tmp_dir.$file_name)); //文件大小

$user_agent = $_SERVER["HTTP_USER_AGENT"];
$encoded_name = rawurlencode($file_name);
if (preg_match("/Firefox/", $user_agent)) { //火狐浏览器
    header(&#39;Content-Disposition: attachment; filename*=utf-8\&#39;\&#39;&#39;.$encoded_name);
} else { // IE, 谷歌浏览器
    header(&#39;Content-Disposition: attachment; filename="&#39; . $file_name . &#39;"&#39;);
}
ob_clean();
flush();
@readfile($tmp_dir.$file_name);
$downloader->deleteDir($tmp_dir);

//文件下载类
class fileDownloader{

    // 下载文件
    // $dir 文件存放地址,绝对路径
    // $urls 文件下载地址
    public function download($dir, $urls = array()){
        if (!file_exists($dir)) {
            mkdir($dir, 0777, true);
        }
        if (empty($urls)) {
            return;
        }

        foreach ($urls as $val) {
            $file_name_arr = explode(&#39;/&#39;, $val); // 使用 / 分隔url
            $file_name = array_pop($file_name_arr); // 弹出数组的最后一个元素,作为文件名

            // 如果以linux作为主机,需要将utf文件名转换成GBK文件名
//                if (PHP_OS != &#39;WINNT&#39;) {
//                    $file_name = mb_convert_encoding($file_name, &#39;gbk&#39;, &#39;utf-8&#39;); // 把文件名从utf-8转换为gbk
//                }
//            $file_name = mb_convert_encoding($file_name, &#39;gbk&#39;, &#39;utf-8&#39;); // 把文件名从utf-8转换为gbk

            // 下载文件
            $ch = curl_init();
            curl_setopt($ch,CURLOPT_URL,$val);
            curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
            curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 0);
            $data = curl_exec($ch);
            error_log(var_export(curl_getinfo($ch), 1));
            curl_close($ch);
            if ($data) {
                // 保存文件
                file_put_contents($dir.$file_name, $data);
            }
        }
    }

    // 压缩文件
    // $dir 扫描目录
    // $filename 压缩文件名
    public function compress($dir, $filename = false){
        if (!file_exists($dir)) {
            return false;
        }

        $file_lists = scandir($dir); // 扫描文件夹
        $file_lists = array_diff($file_lists, [&#39;.&#39;, &#39;..&#39;]); //去除上级目录和当前目录
        if (empty($file_lists)) {
            return false;
        }

        if (!$filename) {
            $filename = time().rand(111, 999).&#39;.zip&#39;;
        } else {
            $filename .= &#39;.zip&#39;;
        }

        $fullname = $dir.$filename; // 带路径的压缩文件名
        if (!file_exists($fullname)) {
            $zip = new ZipArchive();
            if ($zip->open($fullname, ZipArchive::CREATE)==TRUE) {
                foreach($file_lists as $val){
                    if(file_exists($dir.$val)){
                        $zip->addFile($dir.$val, $val);
                    }
                }
                $zip->close();
            }
        }
        return $filename;
    }

    // 递归删除文件和文件夹
    // $path 要删除的文件路径
    public function deleteDir($path)
    {
        //如果是目录则继续
        if (is_dir($path)) {
            $file_lists = scandir($path);//扫描一个文件夹内的所有文件夹和文件并返回数组
            foreach ($file_lists as $val) {//排除目录中的.和..
                if ($val != "." && $val != "..") {//如果是目录则递归子目录,继续操作
                    if (is_dir($path . $val)) {//子目录中操作删除文件夹和文件
                        self::deleteDir($path . $val . &#39;/&#39;);//目录清空后删除空文件夹
                        @rmdir($path . $val . &#39;/&#39;);
                    } else {//如果是文件直接删除
                        unlink($path . $val);
                    }
                }
            }
            @rmdir($path);
        }
    }
}

위 내용은 원격 파일을 다운로드하는 PHP 소스 코드 소개의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 csdn.net에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제