From ccf47841cde7e69a743a3c2a3233790817cdf562 Mon Sep 17 00:00:00 2001 From: Devil Date: Wed, 11 Aug 2021 17:30:06 +0800 Subject: [PATCH] =?UTF-8?q?zip=E6=93=8D=E4=BD=9C=E9=80=82=E9=85=8Dphp8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/service/AppMiniService.php | 79 +++++----- app/service/PaymentService.php | 84 ++++++----- app/service/PluginsAdminService.php | 211 +++++++++++++++------------ app/service/SystemUpgradeService.php | 96 ++++++------ app/service/ThemeService.php | 112 ++++++++------ app/service/UserService.php | 5 +- 6 files changed, 323 insertions(+), 264 deletions(-) diff --git a/app/service/AppMiniService.php b/app/service/AppMiniService.php index 9fa4b5e6d..1b25c05b8 100755 --- a/app/service/AppMiniService.php +++ b/app/service/AppMiniService.php @@ -228,53 +228,62 @@ class AppMiniService } // 开始解压文件 - $resource = zip_open($package_file); - while(($temp_resource = zip_read($resource)) !== false) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - if(zip_entry_open($resource, $temp_resource)) - { - // 资源文件 - $file = zip_entry_name($temp_resource); + return DataReturn('压缩包打开失败['.$resource.']', -11); + } + for($i=0; $i<$zip->numFiles; $i++) + { + // 资源文件 + $file = $zip->getNameIndex($i); - // 排除系统.开头的临时文件和目录 - if(strpos($file, '/.') !== false) + // 排除系统.开头的临时文件和目录 + if(strpos($file, '/.') !== false) + { + continue; + } + + // 排除后缀文件 + $pos = strripos($file, '.'); + if($pos !== false) + { + $info = pathinfo($file); + if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) { continue; } + } - // 排除后缀文件 - $pos = strripos($file, '.'); - if($pos !== false) + // 截取文件路径 + $file_path = $dir.substr($file, 0, strrpos($file, '/')); + + // 路径不存在则创建 + if(!is_dir($file_path)) + { + mkdir($file_path, 0777, true); + } + + // 如果不是目录则写入文件 + if(!is_dir($dir.$file)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - $info = pathinfo($file); - if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) + $file_content = stream_get_contents($stream); + if($file_content !== false) { - continue; + file_put_contents($dir.$file, $file_content); } + fclose($stream); } - - // 截取文件路径 - $file_path = $dir.substr($file, 0, strrpos($file, '/')); - - // 路径不存在则创建 - if(!is_dir($file_path)) - { - mkdir($file_path, 0777, true); - } - - // 如果不是目录则写入文件 - if(!is_dir($dir.$file)) - { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - file_put_contents($dir.$file, $file_content); - } - - // 关闭目录项 - zip_entry_close($temp_resource); } } + // 关闭zip + $zip->close(); + return DataReturn('安装成功'); } diff --git a/app/service/PaymentService.php b/app/service/PaymentService.php index 39fe9a4fa..245ddf80e 100755 --- a/app/service/PaymentService.php +++ b/app/service/PaymentService.php @@ -496,65 +496,71 @@ class PaymentService } // 开始解压文件 - $resource = zip_open($package_file); - if(!is_resource($resource)) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - return DataReturn('压缩包打开失败['.$resource.']', -10); + return DataReturn('压缩包打开失败['.$resource.']', -11); } $success = 0; $error = 0; - while(($temp_resource = zip_read($resource)) !== false) + for($i=0; $i<$zip->numFiles; $i++) { - if(zip_entry_open($resource, $temp_resource)) + // 资源文件 + $file = $zip->getNameIndex($i); + + // 排除临时文件和临时目录 + if(strpos($file, '/.') === false && strpos($file, '__') === false) { - // 当前压缩包中项目名称 - $file = zip_entry_name($temp_resource); - - // 排除临时文件和临时目录 - if(strpos($file, '/.') === false && strpos($file, '__') === false) + // 忽略非php文件 + if(substr($file, -4) != '.php') { - // 忽略非php文件 - if(substr($file, -4) != '.php') - { - $error++; - continue; - } + $error++; + continue; + } - // 文件名称 - $payment = str_replace(array('.', '/', '\\', ':'), '', substr($file, 0, -4)); + // 文件名称 + $payment = str_replace(array('.', '/', '\\', ':'), '', substr($file, 0, -4)); - // 是否已有存在插件 - if(file_exists(self::$payment_dir.$payment)) - { - $error++; - continue; - } else { - $file = self::$payment_dir.$payment.'.php'; - } + // 是否已有存在插件 + if(file_exists(self::$payment_dir.$payment)) + { + $error++; + continue; + } - // 如果不是目录则写入文件 - if(!is_dir($file)) + // 如果不是目录则写入文件 + $new_file = self::$payment_dir.$payment.'.php'; + if(!is_dir($new_file)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - if(@file_put_contents($file, $file_content) !== false) + $file_content = stream_get_contents($stream); + if($file_content !== false) { - // 文件校验 - $config = self::GetPaymentConfig($payment); - if($config === false) + if(@file_put_contents($new_file, $file_content) !== false) { - $error++; - @unlink($file); - } else { - $success++; + // 文件校验 + $config = self::GetPaymentConfig($payment); + if($config === false) + { + $error++; + @unlink($new_file); + } else { + $success++; + } } } + fclose($stream); } } } } + // 关闭zip + $zip->close(); if($success > 0) { diff --git a/app/service/PluginsAdminService.php b/app/service/PluginsAdminService.php index 6ce0993f1..d2a99ff1b 100755 --- a/app/service/PluginsAdminService.php +++ b/app/service/PluginsAdminService.php @@ -1062,129 +1062,148 @@ php; $plugins = ''; // 开始解压文件 - $resource = zip_open($package_file); - if(!is_resource($resource)) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - return DataReturn('压缩包打开失败['.$resource.']', -10); + return DataReturn('压缩包打开失败['.$resource.']', -11); } - while(($temp_resource = zip_read($resource)) !== false) + // 文件第一个目录为当前插件名称 + $entry = $zip->statIndex(0); + $file = $entry['name']; + //根据第一个文件是目录,还是包含namespace payment,判断插件类型 + if(str_ends_with($file, '/')) { - if(zip_entry_open($resource, $temp_resource)) + //获取plugins + $plugins = substr($file, 0, strpos($file, '/')); + + // 业务类型处理 + switch($type) { - // 当前压缩包中项目名称 - $file = zip_entry_name($temp_resource); - - // 获取包名 - if(empty($plugins)) - { - // 应用名称 - $plugins = substr($file, 0, strpos($file, '/')); - if(empty($plugins)) + // 上传安装 + case 0 : + // 应用不存在则添加 + $ret = self::PluginsVerification($plugins); + if($ret['code'] != 0) { - // 应用名称为空、则校验是否为支付插件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - if(stripos($file_content, 'namespace payment') !== false) - { - return DataReturn('支付插件请到[ 网站管理->支付方式 ]模块里面去上传安装', -1); - } - - // 不是支付插件则提示插件包错误 - return DataReturn('插件包有误', -30); + return $ret; } - // 业务类型处理 - switch($type) + // 应用是否存在 + if(self::PluginsExist($plugins)) { - // 上传安装 - case 0 : - // 应用不存在则添加 - $ret = self::PluginsVerification($plugins); - if($ret['code'] != 0) - { - zip_entry_close($temp_resource); - return $ret; - } + return DataReturn('应用名称已存在['.$plugins.']', -1); + } + break; - // 应用是否存在 - if(self::PluginsExist($plugins)) - { - zip_entry_close($temp_resource); - return DataReturn('应用名称已存在['.$plugins.']', -1); - } - break; + // 更新 + case 1 : + // 应用是否存在 + if($plugins != $plugins_old) + { + return DataReturn('应用标识与指定不一致['.$plugins.'<>'.$plugins_old.']', -1); + } + break; + } + } else { + // 应用名称为空、则校验是否为支付插件 + $stream = $zip->getStream($file); + if($stream !== false) + { + $file_content = stream_get_contents($stream); + if($file_content !== false) + { + if(stripos($file_content, 'namespace payment') !== false) + { + return DataReturn('支付插件请到[ 网站管理->支付方式 ]模块里面去上传安装', -1); + } + } + fclose($stream); + } - // 更新 - case 1 : - // 应用是否存在 - if($plugins != $plugins_old) + // 不是支付插件则提示插件包错误 + return DataReturn('插件包有误', -30); + } + + // 应用文件处理 + $success = 0; + for($i=0; $i<$zip->numFiles; $i++) + { + // 资源文件 + $file = $zip->getNameIndex($i); + + // 排除临时文件和临时目录 + if(strpos($file, '/.') === false && strpos($file, '__') === false) + { + // 文件包对应系统所在目录 + $is_has_find = false; + foreach($dir_list as $dir_key=>$dir_value) + { + if(strpos($file, $dir_key) !== false) + { + // 仅控制器模块支持php文件 + if($dir_key != '_controller_') + { + // 排除后缀文件 + $pos = strripos($file, '.'); + if($pos !== false) { - zip_entry_close($temp_resource); - return DataReturn('应用标识与指定不一致['.$plugins.'<>'.$plugins_old.']', -1); + $info = pathinfo($file); + if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) + { + continue; + } } - break; + } + + // 匹配成功文件路径处理、跳出循环 + $new_file = str_replace($plugins.'/'.$dir_key.'/', '', $dir_value.$file); + $is_has_find = true; + break; } } - // 排除临时文件和临时目录 - if(strpos($file, '/.') === false && strpos($file, '__') === false) + // 没有匹配到则指定目录跳过 + if($is_has_find == false) { - // 文件包对应系统所在目录 - $is_has_find = false; - foreach($dir_list as $dir_key=>$dir_value) + continue; + } + + // 截取文件路径 + $file_path = substr($new_file, 0, strrpos($new_file, '/')); + + // 路径不存在则创建 + \base\FileUtil::CreateDir($file_path); + + // 如果不是目录则写入文件 + if(!is_dir($new_file)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - if(strpos($file, $dir_key) !== false) + $file_content = stream_get_contents($stream); + if($file_content !== false) { - // 仅控制器模块支持php文件 - if($dir_key != '_controller_') + if(file_put_contents($new_file, $file_content)) { - // 排除后缀文件 - $pos = strripos($file, '.'); - if($pos !== false) - { - $info = pathinfo($file); - if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) - { - continue; - } - } + $success++; } - - // 匹配成功文件路径处理、跳出循环 - $file = str_replace($plugins.'/'.$dir_key.'/', '', $dir_value.$file); - $is_has_find = true; - break; } + fclose($stream); } - - // 没有匹配到则指定目录跳过 - if($is_has_find == false) - { - continue; - } - - // 截取文件路径 - $file_path = substr($file, 0, strrpos($file, '/')); - - // 路径不存在则创建 - \base\FileUtil::CreateDir($file_path); - - // 如果不是目录则写入文件 - if(!is_dir($file)) - { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - @file_put_contents($file, $file_content); - } - - // 关闭目录项 - zip_entry_close($temp_resource); } } } + // 关闭zip + $zip->close(); + // 未匹配成功一个文件则认为插件包无效 + if($success <= 0) + { + return DataReturn('无效的插件包', -1); + } return DataReturn('success', 0, $plugins); } diff --git a/app/service/SystemUpgradeService.php b/app/service/SystemUpgradeService.php index 691710d0f..40ee3a656 100644 --- a/app/service/SystemUpgradeService.php +++ b/app/service/SystemUpgradeService.php @@ -134,10 +134,11 @@ class SystemUpgradeService public static function UpgradePackageHandle($package_file) { // 开始解压文件 - $resource = zip_open($package_file); - if(!is_resource($resource)) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - return DataReturn('压缩包打开失败['.$resource.']', -10); + return DataReturn('压缩包打开失败['.$resource.']', -11); } // 需要处理的文件 @@ -146,29 +147,29 @@ class SystemUpgradeService 'power.sql', ]; - while(($temp_resource = zip_read($resource)) !== false) + for($i=0; $i<$zip->numFiles; $i++) { - if(zip_entry_open($resource, $temp_resource)) - { - // 当前压缩包中项目名称 - $file = zip_entry_name($temp_resource); + // 资源文件 + $file = $zip->getNameIndex($i); - // 排除临时文件和临时目录 - if(strpos($file, '/.') === false && !is_dir($file) && in_array($file, $handle_file_arr)) + // 排除临时文件和临时目录 + if(strpos($file, '/.') === false && !is_dir($file) && in_array($file, $handle_file_arr)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); + $file_content = stream_get_contents($stream); if(!empty($file_content)) { SqlConsoleService::Implement(['sql'=>$file_content]); } - - // 关闭目录项 - zip_entry_close($temp_resource); + fclose($stream); } } } + // 关闭zip + $zip->close(); return DataReturn('success', 0); } @@ -185,48 +186,51 @@ class SystemUpgradeService public static function SystemPackageHandle($package_file) { // 开始解压文件 - $resource = zip_open($package_file); - if(!is_resource($resource)) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - return DataReturn('压缩包打开失败['.$resource.']', -10); + return DataReturn('压缩包打开失败['.$resource.']', -11); } - - while(($temp_resource = zip_read($resource)) !== false) + for($i=0; $i<$zip->numFiles; $i++) { - if(zip_entry_open($resource, $temp_resource)) + // 资源文件 + $file = $zip->getNameIndex($i); + + // 排除临时文件和临时目录 + if(!empty($file) && strpos($file, '/.') === false) { - // 当前压缩包中项目名称 - $file = zip_entry_name($temp_resource); + // 文件实际位置 + $new_file = ROOT.$file; - // 排除临时文件和临时目录 - if(!empty($file) && strpos($file, '/.') === false) + // 截取文件路径 + $file_path = substr($new_file, 0, strrpos($new_file, '/')); + + // 路径不存在则创建、根目录文件不创建目录 + if(strpos($file, '/') !== false) { - // 文件实际位置 - $file_new = ROOT.$file; + \base\FileUtil::CreateDir($file_path); + } - // 截取文件路径 - $file_path = substr($file_new, 0, strrpos($file_new, '/')); - - // 路径不存在则创建、根目录文件不创建目录 - if(strpos($file, '/') !== false) + // 如果不是目录则写入文件 + if(!is_dir($new_file)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - \base\FileUtil::CreateDir($file_path); + $file_content = stream_get_contents($stream); + if($file_content !== false) + { + file_put_contents($new_file, $file_content); + } + fclose($stream); } - - // 如果不是目录则写入文件 - if(!is_dir($file_new)) - { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - @file_put_contents($file_new, $file_content); - } - - // 关闭目录项 - zip_entry_close($temp_resource); } } } + // 关闭zip + $zip->close(); return DataReturn('success', 0); } diff --git a/app/service/ThemeService.php b/app/service/ThemeService.php index 7ceb4789a..323b02fd1 100755 --- a/app/service/ThemeService.php +++ b/app/service/ThemeService.php @@ -156,70 +156,88 @@ class ThemeService ]; // 开始解压文件 - $resource = zip_open($package_file); - while(($temp_resource = zip_read($resource)) !== false) + $zip = new \ZipArchive(); + $resource = $zip->open($package_file); + if($resource != true) { - if(zip_entry_open($resource, $temp_resource)) + return DataReturn('压缩包打开失败['.$resource.']', -11); + } + $success = 0; + for($i=0; $i<$zip->numFiles; $i++) + { + // 资源文件 + $file = $zip->getNameIndex($i); + + // 排除临时文件和临时目录 + if(strpos($file, '/.') === false && strpos($file, '__') === false) { - // 当前压缩包中项目名称 - $file = zip_entry_name($temp_resource); - - // 排除临时文件和临时目录 - if(strpos($file, '/.') === false && strpos($file, '__') === false) + // 文件包对应系统所在目录 + $is_has_find = false; + foreach($dir_list as $dir_key=>$dir_value) { - // 文件包对应系统所在目录 - $is_has_find = false; - foreach($dir_list as $dir_key=>$dir_value) + if(strpos($file, $dir_key) !== false) { - if(strpos($file, $dir_key) !== false) - { - // 匹配成功文件路径处理、跳出循环 - $file = str_replace($dir_key.'/', '', $dir_value.$file); - $is_has_find = true; - break; - } + // 匹配成功文件路径处理、跳出循环 + $new_file = str_replace($dir_key.'/', '', $dir_value.$file); + $is_has_find = true; + break; } + } - // 没有匹配到则指定目录跳过 - if($is_has_find == false) + // 没有匹配到则指定目录跳过 + if($is_has_find == false) + { + continue; + } + + // 排除后缀文件 + $pos = strripos($file, '.'); + if($pos !== false) + { + $info = pathinfo($file); + if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) { continue; } + } - // 排除后缀文件 - $pos = strripos($file, '.'); - if($pos !== false) + // 截取文件路径 + $file_path = substr($new_file, 0, strrpos($new_file, '/')); + + // 路径不存在则创建 + if(!is_dir($file_path)) + { + mkdir($file_path, 0777, true); + } + + // 如果不是目录则写入文件 + if(!is_dir($new_file)) + { + // 读取这个文件 + $stream = $zip->getStream($file); + if($stream !== false) { - $info = pathinfo($file); - if(isset($info['extension']) && in_array($info['extension'], self::$exclude_ext)) + $file_content = stream_get_contents($stream); + if($file_content !== false) { - continue; + if(file_put_contents($new_file, $file_content)) + { + $success++; + } } + fclose($stream); } - - // 截取文件路径 - $file_path = substr($file, 0, strrpos($file, '/')); - - // 路径不存在则创建 - if(!is_dir($file_path)) - { - mkdir($file_path, 0777, true); - } - - // 如果不是目录则写入文件 - if(!is_dir($file)) - { - // 读取这个文件 - $file_size = zip_entry_filesize($temp_resource); - $file_content = zip_entry_read($temp_resource, $file_size); - file_put_contents($file, $file_content); - } - - // 关闭目录项 - zip_entry_close($temp_resource); } } } + // 关闭zip + $zip->close(); + + // 未匹配成功一个文件则认为插件包无效 + if($success <= 0) + { + return DataReturn('无效的主题包', -1); + } return DataReturn('安装成功', 0); } diff --git a/app/service/UserService.php b/app/service/UserService.php index 064b140af..0b074956f 100755 --- a/app/service/UserService.php +++ b/app/service/UserService.php @@ -2431,7 +2431,10 @@ class UserService $user = (!empty($data) && array_key_exists($user_ids, $data)) ? $data[$user_ids] : []; } } else { - $user = self::UserHandle($user); + if(!empty($user)) + { + $user = self::UserHandle($user); + } } return $user;