php上传文件常见问题总结


Posted in PHP onFebruary 03, 2015

把php上传文件时经常碰到的几个问题总结一下吧,以后用到时不用再去找了。

1.先做个最简单的上传文件

 <html>

 <head>

 <meta http-equiv="Content-Type" content="text/html; charset=utf-8">

 </head>

 <body>

 <form action="upload_file.php" method="post"

 enctype="multipart/form-data">

 <label for="file">Filename:</label>

 <input type="file" name="file" id="file" /> 

 <br />

 <input type="submit" name="submit" value="Submit" />

 </form>

 </body>

 </html>
<?php

if (($_FILES["file"]["size"] < 20000)

  {

  if ($_FILES["file"]["error"] > 0)

    {

    echo "Return Code: " . $_FILES["file"]["error"] . "<br />";

    } 

  else

    {

    echo "Upload: " . $_FILES["file"]["name"] . "<br />";

    echo "Type: " . $_FILES["file"]["type"] . "<br />";

    echo "Size: " . ($_FILES["file"]["size"] / 1024) . " Kb<br />";

    echo "Temp file: " . $_FILES["file"]["tmp_name"] . "<br />";

    if (file_exists("upload/" . $_FILES["file"]["name"]))

      {

      echo $_FILES["file"]["name"] . " already exists. ";

      }

    else

      {

      move_uploaded_file($_FILES["file"]["tmp_name"],

      "upload/" . $_FILES["file"]["name"]);

      echo "Stored in: " . "upload/" . $_FILES["file"]["name"];

      }

    }

  }

else

  {

  echo "Invalid file";

  }

?>

2.然后了解超级全局变量$_FILES的值

$_FILES['userfile']['name']

$_FILES['userfile']['type']

$_FILES['userfile']['size']

$_FILES['userfile']['tmp_name']

$_FILES['userfile']['error']

其中,$_FILES['userfile']['error']的所有值:

UPLOAD_ERR_OK 其值为 0,没有错误发生,文件上传成功。

UPLOAD_ERR_INI_SIZE 其值为 1,上传的文件超过了 php.ini 中 upload_max_filesize 选项限制的值。

UPLOAD_ERR_FORM_SIZE 其值为 2,上传文件的大小超过了 HTML 表单中 MAX_FILE_SIZE 选项指定的值。

UPLOAD_ERR_PARTIAL 其值为 3,文件只有部分被上传。

UPLOAD_ERR_NO_FILE 其值为 4,没有文件被上传。

UPLOAD_ERR_NO_TMP_DIR 其值为 6,找不到临时文件夹。PHP 4.3.10 和 PHP 5.0.3 引进。

UPLOAD_ERR_CANT_WRITE 其值为 7,文件写入失败。PHP 5.1.0 引进。

3.很多情况:需要严格判断上传文件类型

     我们知道使用$_FILES['userfile']['type']判断上传文件类型是一个很不明智的做法,因为该判断依据是文件的后缀名,任何人都可以将一个mp3文件的后缀改成jpg从而伪装成图片进行上传,因此php官方建议使用php的扩展php_fileinfo来判断文件的mime,开启拓展的方法百度一下有很多,win和linux略有不同。

4.情景一:上传文件重名后自动重命名

if (file_exists("./upload/" . $_FILES["file"]["name"]))  

{    

   do{  

       $suffix ="";  

       $suffix_length = 4;  

       $str = "0123456789abcdefghijklmnopqrstuvwxyz";  

       $len = strlen($str)-1; 

       //文件名后追加4个随机字符  

       for($i=0 ; $i<$suffix_length; $i++){  

          $suffix .= $str[rand(0,$len)];  

       }  

       $upload_filename = $_FILES['file']['name'];                                            

       $filename = substr($upload_filename,0,strrpos($upload_filename,".")).$suffix.".".substr($upload_filename,strrpos($_FILES["file"]["name"],".")+1); 

   }while(file_exists("./upload/".$filename));  

       move_uploaded_file($_FILES["file"]["tmp_name"],"./upload/" . $filename);  

}else{  

       move_uploaded_file($_FILES["file"]["tmp_name"], "upload/" . $_FILES["file"]["name"]);   

} 

5.情景二:根据日期分目录上传文件

$structure = './'.date("Y").'/'.date("m").'/'.date("d").'/';

if (!mkdir($structure, 0777, true)) {

    die('Failed to create folders...');

}

move_uploaded_file($_FILES["file"]["tmp_name"],$structure . $_FILES["file"]["name"]);

6.情景三:多文件上传

 <form action="" method="post" enctype="multipart/form-data">

 <p>Pictures:

 <input type="file" name="pictures[]" />

 <input type="file" name="pictures[]" />

 <input type="file" name="pictures[]" />

 <input type="submit" value="Send" />

 </p>

 </form>
 <?php

 foreach ($_FILES["pictures"]["error"] as $key => $error) {

     if ($error == UPLOAD_ERR_OK) {

         $tmp_name = $_FILES["pictures"]["tmp_name"][$key];

         $name = $_FILES["pictures"]["name"][$key];

         move_uploaded_file($tmp_name, "data/$name");

     }

 }

 ?>

有的情况下多文件的这种变量结构并不好用:

array(1) {

    ["upload"]=>array(2) {

        ["name"]=>array(2) {

            [0]=>string(9)"file0.txt"

            [1]=>string(9)"file1.txt"

        }

        ["type"]=>array(2) {

            [0]=>string(10)"text/plain"

            [1]=>string(10)"text/html"

        }

    }

}

很多情况下我们需要的是类似这样的结构

array(1) {

    ["upload"]=>array(2) {

        [0]=>array(2) {

            ["name"]=>string(9)"file0.txt"

            ["type"]=>string(10)"text/plain"

        },

        [1]=>array(2) {

            ["name"]=>string(9)"file1.txt"

            ["type"]=>string(10)"text/html"

        }

}

}

使用下面的函数就能轻松转化结构

 function diverse_array($vector) { 

     $result = array(); 

     foreach($vector as $key1 => $value1) 

         foreach($value1 as $key2 => $value2) 

             $result[$key2][$key1] = $value2; 

     return $result; 

 } 

 $upload = diverse_array($_FILES["upload"]);

7. 有的时候:需要配置服务器修改最大上传文件大小

首先,在表单上

<input type="hidden" name="MAX_FILE_SIZE" value="字节" />
可以限制上传文件大小(可以被绕过)。

然后在服务器上也需要调整一下配置

php.ini:

max_execution_time = 30 每个脚本运行的最长时间,单位秒
max_input_time = 60,每个脚本可以消耗的时间,单位也是秒
memory_limit = 128M,这个是脚本运行最大消耗的内存
post_max_size = 8M,表单提交最大数据为 8M,此项不是限制上传单个文件的大小,而是针对整个表单的提交数据进行限制的。
upload_max_filesize = 2M ,上载文件的最大许可大小

nginx:

 location / {

     root   html;

     index  index.html index.htm;

     client_max_body_size    1000m;

  }

以上就是常见的问题的处理方法了,希望大家能够喜欢。

PHP 相关文章推荐
php array_intersect比array_diff快(附详细的使用说明)
Jul 03 PHP
php中获取远程客户端的真实ip地址的方法
Aug 03 PHP
PHP 透明水印生成代码
Aug 27 PHP
解析PHP中empty is_null和isset的测试
Jun 29 PHP
PHP基础知识介绍
Sep 17 PHP
Thinkphp中的volist标签用法简介
Jun 18 PHP
php实现俄罗斯乘法实例
Mar 07 PHP
Yii2中如何使用modal弹窗(基本使用)
May 30 PHP
PHP多进程编程总结(推荐)
Jul 18 PHP
PHP常用日期加减计算方法实例小结
Jul 31 PHP
php多进程模拟并发事务产生的问题小结
Dec 07 PHP
PHP架构及原理知识点详解
Dec 22 PHP
PHP、Python和Javascript的装饰器模式对比
Feb 03 #PHP
php对象在内存中的存在形式分析
Feb 03 #PHP
浅析THINKPHP的addAll支持的最大数据量
Feb 03 #PHP
php格式化金额函数分享
Feb 02 #PHP
php可应用于面包屑导航的迭代寻找家谱树实现方法
Feb 02 #PHP
php生成唯一的订单函数分享
Feb 02 #PHP
php数组去除空值函数分享
Feb 02 #PHP
You might like
DOTA2游戏同人动画《龙之血》导演接受采访
2021/03/05 欧美动漫
php数组函数序列之array_key_exists() - 查找数组键名是否存在
2011/10/29 PHP
解析VS2010利用VS.PHP插件调试PHP的方法
2013/07/19 PHP
PHP下通过QRCode类库创建中间带网站LOGO的二维码
2014/07/12 PHP
laravel安装和配置教程
2014/10/29 PHP
thinkphp在低版本Nginx 下支持PATHINFO的方法分享
2016/05/27 PHP
Thinkphp 框架扩展之行为扩展原理与实现方法分析
2020/04/23 PHP
CL vs ForZe BO5 第五场 2.13
2021/03/10 DOTA
pjblog修改技巧汇总
2007/03/12 Javascript
Firefox outerHTML实现代码
2009/06/04 Javascript
ExtJS 刷新后如何默认选中刷新前最后一次选中的节点
2014/04/03 Javascript
JavaScript中的getTimezoneOffset()方法使用详解
2015/06/10 Javascript
js贪吃蛇网页版游戏特效代码分享(挑战十关)
2015/08/24 Javascript
Atitit.js的键盘按键事件捆绑and事件调度
2016/04/01 Javascript
Angularjs手动解析表达式($parse)
2016/10/12 Javascript
jquery Banner轮播选项卡
2016/12/26 Javascript
Angularjs使用指令做表单校验的方法
2017/03/31 Javascript
Vue0.1的过滤代码如何添加到Vue2.0直接使用
2017/08/23 Javascript
浅谈Vue.js 组件中的v-on绑定自定义事件理解
2017/11/17 Javascript
layui实现文件或图片上传记录
2018/08/28 Javascript
Vue项目中使用better-scroll实现一个轮播图自动播放功能
2018/12/03 Javascript
js blob类型url的视频下载问题的解决
2019/11/29 Javascript
微信小程序修改数组长度的问题的解决
2019/12/17 Javascript
Python文件打开方式实例详解【a、a+、r+、w+区别】
2019/03/30 Python
linux下安装python3和对应的pip环境教程详解
2019/07/01 Python
原生python实现knn分类算法
2019/10/24 Python
使用PyTorch训练一个图像分类器实例
2020/01/08 Python
Python生成器next方法和send方法区别详解
2020/05/30 Python
Python decimal模块使用方法详解
2020/06/08 Python
办公室文秘自我鉴定
2013/09/21 职场文书
租赁意向书范本
2014/04/01 职场文书
清明节演讲稿
2014/05/27 职场文书
企业晚会策划方案
2014/05/29 职场文书
公司借款担保书
2015/09/22 职场文书
新娘婚礼答谢词
2015/09/29 职场文书
2019大学竞选班长发言稿
2019/06/27 职场文书