1054 lines
36 KiB
PHP
1054 lines
36 KiB
PHP
![]() |
<?php
|
|||
|
/*
|
|||
|
* @link http://kodcloud.com/
|
|||
|
* @author warlee | e-mail:kodcloud@qq.com
|
|||
|
* @copyright warlee 2014.(Shanghai)Co.,Ltd
|
|||
|
* @license http://kodcloud.com/tools/license/license.txt
|
|||
|
*/
|
|||
|
|
|||
|
/**
|
|||
|
* 系统函数: filesize(),file_exists(),pathinfo(),rname(),unlink(),filemtime(),is_readable(),is_wrieteable();
|
|||
|
* 获取文件详细信息 file_info($fileName)
|
|||
|
* 获取文件夹详细信息 path_info($dir)
|
|||
|
* 递归获取文件夹信息 path_info_more($dir,&$fileCount=0,&$pathCount=0,&$size=0)
|
|||
|
* 获取文件夹下文件列表 path_list($dir)
|
|||
|
* 路径当前文件[夹]名 get_path_this($path)
|
|||
|
* 获取路径父目录 get_path_father($path)
|
|||
|
* 删除文件 del_file($file)
|
|||
|
* 递归删除文件夹 del_dir($dir)
|
|||
|
* 递归复制文件夹 copy_dir($source, $dest)
|
|||
|
* 创建目录 mk_dir($dir, $mode = 0777)
|
|||
|
* 文件大小格式化 size_format($bytes, $precision = 2)
|
|||
|
* 判断是否绝对路径 path_is_absolute( $path )
|
|||
|
* 扩展名的文件类型 ext_type($ext)
|
|||
|
* 文件下载 file_download($file)
|
|||
|
* 文件下载到服务器 file_download_this($from, $fileName)
|
|||
|
* 获取文件(夹)权限 get_mode($file) //rwx_rwx_rwx [文件名需要系统编码]
|
|||
|
* 上传文件(单个,多个) upload($fileInput, $path = './');//
|
|||
|
* 获取配置文件项 get_config($file, $ini, $type="string")
|
|||
|
* 修改配置文件项 update_config($file, $ini, $value,$type="string")
|
|||
|
* 写日志到LOG_PATH下 write_log('dd','default|.自建目录.','log|error|warning|debug|info|db')
|
|||
|
*/
|
|||
|
|
|||
|
// 传入参数为程序编码时,有传出,则用程序编码,
|
|||
|
// 传入参数没有和输出无关时,则传入时处理成系统编码。
|
|||
|
function iconv_app($str){
|
|||
|
global $config;
|
|||
|
$result = iconv_to($str,$config['systemCharset'], $config['appCharset']);
|
|||
|
return $result;
|
|||
|
}
|
|||
|
function iconv_system($str){
|
|||
|
//去除中文空格UTF8; windows下展示异常;过滤文件上传、新建文件等时的文件名
|
|||
|
//文件名已存在含有该字符时,没有办法操作.
|
|||
|
$char_empty = "\xc2\xa0";
|
|||
|
if(strpos($str,$char_empty) !== false){
|
|||
|
$str = str_replace($char_empty," ",$str);
|
|||
|
}
|
|||
|
|
|||
|
global $config;
|
|||
|
$result = iconv_to($str,$config['appCharset'], $config['systemCharset']);
|
|||
|
$result = path_filter($result);
|
|||
|
return $result;
|
|||
|
}
|
|||
|
function iconv_to($str,$from,$to){
|
|||
|
if (strtolower($from) == strtolower($to)){
|
|||
|
return $str;
|
|||
|
}
|
|||
|
if (!function_exists('iconv')){
|
|||
|
return $str;
|
|||
|
}
|
|||
|
//尝试用mb转换;android环境部分问题解决
|
|||
|
if(function_exists('mb_convert_encoding')){
|
|||
|
$result = @mb_convert_encoding($str,$to,$from);
|
|||
|
}else{
|
|||
|
$result = @iconv($from, $to, $str);
|
|||
|
}
|
|||
|
if(strlen($result)==0){
|
|||
|
return $str;
|
|||
|
}
|
|||
|
return $result;
|
|||
|
}
|
|||
|
function path_filter($path){
|
|||
|
if(strtoupper(substr(PHP_OS, 0,3)) != 'WIN'){
|
|||
|
return $path;
|
|||
|
}
|
|||
|
$notAllow = array('*','?','"','<','>','|');//去除 : D:/
|
|||
|
return str_replace($notAllow,' ', $path);
|
|||
|
}
|
|||
|
|
|||
|
//filesize 解决大于2G 大小问题
|
|||
|
//http://stackoverflow.com/questions/5501451/php-x86-how-to-get-filesize-of-2-gb-file-without-external-program
|
|||
|
//32位系统; 修改编译php实现兼容支持; https://demo.kodcloud.com/#s/735psg0g
|
|||
|
//源码修改: zend_off_t(文件定位)修改为64位int64_t; ftell返回值类型加宽; fseek传入值处理,校验类型处理; fstate处理;
|
|||
|
function get_filesize($path){
|
|||
|
if(PHP_INT_SIZE >= 8 ) return @filesize($path);
|
|||
|
$fp = fopen($path,"r");
|
|||
|
if(!$fp) return 0;
|
|||
|
if (fseek($fp, 0, SEEK_END) === 0) {
|
|||
|
$result = 0.0;
|
|||
|
$step = 0x7FFFFFFF;
|
|||
|
while ($step > 0) {
|
|||
|
if (fseek($fp, - $step, SEEK_CUR) === 0) {
|
|||
|
$result += floatval($step);
|
|||
|
} else {
|
|||
|
$step >>= 1;
|
|||
|
}
|
|||
|
}
|
|||
|
}else{
|
|||
|
static $iswin;
|
|||
|
if (!isset($iswin)) {
|
|||
|
$iswin = (strtoupper(substr(PHP_OS, 0, 3)) == 'WIN');
|
|||
|
}
|
|||
|
static $exec_works;
|
|||
|
if (!isset($exec_works)) {
|
|||
|
$exec_works = (function_exists('exec') && !ini_get('safe_mode') && @exec('echo EXEC') == 'EXEC');
|
|||
|
}
|
|||
|
if ($iswin && class_exists("COM")) {
|
|||
|
try {
|
|||
|
$fsobj = new COM('Scripting.FileSystemObject');
|
|||
|
$f = $fsobj->GetFile( realpath($path) );
|
|||
|
$size = $f->Size;
|
|||
|
} catch (Exception $e) {
|
|||
|
$size = null;
|
|||
|
}
|
|||
|
if (is_numeric($size)) {
|
|||
|
$result = $size;
|
|||
|
}
|
|||
|
}else if ($exec_works){
|
|||
|
$cmd = ($iswin) ? "for %F in (\"$path\") do @echo %~zF" : "stat -c%s \"$path\"";
|
|||
|
@exec($cmd, $output);
|
|||
|
if (is_array($output) && is_numeric($size = trim(implode("\n", $output)))) {
|
|||
|
$result = $size;
|
|||
|
}
|
|||
|
}else{
|
|||
|
$result = filesize($path);
|
|||
|
}
|
|||
|
}
|
|||
|
fclose($fp);
|
|||
|
return $result;
|
|||
|
}
|
|||
|
|
|||
|
function filesize_64($file){
|
|||
|
return get_filesize($file);
|
|||
|
}
|
|||
|
function ftell_64($fp){
|
|||
|
return ftell($fp);
|
|||
|
}
|
|||
|
function fseek_64($fp,$pose=0,$from=SEEK_SET,$first=true){
|
|||
|
return fseek($fp,$pose,$from);// php 编译兼容支持;
|
|||
|
|
|||
|
if(PHP_INT_SIZE >= 8){return fseek($fp,$pose,$first);}
|
|||
|
if($first) fseek($fp,0,SEEK_SET);
|
|||
|
$intMax = PHP_INT_MAX;
|
|||
|
$pos = floatval($pose);
|
|||
|
if($pos <= $intMax){
|
|||
|
fseek($fp,$pos,SEEK_CUR);
|
|||
|
}else {
|
|||
|
fseek($fp,$intMax,SEEK_CUR);
|
|||
|
$pos -= $intMax;
|
|||
|
fseek_64($fp,$pos,SEEK_CUR,false);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// 文件复制,支持32位系统复制大于4G文件; 命令行调用,比fopen/fwrite快;
|
|||
|
function copy_64($from,$dest){
|
|||
|
if(!$from || !$dest || !file_exists($from)) return false;
|
|||
|
if(!$GLOBALS['config']['settings']['bigFileForce']){
|
|||
|
// 改php源代码后影响copy的逻辑(循环,暂未适配); 使用命令行获取;
|
|||
|
$result = @copy($from,$dest);
|
|||
|
if($result) return true;
|
|||
|
}
|
|||
|
|
|||
|
// 命令行调用复制;
|
|||
|
if(function_exists("shell_exec")){
|
|||
|
$command = 'cp ';
|
|||
|
if($GLOBALS['config']['systemOS'] == 'windows'){
|
|||
|
$command = 'COPY ';
|
|||
|
}
|
|||
|
$command .= escapeShell($from).' '.escapeShell($dest);
|
|||
|
@shell_exec($command);
|
|||
|
}else{
|
|||
|
/*
|
|||
|
$size = filesize_64($from);
|
|||
|
$fromFp = @fopen($from,'r');
|
|||
|
$destFp = @fopen($dest,'w+');
|
|||
|
$chunk = 1024*1024*5;$start = 0;
|
|||
|
while($start < $size && $size>= 0) {
|
|||
|
$read = fread($fromFp,$chunk);
|
|||
|
if(!strlen($read)){break;}
|
|||
|
fwrite($destFp,$read);
|
|||
|
$start += strlen($read);
|
|||
|
}
|
|||
|
fclose($fromFp);fclose($destFp);
|
|||
|
*/
|
|||
|
}
|
|||
|
return @file_exists($dest);
|
|||
|
}
|
|||
|
|
|||
|
//文件是否存在,区分文件大小写
|
|||
|
function file_exists_case( $fileName ){
|
|||
|
if(file_exists($fileName) === false){
|
|||
|
return false;
|
|||
|
}
|
|||
|
$status = false;
|
|||
|
$directoryName = dirname( $fileName );
|
|||
|
$fileArray = glob( $directoryName . '/*', GLOB_NOSORT);
|
|||
|
if ( preg_match( "/\\\|\//", $fileName) ){
|
|||
|
$array = preg_split("/\\\|\//", $fileName);
|
|||
|
$fileName = $array[ count( $array ) -1 ];
|
|||
|
}
|
|||
|
foreach($fileArray as $file ){
|
|||
|
if(preg_match("/{$fileName}/i", $file)){
|
|||
|
$output = "{$directoryName}/{$fileName}";
|
|||
|
$status = true;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
return $status;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
function path_readable($path){
|
|||
|
$result = intval(is_readable($path));
|
|||
|
if($result){
|
|||
|
return $result;
|
|||
|
}
|
|||
|
$mode = get_mode($path);
|
|||
|
if( $mode &&
|
|||
|
strlen($mode) == 18 &&
|
|||
|
substr($mode,-9,1) == 'r'){// -rwx rwx rwx(0777)
|
|||
|
return true;
|
|||
|
}
|
|||
|
return false;
|
|||
|
}
|
|||
|
function path_writeable($path){
|
|||
|
$result = intval(is_writeable($path));
|
|||
|
if($result) return $result;
|
|||
|
|
|||
|
$mode = get_mode($path);
|
|||
|
if( $mode &&
|
|||
|
strlen($mode) == 18 &&
|
|||
|
substr($mode,-8,1) == 'w'){// -rwx rwx rwx (0777)
|
|||
|
return true;
|
|||
|
}
|
|||
|
return false;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 获取文件详细信息
|
|||
|
* 文件名从程序编码转换成系统编码,传入utf8,系统函数需要为gbk
|
|||
|
*/
|
|||
|
function file_info($path){
|
|||
|
$info = array(
|
|||
|
'name' => iconv_app(get_path_this($path)),
|
|||
|
'path' => iconv_app($path),
|
|||
|
'ext' => get_path_ext($path),
|
|||
|
'type' => 'file',
|
|||
|
'mode' => get_mode($path),
|
|||
|
'atime' => @fileatime($path), //最后访问时间
|
|||
|
'ctime' => @filectime($path), //创建时间
|
|||
|
'mtime' => @filemtime($path), //最后修改时间
|
|||
|
'isReadable' => path_readable($path),
|
|||
|
'isWriteable' => path_writeable($path),
|
|||
|
'size' => get_filesize($path)
|
|||
|
);
|
|||
|
return $info;
|
|||
|
}
|
|||
|
/**
|
|||
|
* 获取文件夹细信息
|
|||
|
*/
|
|||
|
function folder_info($path){
|
|||
|
$info = array(
|
|||
|
'name' => iconv_app(get_path_this($path)),
|
|||
|
'path' => iconv_app(rtrim($path,'/').'/'),
|
|||
|
'type' => 'folder',
|
|||
|
'mode' => get_mode($path),
|
|||
|
'atime' => @fileatime($path), //访问时间
|
|||
|
'ctime' => @filectime($path), //创建时间
|
|||
|
'mtime' => @filemtime($path), //最后修改时间
|
|||
|
'isReadable' => path_readable($path),
|
|||
|
'isWriteable' => path_writeable($path)
|
|||
|
);
|
|||
|
return $info;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
/**
|
|||
|
* 获取一个路径(文件夹&文件) 当前文件[夹]名
|
|||
|
* test/11/ ==>11 test/1.c ==>1.c
|
|||
|
*/
|
|||
|
function get_path_this($path){
|
|||
|
$path = str_replace('\\','/', rtrim($path,'/'));
|
|||
|
$pos = strrpos($path,'/');
|
|||
|
if($pos === false){
|
|||
|
return $path;
|
|||
|
}
|
|||
|
return substr($path,$pos+1);
|
|||
|
}
|
|||
|
/**
|
|||
|
* 获取一个路径(文件夹&文件) 父目录
|
|||
|
* /test/11/==>/test/ /test/1.c ==>/www/test/
|
|||
|
*/
|
|||
|
function get_path_father($path){
|
|||
|
$path = str_replace('\\','/', rtrim($path,'/'));
|
|||
|
$pos = strrpos($path,'/');
|
|||
|
if($pos === false){
|
|||
|
return $path;
|
|||
|
}
|
|||
|
return substr($path, 0,$pos+1);
|
|||
|
}
|
|||
|
/**
|
|||
|
* 获取扩展名
|
|||
|
*/
|
|||
|
function get_path_ext($path){
|
|||
|
$name = get_path_this($path);
|
|||
|
$ext = '';
|
|||
|
if(strstr($name,'.')){$ext = substr($name,strrpos($name,'.')+1);}
|
|||
|
$isMatch = preg_match("/[0-9a-zA-Z_]+/",$ext,$match);// 只允许数字字母和下划线
|
|||
|
return ($isMatch && $match[0]) ? strtolower($match[0]):'';
|
|||
|
}
|
|||
|
function get_path_ext_name($path){
|
|||
|
$name = get_path_this($path);
|
|||
|
$ext = get_path_ext($name);
|
|||
|
return $ext ? substr($name,0,strripos($name,'.'.$ext)):$name;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
|
|||
|
//自动获取不重复文件(夹)名
|
|||
|
//如果传入$file_add 则检测存在则自定重命名 a.txt 为a{$file_add}.txt
|
|||
|
function get_filename_auto($path,$file_add = "",$same_file_type='replace'){
|
|||
|
if (is_dir($path) && $same_file_type!=REPEAT_RENAME_FOLDER) {//文件夹则忽略
|
|||
|
return $path;
|
|||
|
}
|
|||
|
//重名处理
|
|||
|
if (file_exists($path)) {
|
|||
|
if ($same_file_type== REPEAT_REPLACE) {
|
|||
|
return $path;
|
|||
|
}else if($same_file_type==REPEAT_SKIP){
|
|||
|
return false;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
$i=1;
|
|||
|
$father = get_path_father($path);
|
|||
|
$name = get_path_this($path);
|
|||
|
$ext = get_path_ext($name);
|
|||
|
if(is_dir($path)){
|
|||
|
$ext = '';
|
|||
|
}
|
|||
|
if (strlen($ext)>0) {
|
|||
|
$ext='.'.$ext;
|
|||
|
$name = substr($name,0,strlen($name)-strlen($ext));
|
|||
|
}
|
|||
|
while(file_exists($path)){
|
|||
|
if ($file_add != '') {
|
|||
|
$path = $father.$name.$file_add.$ext;
|
|||
|
$file_add.='-';
|
|||
|
}else{
|
|||
|
$path = $father.$name.'('.$i.')'.$ext;
|
|||
|
$i++;
|
|||
|
}
|
|||
|
}
|
|||
|
return $path;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 获取文件夹详细信息,文件夹属性时调用,包含子文件夹数量,文件数量,总大小
|
|||
|
*/
|
|||
|
function path_info($path){
|
|||
|
if (!file_exists($path)) return false;
|
|||
|
$pathinfo = _path_info_more($path);//子目录文件大小统计信息
|
|||
|
$folderinfo = folder_info($path);
|
|||
|
return array_merge($pathinfo,$folderinfo);
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 检查名称是否合法
|
|||
|
*/
|
|||
|
function path_check($path){
|
|||
|
$check = array('/','\\',':','*','?','"','<','>','|');
|
|||
|
$path = rtrim($path,'/');
|
|||
|
$path = get_path_this($path);
|
|||
|
foreach ($check as $v) {
|
|||
|
if (strstr($path,$v)) {
|
|||
|
return false;
|
|||
|
}
|
|||
|
}
|
|||
|
return true;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 递归获取文件夹信息: 子文件夹数量,文件数量,总大小
|
|||
|
*/
|
|||
|
function _path_info_more($dir, &$fileCount = 0, &$pathCount = 0, &$size = 0){
|
|||
|
if (!$dh = @opendir($dir)) return array('fileCount'=>0,'folderCount'=>0,'size'=>0);
|
|||
|
while (($file = readdir($dh)) !== false) {
|
|||
|
if ($file =='.' || $file =='..') continue;
|
|||
|
$fullpath = $dir . "/" . $file;
|
|||
|
if (!is_dir($fullpath)) {
|
|||
|
$fileCount ++;
|
|||
|
$size += get_filesize($fullpath);
|
|||
|
} else {
|
|||
|
_path_info_more($fullpath, $fileCount, $pathCount, $size);
|
|||
|
$pathCount ++;
|
|||
|
}
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
$pathinfo['fileCount'] = $fileCount;
|
|||
|
$pathinfo['folderCount'] = $pathCount;
|
|||
|
$pathinfo['size'] = $size;
|
|||
|
return $pathinfo;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
/**
|
|||
|
* 获取多选文件信息,包含子文件夹数量,文件数量,总大小,父目录权限
|
|||
|
*/
|
|||
|
function path_info_muti($list,$timeType){
|
|||
|
$list = is_array($list) ? $list : array();
|
|||
|
if (count($list) == 1) {
|
|||
|
if ($list[0]['type']=="folder"){
|
|||
|
return path_info($list[0]['path'],$timeType);
|
|||
|
}else{
|
|||
|
return file_info($list[0]['path'],$timeType);
|
|||
|
}
|
|||
|
}
|
|||
|
$pathinfo = array(
|
|||
|
'fileCount' => 0,
|
|||
|
'folderCount' => 0,
|
|||
|
'size' => 0,
|
|||
|
'father_name' => '',
|
|||
|
'mod' => ''
|
|||
|
);
|
|||
|
foreach ($list as $val){
|
|||
|
if ($val['type'] == 'folder') {
|
|||
|
$pathinfo['folderCount'] ++;
|
|||
|
$temp = path_info($val['path']);
|
|||
|
$pathinfo['folderCount'] += $temp['folderCount'];
|
|||
|
$pathinfo['fileCount'] += $temp['fileCount'];
|
|||
|
$pathinfo['size'] += $temp['size'];
|
|||
|
}else{
|
|||
|
$pathinfo['fileCount']++;
|
|||
|
$pathinfo['size'] += get_filesize($val['path']);
|
|||
|
}
|
|||
|
}
|
|||
|
$father_name = get_path_father($list[0]['path']);
|
|||
|
$pathinfo['mode'] = get_mode($father_name);
|
|||
|
return $pathinfo;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 获取文件夹下列表信息
|
|||
|
* dir 包含结尾/ d:/wwwroot/test/
|
|||
|
* 传入需要读取的文件夹路径,为程序编码
|
|||
|
*/
|
|||
|
function path_list($dir,$listFile=true,$checkChildren=false){
|
|||
|
$dir = rtrim($dir,'/').'/';
|
|||
|
if (!is_dir($dir) || !($dh = @opendir($dir))){
|
|||
|
return array('folderList'=>array(),'fileList'=>array());
|
|||
|
}
|
|||
|
$folderList = array();$fileList = array();//文件夹与文件
|
|||
|
while (($file = readdir($dh)) !== false) {
|
|||
|
if ($file =='.' || $file =='..' || $file == ".svn") continue;
|
|||
|
$fullpath = $dir . $file;
|
|||
|
if (is_dir($fullpath)) {
|
|||
|
$info = folder_info($fullpath);
|
|||
|
if($checkChildren){
|
|||
|
$info['isParent'] = path_haschildren($fullpath,$listFile);
|
|||
|
}
|
|||
|
$folderList[] = $info;
|
|||
|
} else if($listFile) {//是否列出文件
|
|||
|
$info = file_info($fullpath);
|
|||
|
if($checkChildren) $info['isParent'] = false;
|
|||
|
$fileList[] = $info;
|
|||
|
}
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
return array('folderList' => $folderList,'fileList' => $fileList);
|
|||
|
}
|
|||
|
|
|||
|
// 判断文件夹是否含有子内容【区分为文件或者只筛选文件夹才算】
|
|||
|
function path_haschildren($dir,$checkFile=false){
|
|||
|
$dir = rtrim($dir,'/').'/';
|
|||
|
if (!$dh = @opendir($dir)) return false;
|
|||
|
while (($file = readdir($dh)) !== false){
|
|||
|
if ($file =='.' || $file =='..') continue;
|
|||
|
$fullpath = $dir.$file;
|
|||
|
if ($checkFile) {//有子目录或者文件都说明有子内容
|
|||
|
if(@is_file($fullpath) || is_dir($fullpath.'/')){
|
|||
|
closedir($dh);
|
|||
|
return true;
|
|||
|
}
|
|||
|
}else{//只检查有没有文件
|
|||
|
if(@is_dir($fullpath.'/')){//解决部分主机报错问题
|
|||
|
closedir($dh);
|
|||
|
return true;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
return false;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 删除文件 传入参数编码为操作系统编码. win--gbk
|
|||
|
*/
|
|||
|
function del_file($fullpath){
|
|||
|
if (!@unlink($fullpath)) { // 删除不了,尝试修改文件权限
|
|||
|
@chmod($fullpath, DEFAULT_PERRMISSIONS);
|
|||
|
if (!@unlink($fullpath)) {return false;}
|
|||
|
} else {
|
|||
|
return true;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 删除文件夹 传入参数编码为操作系统编码. win--gbk
|
|||
|
*/
|
|||
|
function del_dir($dir){
|
|||
|
if(!file_exists($dir) || !is_dir($dir)) return true;
|
|||
|
if (!$dh = opendir($dir)) return false;
|
|||
|
set_timeout();
|
|||
|
while (($file = readdir($dh)) !== false) {
|
|||
|
if ($file =='.' || $file =='..') continue;
|
|||
|
$fullpath = rtrim($dir, '/') . '/' . $file;
|
|||
|
if (!is_dir($fullpath)) {
|
|||
|
if (!@unlink($fullpath)) { // 删除不了,尝试修改文件权限
|
|||
|
@chmod($fullpath, DEFAULT_PERRMISSIONS);
|
|||
|
if (!@unlink($fullpath)) {return false;}
|
|||
|
}
|
|||
|
} else {
|
|||
|
if (!del_dir($fullpath)) {
|
|||
|
@chmod($fullpath, DEFAULT_PERRMISSIONS);
|
|||
|
if (!del_dir($fullpath)) return false;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
if (rmdir($dir)) {
|
|||
|
return true;
|
|||
|
} else {
|
|||
|
return false;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
/**
|
|||
|
* 复制文件夹
|
|||
|
* eg:将D:/wwwroot/下面wordpress复制到
|
|||
|
* D:/wwwroot/www/explorer/0000/del/1/
|
|||
|
* 末尾都不需要加斜杠,复制到地址如果不加源文件夹名,
|
|||
|
* 就会将wordpress下面文件复制到D:/wwwroot/www/explorer/0000/del/1/下面
|
|||
|
* $from = 'D:/wwwroot/wordpress';
|
|||
|
* $to = 'D:/wwwroot/www/explorer/0000/del/1/wordpress';
|
|||
|
*/
|
|||
|
|
|||
|
function copy_dir($source, $dest){
|
|||
|
if (!$dest) return false;
|
|||
|
if (is_dir($source) && $source == substr($dest,0,strlen($source))) return false;//防止父文件夹拷贝到子文件夹,无限递归
|
|||
|
|
|||
|
set_timeout();
|
|||
|
$result = true;
|
|||
|
if (is_file($source)) {
|
|||
|
if ($dest[strlen($dest)-1] == '/') {
|
|||
|
$__dest = $dest . "/" . basename($source);
|
|||
|
} else {
|
|||
|
$__dest = $dest;
|
|||
|
}
|
|||
|
$result = copy_64($source,$__dest);
|
|||
|
@chmod($__dest, DEFAULT_PERRMISSIONS);
|
|||
|
}else if(is_dir($source)) {
|
|||
|
if ($dest[strlen($dest)-1] == '/') {
|
|||
|
$dest = $dest . basename($source);
|
|||
|
}
|
|||
|
if (!is_dir($dest)) {
|
|||
|
@mkdir($dest,DEFAULT_PERRMISSIONS);
|
|||
|
}
|
|||
|
if (!$dh = opendir($source)) return false;
|
|||
|
while (($file = readdir($dh)) !== false) {
|
|||
|
if ($file =='.' || $file =='..') continue;
|
|||
|
$result = copy_dir($source . "/" . $file, $dest . "/" . $file);
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
}
|
|||
|
return $result;
|
|||
|
}
|
|||
|
|
|||
|
function move_file($source,$dest,$repeat_add,$repeat_type){
|
|||
|
if($source == $dest) return true;
|
|||
|
if ($dest[strlen($dest)-1] == '/') {
|
|||
|
$dest = $dest . "/" . basename($source);
|
|||
|
}
|
|||
|
if(file_exists($dest)){
|
|||
|
$dest = get_filename_auto($dest,$repeat_add,$repeat_type);//同名文件处理规则
|
|||
|
}
|
|||
|
@chmod($source, DEFAULT_PERRMISSIONS);
|
|||
|
$result = intval(@rename($source,$dest));
|
|||
|
if (! $result) { // windows部分ing情况处理
|
|||
|
$result = intval(@copy_64($source,$dest));
|
|||
|
if ($result) {
|
|||
|
@unlink($source);
|
|||
|
}
|
|||
|
}
|
|||
|
return $result;
|
|||
|
}
|
|||
|
function move_path($source,$dest,$repeat_add='',$repeat_type='replace'){
|
|||
|
if (!$dest || !file_exists($source)) return false;
|
|||
|
if ( is_dir($source) ){
|
|||
|
//防止父文件夹拷贝到子文件夹,无限递归
|
|||
|
if($source == substr($dest,0,strlen($source))){
|
|||
|
return false;
|
|||
|
}
|
|||
|
//地址相同
|
|||
|
if(rtrim($source,'/') == rtrim($dest,'/')){
|
|||
|
return false;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
set_timeout();
|
|||
|
if(is_file($source)){
|
|||
|
return move_file($source,$dest,$repeat_add,$repeat_type);
|
|||
|
}
|
|||
|
recursion_dir($source,$dirs,$files,-1,0);
|
|||
|
|
|||
|
@mkdir($dest);
|
|||
|
foreach($dirs as $f){
|
|||
|
$path = $dest.'/'.substr($f,strlen($source));
|
|||
|
if(!file_exists($path)){
|
|||
|
mk_dir($path);
|
|||
|
}
|
|||
|
}
|
|||
|
$file_success = 0;
|
|||
|
foreach($files as $f){
|
|||
|
$path = $dest.'/'.substr($f,strlen($source));
|
|||
|
$file_success += move_file($f,$path,$repeat_add,$repeat_type);
|
|||
|
}
|
|||
|
foreach($dirs as $f){
|
|||
|
rmdir($f);
|
|||
|
}
|
|||
|
@rmdir($source);
|
|||
|
if($file_success == count($files)){
|
|||
|
del_dir($source);
|
|||
|
return true;
|
|||
|
}
|
|||
|
return false;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 创建目录
|
|||
|
*
|
|||
|
* @param string $dir
|
|||
|
* @param int $mode
|
|||
|
* @return bool
|
|||
|
*/
|
|||
|
function mk_dir($dir, $mode = 0755){
|
|||
|
if (!$dir) return false;
|
|||
|
if (is_dir($dir) || @mkdir($dir, $mode)){
|
|||
|
return true;
|
|||
|
}
|
|||
|
if (!mk_dir(dirname($dir), $mode)){
|
|||
|
return false;
|
|||
|
}
|
|||
|
return @mkdir($dir, $mode);
|
|||
|
}
|
|||
|
|
|||
|
/*
|
|||
|
* 获取文件&文件夹列表(支持文件夹层级)
|
|||
|
* path : 文件夹 $dir ——返回的文件夹array files ——返回的文件array
|
|||
|
* $deepest 是否完整递归;$deep 递归层级
|
|||
|
*/
|
|||
|
function recursion_dir($path,&$dir,&$file,$deepest=-1,$deep=0){
|
|||
|
$path = rtrim($path,'/').'/';
|
|||
|
if (!is_array($file)) $file=array();
|
|||
|
if (!is_array($dir)) $dir=array();
|
|||
|
if (!is_dir($path)) return false;
|
|||
|
if (!$dh = opendir($path)) return false;
|
|||
|
while(($val=readdir($dh)) !== false){
|
|||
|
if ($val=='.' || $val=='..') continue;
|
|||
|
$value = strval($path.$val);
|
|||
|
if (is_file($value)){
|
|||
|
$file[] = $value;
|
|||
|
}else if(is_dir($value)){
|
|||
|
$dir[]=$value;
|
|||
|
if ($deepest==-1 || $deep<$deepest){
|
|||
|
recursion_dir($value."/",$dir,$file,$deepest,$deep+1);
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
return true;
|
|||
|
}
|
|||
|
function dir_list($path){
|
|||
|
recursion_dir($path,$dirs,$files);
|
|||
|
return array_merge($dirs,$files);
|
|||
|
}
|
|||
|
|
|||
|
/*
|
|||
|
* $search 为包含的字符串
|
|||
|
* is_content 表示是否搜索文件内容;默认不搜索
|
|||
|
* is_case 表示区分大小写,默认不区分
|
|||
|
*/
|
|||
|
function path_search($path,$search,$is_content=false,$file_ext='',$isCase=false){
|
|||
|
$result = array();
|
|||
|
$result['fileList'] = array();
|
|||
|
$result['folderList'] = array();
|
|||
|
if(!$path) return $result;
|
|||
|
|
|||
|
$ext_arr = explode("|",$file_ext);
|
|||
|
recursion_dir($path,$dirs,$files,-1,0);
|
|||
|
$strpos = 'stripos';//是否区分大小写
|
|||
|
if ($isCase) $strpos = 'strpos';
|
|||
|
$result_num = 0;
|
|||
|
$result_num_max = 2000;//搜索文件内容,限制最多匹配条数
|
|||
|
foreach($files as $f){
|
|||
|
if($result_num >= $result_num_max){
|
|||
|
$result['error_info'] = $result_num_max;
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
//若指定了扩展名则只在匹配扩展名文件中搜索
|
|||
|
$ext = get_path_ext($f);
|
|||
|
if($file_ext != '' && !in_array($ext,$ext_arr)){
|
|||
|
continue;
|
|||
|
}
|
|||
|
|
|||
|
//搜索内容则不搜索文件名
|
|||
|
if ($is_content) {
|
|||
|
if(!is_text_file($ext)) continue; //在限定中或者不在bin中
|
|||
|
$search_info = file_search($f,$search,$isCase);
|
|||
|
if($search_info !== false){
|
|||
|
$result_num += count($search_info['searchInfo']);
|
|||
|
$result['fileList'][] = $search_info;
|
|||
|
}
|
|||
|
}else{
|
|||
|
$path_this = get_path_this($f);
|
|||
|
if ($strpos($path_this,iconv_system($search)) !== false){//搜索文件名;
|
|||
|
$result['fileList'][] = file_info($f);
|
|||
|
$result_num ++;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
if (!$is_content && $file_ext == '' ) {//没有指定搜索文件内容,且没有限定扩展名,才搜索文件夹
|
|||
|
foreach($dirs as $f){
|
|||
|
$path_this = get_path_this($f);
|
|||
|
if ($strpos($path_this,iconv_system($search)) !== false){
|
|||
|
$result['folderList'][]= array(
|
|||
|
'name' => iconv_app(get_path_this($f)),
|
|||
|
'path' => iconv_app($f)
|
|||
|
);
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
return $result;
|
|||
|
}
|
|||
|
|
|||
|
// 文件搜索;返回行及关键词附近行
|
|||
|
function file_search($path,$search,$isCase){
|
|||
|
if(@filesize($path) >= 1024*1024*20) return false;
|
|||
|
$content = file_get_contents($path);
|
|||
|
$result = content_search($content,$search,$isCase);
|
|||
|
unset($content);
|
|||
|
if(!$result) return false;
|
|||
|
|
|||
|
$info = file_info($path);
|
|||
|
$info['searchInfo'] = $result;
|
|||
|
return $info;
|
|||
|
}
|
|||
|
|
|||
|
// 文本搜索;返回行及关键词附近行
|
|||
|
function content_search(&$content,$search,$isCase,$maxCount=1000,$isUtf8=false){
|
|||
|
$strpos = 'stripos';//是否区分大小写
|
|||
|
if( $isCase) $strpos = 'strpos';
|
|||
|
if( $strpos($content,"\0") > 0 ){return false;}// 不是文本文档
|
|||
|
if(!$isUtf8){
|
|||
|
//搜索关键字为纯英文则直接搜索;含有中文则转为utf8再搜索,为兼容其他文件编码格式
|
|||
|
$charset = get_charset($content);
|
|||
|
$notAscii = preg_match("/[\x7f-\xff]/", $search);
|
|||
|
if($notAscii && !in_array($charset,array('utf-8','ascii'))){
|
|||
|
$content = iconv_to($content,$charset,'utf-8');
|
|||
|
}
|
|||
|
}
|
|||
|
//文件没有搜索到目标直接返回
|
|||
|
if ($strpos($content,$search) === false) return false;
|
|||
|
|
|||
|
$fileSize = strlen($content);
|
|||
|
$arrSearch = array();$pose = 0; // 匹配结果所在位置
|
|||
|
$searchLen = strlen($search);
|
|||
|
// 通过分割方式快速得到数组,加速处理; 比一次strpos快(去除最后一项)
|
|||
|
$arraySplit = explode(strtolower($search),strtolower($content));
|
|||
|
$arraySplitCount = count($arraySplit);
|
|||
|
foreach ($arraySplit as $i => $chunk){
|
|||
|
if(count($arrSearch) >= $maxCount){break;}
|
|||
|
if($i == $arraySplitCount - 1){break;}
|
|||
|
$arrSearch[] = strlen($chunk) + $pose;
|
|||
|
$pose = $pose + strlen($chunk) + $searchLen;
|
|||
|
}
|
|||
|
|
|||
|
// $arrSearch = array();$pose = 0;
|
|||
|
// while ( $pose !== false) {
|
|||
|
// $pose = stripos($content,$search, $pose);
|
|||
|
// if($pose === false){break;}
|
|||
|
// $arrSearch[] = $pose;$pose ++;
|
|||
|
// if(count($arrSearch) >= $maxCount){break;}
|
|||
|
// }
|
|||
|
|
|||
|
$arrLine = array();$pose = 0;
|
|||
|
while($pose !== false) {
|
|||
|
$pose = strpos($content, "\n", $pose);
|
|||
|
if($pose === false){break;}
|
|||
|
$arrLine[] = $pose;$pose ++;
|
|||
|
}
|
|||
|
$arrLine[] = $fileSize;//文件只有一行而且没有换行,则构造虚拟换行
|
|||
|
$result = array();// [2,10,22,45,60] [20,30,40,50,55]
|
|||
|
$lenSearch = count($arrSearch);
|
|||
|
$lenLine = count($arrLine);
|
|||
|
for ($i=0,$line=0; $i < $lenSearch && $line < $lenLine; $line++) {
|
|||
|
while ( $arrSearch[$i] <= $arrLine[$line]) {
|
|||
|
$curPose = $arrSearch[$i];//行截取字符串
|
|||
|
$lenLeft = 80;$lenRight = 120;$curFrom = $curPose + $searchLen;
|
|||
|
$curMin = $curPose - $lenLeft <= 0 ? 0 : $curPose - $lenLeft;
|
|||
|
$curMax = $curFrom + $lenRight >= $fileSize ? $fileSize : $curFrom + $lenRight;
|
|||
|
$from = $curMin; $to = $curMax;
|
|||
|
|
|||
|
//中文避免截断(向前 向后找到分隔符后终止) // ',','、',
|
|||
|
$token = array("\r","\n",'。');
|
|||
|
$strLeft = substr($content,$curMin,($curPose - $curMin));
|
|||
|
$strRight = substr($content,$curFrom,$lenRight);
|
|||
|
foreach($token as $char){
|
|||
|
$leftFind = strrpos($strLeft,$char);
|
|||
|
$rightFind = strpos($strRight,$char);
|
|||
|
if($leftFind !== false){$from = max($from, $curMin + $leftFind + strlen($char));}
|
|||
|
if($rightFind !== false){$to = min($to, $curFrom + $rightFind + strlen($char));}
|
|||
|
}
|
|||
|
|
|||
|
// $lineStr = substr($content,$from,$to - $from);
|
|||
|
$lineStr = utf8Repair(substr($content,$from,$to - $from));
|
|||
|
$result[] = array('line'=>$line+1,'str'=>trim($lineStr));
|
|||
|
if(count($result) >= $maxCount) return $result;
|
|||
|
if(++$i >= $lenSearch ){break;}
|
|||
|
}
|
|||
|
}
|
|||
|
return $result;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
/**
|
|||
|
* 修改文件、文件夹权限
|
|||
|
* @param $path 文件(夹)目录
|
|||
|
* @return :string
|
|||
|
*/
|
|||
|
function chmod_path($path,$mod=0){
|
|||
|
$mod = $mod == 0 ? DEFAULT_PERRMISSIONS:$mod;
|
|||
|
if (!file_exists($path)) return false;
|
|||
|
if (is_file($path)) return @chmod($path,$mod);
|
|||
|
if (!$dh = @opendir($path)) return false;
|
|||
|
while (($file = readdir($dh)) !== false){
|
|||
|
if ($file =='.' || $file =='..') continue;
|
|||
|
$fullpath = $path . '/' . $file;
|
|||
|
chmod_path($fullpath,$mod);
|
|||
|
@chmod($fullpath,$mod);
|
|||
|
}
|
|||
|
closedir($dh);
|
|||
|
return @chmod($path,$mod);
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 文件大小格式化
|
|||
|
*
|
|||
|
* @param $ :$bytes, int 文件大小
|
|||
|
* @param $ :$precision int 保留小数点
|
|||
|
* @return :string
|
|||
|
*/
|
|||
|
function size_format($bytes, $precision = 2){
|
|||
|
if ($bytes == 0) return "0 B";
|
|||
|
$unit = array(
|
|||
|
'PB' => 1099511627776*1024, // pow( 1024, 5)
|
|||
|
'TB' => 1099511627776, // pow( 1024, 4)
|
|||
|
'GB' => 1073741824, // pow( 1024, 3)
|
|||
|
'MB' => 1048576, // pow( 1024, 2)
|
|||
|
'kB' => 1024, // pow( 1024, 1)
|
|||
|
'B ' => 1, // pow( 1024, 0)
|
|||
|
);
|
|||
|
foreach ($unit as $un => $mag) {
|
|||
|
if (doubleval($bytes) >= $mag)
|
|||
|
return round($bytes / $mag, $precision).' '.$un;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 判断路径是不是绝对路径
|
|||
|
* 返回true('/foo/bar','c:\windows').
|
|||
|
*
|
|||
|
* @return 返回true则为绝对路径,否则为相对路径
|
|||
|
*/
|
|||
|
function path_is_absolute($path){
|
|||
|
if (realpath($path) == $path)// *nux 的绝对路径 /home/my
|
|||
|
return true;
|
|||
|
if (strlen($path) == 0 || $path[0] == '.')
|
|||
|
return false;
|
|||
|
if (preg_match('#^[a-zA-Z]:\\\\#', $path))// windows 的绝对路径 c:\aaa\
|
|||
|
return true;
|
|||
|
return (bool)preg_match('#^[/\\\\]#', $path); //绝对路径 运行 / 和 \绝对路径,其他的则为相对路径
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
function is_text_file($ext){
|
|||
|
$extArray = array(
|
|||
|
'3ds','4th','_adb','a','abap','abc','ac','acl','ada','adb','adoc','ahk','alda','am','apex','apl','app','apple-app-site-association','applescript','aql','arcconfig','arclint','as','asc','asciidoc','asl','asm','asn','asn1','asp','aspx','ass','astylerc','atom','authors','aw',
|
|||
|
'b','babelrc','bak','bash','bash_history','bash_logout','bash_profile','bashrc','bat','bf','bib','brew_all_commands','bro','build','bzl',
|
|||
|
'c','c9search_results','cabal','cakefile','cbl','cc','cer','cf','cfg','cfm','cgi','changelog','changes','cirru','cl','classpath','clj','cljc','cljs','cljx','cls','cmake','in','cmd','cnf','cob','coffee','commit_editmsg','compile','component','conf','config','configure','container','contributing','copying','coveragerc','cpp','cpy','cql','cr','credits','cs','csd','cshtml','cson','csproj','css','csv','ctp','curly','cxx','cyp','cypher','crt',
|
|||
|
'd','dae','darglint','dart','def','depcomp','description','desktop','di','diff','dist','dockerfile','dockerfile-dist','dockerfile-master','dockerignore','dot','dox','drl','dsl','dtd','dummy','dxf','dxf-check','dxfb-check','dyalog','dyl','dylan',
|
|||
|
'e','ecl','edi','editorconfig','edn','eex','ejs','el','elm','empty','epp','erb','erl','err','eslintignore','ex','example','exclude','exs',
|
|||
|
'f','f77','f90','f95','factor','feature','fetch_head','filters','fingerprint','for','forth','frag','frt','fs','fsi','fsl','fsscript','fsx','fth','ftl','fun','fx',
|
|||
|
'gbs','gcode','ge','gemfile','gemspec','gendocs_template','geojson','git-credentials','git-version-gen','gitattributes','gitconfig','gitflow_export','gitignore','gitignore_global','gitkeep','gitlog-to-changelog','gitmodules','glsl','gltf','gnumakefile','go','gql','gradle','groovy','gss','guardfile','guess','gunmakefile','gypi',
|
|||
|
'h','hacking','haml','handlebars','hbs','head','hgignore_global','hh','hjson','hlean','hpp','hrl','hs','hta','htaccess','htgroups','htm','html','html.eex','html.erb','htpasswd','http','hx','hxml','hxx',
|
|||
|
'i','iml','in','inc','inf','ini','ino','install','install-sh','installversion','intr','inx','io','po',
|
|||
|
'j2','jack','jade','java','ji','jinja','jinja2','jl','jq','js','jsdtscope','jshintrc','jsm','json','json-check','json5','jsonld','jsp','jssm','jssm_state','jsx',
|
|||
|
'key','keys','kml','ksh','kt','kts',
|
|||
|
'la','latex','latte','ldr','lean','less','lesshst','lgc','lhs','license','liquid','lisp','list','lnk','local','localized','lock','log','logic','lp','lql','lrc','ls','lsl','lsp','ltx','lua','lucene',
|
|||
|
'm','m3u8','m4','magnet','mailcap','make','makefile','manifest','map','markdown','mask','master','mathml','matlab','mbox','mc','md','mdx','mediawiki','mel','meta','mf','mime','missing','mixal','mjs','mkd','ml','mli','mll','mly','mm','mml','mo','mod','module','mps','msc','mscgen','mscin','msgenny','mtl','mush','mustache','mvnw','mycli-history','myclirc','mymetadata','mysql','mysql_history','mz',
|
|||
|
'name','nb','nc','ncx','netrwhist','news','nginx','nim','nix','nj','njk','nmf','node_repl_history','npmignore','npmrc','nq','nsh','nsi','nt','nunjs','nunjucks','nut',
|
|||
|
'oak','obj','ocamlmakefile','oexe','opf','orc','orig_head','out','owners','oz',
|
|||
|
'p','p6','packed-refs','packs','page','pas','patch','pbxproj','pc','pch','pearrc','pem','pgp','pgsql','php','php3','php4','php5','php7','phps','phpt','phtml','pid','pig','pl','pl6','plantuml','plg','plist','plistpch','pls','plugins','ply','pm','pm6','pp','praat','praatscript','prefs','prettierrc','pri','prisma','pro','proc','project','prolog','properties','props','proto','ps1','psc','psd1','psm1','pub','pug','puml','pxd','pxi','py','pylintrc','pyw','pyx',
|
|||
|
'q','qml','qrc',
|
|||
|
'r','rake','rakefile','raku','rakumod','rakutest','rb','rd','rdf','readme','red','rediscli_history','reds','refs','reg','rels','repo','resx','rhtml','rkt','rng','rq','rs','rss','rst','ru',
|
|||
|
's','sample','sas','sass','sbt','scad','scala','schema','scheme','scm','sco','scss','servers','settings','sh','sh_history','sharedmimeinfo','shtml','sieve','sig','siv','sjs','skim','slim','sln','sm','smackspec','smarty','smithy','sml','snippets','sourcetreeconfig','soy','space','sparql','spec','sql','sqlite_history','sqlserver','srt','ss','st','status','stcommitmsg','stl','storyboard','str','strings','styl','stylus','sub','sublime-project','sum','supp','sv','svg','svh','swift','swig',
|
|||
|
't','targets','tcl','template','tern-project','terragrunt','tex','texi','text','textile','tf','tfvars','tgr','tld','todo','toml','tpl','trigger','ts','tsv','tsx','ttcn','ttcn3','ttcnpp','ttl','twig','txt','typed','types','typescript',
|
|||
|
'ui','url','using_foreign_code',
|
|||
|
'v','vala','values','vb','vbproj','vbs','vcproj','vcxproj','version','vert','vfp','vh','vhd','vhdl','viminfo','vm','vmx','vmxd','vmxf','vsixmanifest','vtl','vtt','vue',
|
|||
|
'wast','wat','we','webapp','webidl','webloc','wiki','wl','wlk','wls','wpgm','wpy','wsdl','wtest',
|
|||
|
'x3d','xaml','xbl','xcscheme','xhtml','xib','xml','xq','xquery','xsd','xsl','xslt','xu','xul','xy',
|
|||
|
'yaml','yml','ys','z80','mht','mhtml',
|
|||
|
'zeek','zsh','zsh-template','zsh-theme','zsh-update','zsh_history','zshrc','zshrc_self',
|
|||
|
'service','target','lightbgcolor','cshrc','crontab','environment','exports','defs',
|
|||
|
'odin','jexl','plsql','robot',
|
|||
|
);
|
|||
|
if($ext === -1) return $extArray;
|
|||
|
return in_array($ext,$extArray);
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 远程文件下载到服务器
|
|||
|
* 支持fopen的打开都可以;支持本地、url
|
|||
|
*/
|
|||
|
function file_download_this($from, $fileName,$headerSize=0){
|
|||
|
set_timeout();
|
|||
|
$fileTemp = $fileName.'.downloading';
|
|||
|
if ($fp = @fopen ($from, "rb")){
|
|||
|
if(!$downloadFp = @fopen($fileTemp, "wb")){
|
|||
|
return false;
|
|||
|
}
|
|||
|
while(!feof($fp)){
|
|||
|
if(!file_exists($fileTemp)){//删除目标文件;则终止下载
|
|||
|
fclose($downloadFp);
|
|||
|
return false;
|
|||
|
}
|
|||
|
//对于部分fp不结束的通过文件大小判断
|
|||
|
clearstatcache();
|
|||
|
if( $headerSize>0 &&
|
|||
|
$headerSize==get_filesize(iconv_system($fileTemp))
|
|||
|
){
|
|||
|
break;
|
|||
|
}
|
|||
|
fwrite($downloadFp, fread($fp, 1024 * 200 ), 1024 * 200);
|
|||
|
}
|
|||
|
//下载完成,重命名临时文件到目标文件
|
|||
|
fclose($downloadFp);
|
|||
|
fclose($fp);
|
|||
|
if(!@rename($fileTemp,$fileName)){
|
|||
|
unlink($fileName);
|
|||
|
return rename($fileTemp,$fileName);
|
|||
|
}
|
|||
|
return true;
|
|||
|
}else{
|
|||
|
return false;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 获取文件(夹)权限 rwx_rwx_rwx
|
|||
|
*/
|
|||
|
function get_mode($file){
|
|||
|
$Mode = @fileperms($file);
|
|||
|
$theMode = ' '.decoct($Mode);
|
|||
|
$theMode = substr($theMode,-4);
|
|||
|
$Owner = array();$Group=array();$World=array();
|
|||
|
if ($Mode &0x1000) $Type = 'p'; // FIFO pipe
|
|||
|
elseif ($Mode &0x2000) $Type = 'c'; // Character special
|
|||
|
elseif ($Mode &0x4000) $Type = 'd'; // Directory
|
|||
|
elseif ($Mode &0x6000) $Type = 'b'; // Block special
|
|||
|
elseif ($Mode &0x8000) $Type = '-'; // Regular
|
|||
|
elseif ($Mode &0xA000) $Type = 'l'; // Symbolic Link
|
|||
|
elseif ($Mode &0xC000) $Type = 's'; // Socket
|
|||
|
else $Type = 'u'; // UNKNOWN
|
|||
|
// Determine les permissions par Groupe
|
|||
|
$Owner['r'] = ($Mode &00400) ? 'r' : '-';
|
|||
|
$Owner['w'] = ($Mode &00200) ? 'w' : '-';
|
|||
|
$Owner['x'] = ($Mode &00100) ? 'x' : '-';
|
|||
|
$Group['r'] = ($Mode &00040) ? 'r' : '-';
|
|||
|
$Group['w'] = ($Mode &00020) ? 'w' : '-';
|
|||
|
$Group['e'] = ($Mode &00010) ? 'x' : '-';
|
|||
|
$World['r'] = ($Mode &00004) ? 'r' : '-';
|
|||
|
$World['w'] = ($Mode &00002) ? 'w' : '-';
|
|||
|
$World['e'] = ($Mode &00001) ? 'x' : '-';
|
|||
|
// Adjuste pour SUID, SGID et sticky bit
|
|||
|
if ($Mode &0x800) $Owner['e'] = ($Owner['e'] == 'x') ? 's' : 'S';
|
|||
|
if ($Mode &0x400) $Group['e'] = ($Group['e'] == 'x') ? 's' : 'S';
|
|||
|
if ($Mode &0x200) $World['e'] = ($World['e'] == 'x') ? 't' : 'T';
|
|||
|
$Mode = $Type.$Owner['r'].$Owner['w'].$Owner['x'].' '.
|
|||
|
$Group['r'].$Group['w'].$Group['e'].' '.
|
|||
|
$World['r'].$World['w'].$World['e'];
|
|||
|
return $Mode.'('.$theMode.')';
|
|||
|
}
|
|||
|
|
|||
|
function path_clear($path){
|
|||
|
$path = str_replace('\\','/',trim($path));
|
|||
|
$path = preg_replace('/\/+/', '/', $path);
|
|||
|
if (strstr($path,'../')) {
|
|||
|
$path = preg_replace('/\/\.+\//', '/', $path);
|
|||
|
}
|
|||
|
return $path;
|
|||
|
}
|
|||
|
function path_clear_name($path){
|
|||
|
$path = str_replace('\\','/',trim($path));
|
|||
|
$path = str_replace('/','.',trim($path));
|
|||
|
return $path;
|
|||
|
}
|
|||
|
|
|||
|
/**
|
|||
|
* 写日志
|
|||
|
* @param string $log 日志信息
|
|||
|
* @param string $type 日志类型 [system|app|...]
|
|||
|
* @param string $level 日志级别
|
|||
|
* @return boolean
|
|||
|
*/
|
|||
|
function write_log($log, $type = 'default', $level = 'log'){
|
|||
|
if(!defined('LOG_PATH')) return;
|
|||
|
list($usec, $sec) = explode(' ', microtime());
|
|||
|
$now_time = date('[H:i:s.').substr($usec,2,3).' id-'.REQUEST_ID.']';
|
|||
|
$target = LOG_PATH . strtolower($type) . '/';
|
|||
|
mk_dir($target);
|
|||
|
if (!path_writeable($target)){
|
|||
|
return;// 日志写入失败不处理;
|
|||
|
exit('path can not write! ['.$target.']');
|
|||
|
}
|
|||
|
$ext = '.php';//.php .log;
|
|||
|
$target .= date('Y_m_d').'__'.$level.$ext;
|
|||
|
//检测日志文件大小, 超过配置大小则重命名
|
|||
|
if (file_exists($target) && get_filesize($target) >= 1024*1024*5) {
|
|||
|
$fileName = substr(basename($target),0,strrpos(basename($target),$ext)).date('H-i-s').$ext;
|
|||
|
@rename($target, dirname($target) .'/'. $fileName);
|
|||
|
}
|
|||
|
if(!file_exists($target)){
|
|||
|
error_log("<?php exit;?>\n", 3,$target);
|
|||
|
@chmod($target,_get($GLOBALS,'config.DEFAULT_PERRMISSIONS',0777));
|
|||
|
}
|
|||
|
|
|||
|
if(is_object($log) || is_array($log)){
|
|||
|
$log = json_encode_force($log);
|
|||
|
$log = str_replace(array('\\n','\\r','\\t','\\"','\\\'','\/'),array("\n","\r","\t",'"',"'",'/'),$log);
|
|||
|
}
|
|||
|
clearstatcache();
|
|||
|
return error_log("$now_time $log\n", 3, $target);
|
|||
|
}
|