需求:保存正反面图片到指定文件夹,若文件夹不存在则自动创建,之后打包该文件夹进行下载(即压缩下载)
代码如下:

<?php
/*
 * 下载图片压缩包
 * @author CMaZen <cmazen@163.com>
 * @request https://www.52bz.la
 */
public function _uploadImgZip(){

    //上面获取下载数据链接...
    
    //存照片
    foreach($list as $_item){
    
        //此处dlfile()方法是下载图片并存放到指定目录
    
        dlfile($_item['upload_img'],"ImgZip/".$_item['ordersn']."/","正.".pathinfo($_item['upload_img'])['extension']);
        dlfile($_item['cover'],"ImgZip/".$_item['ordersn']."/","反.".pathinfo($_item['cover'])['extension']);
    }

    //文件压缩
    $zip = new \ZipArchive();
    //检测文件夹是否存在,不存在则创建
    if(!file_exists(PUBLIC_PATCH."/zip")){
        mkdir(PUBLIC_PATCH."/zip", 0777);
    }
    
    //指定压缩包路径
    $path = PUBLIC_PATCH.'/zip/'.date("H-i-s",time()).'.zip';
    
    //必须新建一个压缩文件才能往下操作
    $res = $zip->open($path, \ZipArchive::CREATE);
    
    if($res === TRUE){
        $this->addFileToZip(PUBLIC_PATCH."ImgZip", $zip); //调用方法,对要打包的根目录进行操作,并将ZipArchive的对象传递给方法
    }
    
    //关闭压缩包
    $zip->close();

    //打包下载
    header("Cache-Control: public");
    header("Content-Description: File Transfer");
    header('Content-disposition: attachment; filename=' . basename($path)); //文件名
    header("Content-Type: application/zip"); //zip格式的
    header("Content-Transfer-Encoding: binary"); //告诉浏览器,这是二进制文件
    header('Content-Length: ' . filesize($path)); //告诉浏览器,文件大小
    @readfile($path);
    if (!empty($path)) {//删除在服务器上生成的zip文件及自定义的存放下载图片的文件
        unlink($path);
        deldir(PUBLIC_PATCH."ImgZip/");
    }
    // 打包下载结束
    return $this->apiReturn($this->code_success,[],"等待下载完成");
}

/**
 * 将文件夹打包成zip文件
 */
private function addFileToZip($path, $zip)
{
    $handler = opendir($path); //打开当前文件夹由$path指定。
    /*
    循环的读取文件夹下的所有文件和文件夹
    其中$filename = readdir($handler)是每次循环的时候将读取的文件名赋值给$filename,
    为了不陷于死循环,所以还要让$filename !== false。
    一定要用!==,因为如果某个文件名如果叫'0',或者某些被系统认为是代表false,用!=就会停止循环
    */
    while (($filename = readdir($handler)) !== false) {
        if ($filename != "." && $filename != "..") {//文件夹文件名字为'.'和‘..’,不要对他们进行操作
            if (is_dir($path . "/" . $filename)) {// 如果读取的某个对象是文件夹,则递归
                $this->addFileToZip($path . "/" . $filename, $zip);
            } else { //将文件加入zip对象
                $zip->addFile($path ."/" . $filename);
            }
        }
    }
    @closedir($path);
}

/*
 * 下载图片
 * @param $file_url  需要下载的地址
 * @param $path  存储路径,默认存储在public目录下 格式如:img/
 * @param $filename  文件名
 * @param $mode  权限
 */
function dlfile($file_url, $path, $filename, $mode = 0777)
{
    //目录不存在则创建
    if (!file_exists(PUBLIC_PATCH . $path)) {
        mkdir(PUBLIC_PATCH . $path, $mode, true);
        dlfile($file_url, $path, $filename, $mode);
    } else {
        $content = file_get_contents($file_url);
        file_put_contents(PUBLIC_PATCH . $path.$filename, $content);
    }
}


注意:

使用压缩功能需要开启自带的==ZipArchive==类 开启方法如下:

windows下:

  • 首先需要从官网上下载,下载地址 [https://windows.php.net/downloads/pecl/releases/zip/ ]
  • 打开官网列表后需要查找适合自己的PHP版本和系统的zip,我的PHP版本是5.5的,这里我选择的版本号是1.13.5
  • list
  • 下载完后解压,把里面的php_zip.dll文件放到PHP的扩展文件夹里
  • set
  • 扩展文件夹路径一般都是在PHP版本文件夹里的ext文件夹,譬如我的就是D:php-5.5.38ext
  • 把php_zip.dll文件放进去后,打开PHP的配置文件php.ini,添加extension=php_zip.dll,保存后,重启apache服务器

linux下:

  • 在Linux下没有php_zip.dll这个文件(有也不会起作用的),所以需要重新编译一下php的zip模块。具体安装方法如下:
  • cd /usr/src

    wget http://pecl.php.net/get/zip

    tar -zxvf zip

    cd zip-1.x.x

    phpize

    ./configure

    make

    sudo make instal

  • 其中, 在最后使用make install命令的时候,可能需要用到root的权限,所以建议使用sudo来运行。安装完之后,屏幕上会提示zip.so的位置。然后将其记录下来,如:/usr/local/lib/php/extensions/zip.so。
  • 使用root权限修改php.ini(通常可能会在/usr/local/lib/文件夹下,不过视当初安装php而定,可以通过phpinfo()来查看):
  • 增加extension = /usr/local/lib/php/extensions/zip.so,然后同样在php.ini文件中,将 zlib.output_compression = Off 改为 zlib.output_compression = On ;
  • 重启一下Apache:apachectl restart;
  • 最后查看phpinfo是否存在下图的扩展,有则安装成功
  • phpinfo
最后修改:2023 年 07 月 25 日
您的赞赏是对我最大的支持。