php文件上传的两种实现方法


Posted in PHP onApril 04, 2016

文件上传一般有下面2种方式:

有两种:
1、标准input表单方式,典型的用$_FILES进行接收;
2、以Base64的方式进行传送,一般是AJAX异步上传。

第一种
标准的input表单方式,适用于大文件进行上传,同时支持批量。html代码关键的几句:

<form enctype="multipart/form-data" method="post" action="upload.php"">
  <input type="file" name="id_pic[]" accept="image/*" class="form-control" multiple />
  <input type="submit" value="上传 " />
</form>

不同的name时:

<form enctype="multipart/form-data" method="post" action="upload.php"">
  <input type="file" name="id_pic_1" accept="image/*" class="form-control" />
  <input type="file" name="id_pic_2" accept="image/*" class="form-control" />
  <input type="submit" value="上传 " />
</form>

其中enctype="multipart/form-data"对于文件上传是必不可少的。另外type="file"设置input类型,accept="image/*"指定优先上传图片(MIME 参考手册)。multiple支持一次选多个文件,pic[]以数组的形式接收多个文件。手机端端还可以加入参数capture="camera"选择摄像头拍照上传。

后端处理:
通过$_FILES获取上传的文件。

$files = $_FILES;
传多个文件时,如果name不同,则返回的$_FILES数组格式不同。

name相同时:

array(1) {
 ["id_pic"] => array(5) {
  ["name"] => array(2) {
   [0] => string(5) "1.jpg"
   [1] => string(5) "2.jpg"
  }
  ["type"] => array(2) {
   [0] => string(10) "image/jpeg"
   [1] => string(10) "image/jpeg"
  }
  ["tmp_name"] => array(2) {
   [0] => string(27) "C:\Windows\Temp\php7A7E.tmp"
   [1] => string(27) "C:\Windows\Temp\php7A7F.tmp"
  }
  ["error"] => array(2) {
   [0] => int(0)
   [1] => int(0)
  }
  ["size"] => array(2) {
   [0] => int(77357)
   [1] => int(56720)
  }
 }
}

name不相同时:

array(2) {
 ["id_pic_1"] => array(5) {
  ["name"] => string(5) "1.jpg"
  ["type"] => string(10) "image/jpeg"
  ["tmp_name"] => string(27) "C:\Windows\Temp\phpBBEE.tmp"
  ["error"] => int(0)
  ["size"] => int(77357)
 }
 ["id_pic_2"] => array(5) {
  ["name"] => string(5) "2.jpg"
  ["type"] => string(10) "image/jpeg"
  ["tmp_name"] => string(27) "C:\Windows\Temp\phpBBEF.tmp"
  ["error"] => int(0)
  ["size"] => int(56720)
 }
}

在对$_FILES进行foreach遍历时,前面那种输出格式不大方便。后面那种就可以直接遍历。我们可以写个方法进行统一转换:

function dealFiles($files) {
    $fileArray = array();
    $n     = 0;
    foreach ($files as $key=>$file){
      if(is_array($file['name'])) {
        $keys    =  array_keys($file);
        $count   =  count($file['name']);
        for ($i=0; $i<$count; $i++) {
          $fileArray[$n]['key'] = $key;
          foreach ($keys as $_key){
            $fileArray[$n][$_key] = $file[$_key][$i];
          }
          $n++;
        }
      }else{
        $fileArray = $files;
        break;
      }
    }
    return $fileArray;
 }

好,前面讲到后端如何处理接收到的$_FILES数组,并转换成统一格式。接下来任务主要是:
1、检测上传的文件是否非法;
2、检测上传的文件是否超过大小;
3、检测保存的路径是否存在,是否可写;
4、文件重命名;

其中上传过程中用到了个很重要的函数:move_uploaded_file(filename , $destination )进行文件移动操作。将$_FILES['id_pic']['tmp_name']移动到新的路径里。当然,移动前可以用is_uploaded_file($_FILES['id_pic']['tmp_name'])进行判断文件是否正常上传的。

多文件上传则是循环的方法多次使用move_uploaded_file()进行移动操作。

第二种
主要以上传图片为主。
利用input的change事件,借助canvas对图片进行处理(例如压缩),然后ajax发送文件流到后端。

基本原理是通过canvas渲染图片,再通过 toDataURL 方法压缩保存为base64字符串(能够编译为jpg格式的图片)。

后端处理:
后端最终会收到前端发送的base64字符串,接着处理字符串为图片即可。具体请使用关键字base64 转 image 开发语言进行谷歌|百度。前端生成的结果中有一个base64Len,这是字符串的长度,后端应该核对以确认是否提交完整。

//php示例:
$img = base64_decode($_POST['img']);
$img = imagecreatefromstring($img);

以上就是本文的全部内容,希望对大家的学习有所帮助。

PHP 相关文章推荐
PHP概述.
Oct 09 PHP
实现分十页分向前十页向后十页的处理
Oct 09 PHP
教你如何把一篇文章按要求分段
Oct 09 PHP
PHP完整的日历类(CLASS)
Nov 27 PHP
自动分页的不完整解决方案
Jan 12 PHP
比较全面的PHP数组的使用方法小结
Sep 23 PHP
PHP查询数据库中满足条件的记录条数(两种实现方法)
Jan 29 PHP
php实现MD5加密16位(不要默认的32位)
Aug 12 PHP
详细解读php的命名空间(一)
Feb 21 PHP
php实现微信支付之退款功能
May 30 PHP
针对thinkPHP5框架存储过程bug重写的存储过程扩展类完整实例
Jun 16 PHP
Laravel 中使用简单的方法跟踪用户是否在线(推荐)
Oct 30 PHP
在Win2003(64位)中配置IIS6+PHP5.2.17+MySQL5.5的运行环境
Apr 04 #PHP
PHP版本的选择5.2.17 5.3.27 5.3.28 5.4 5.5兼容性问题分析
Apr 04 #PHP
PHP命名空间和自动加载类
Apr 03 #PHP
PHP中的Trait 特性及作用
Apr 03 #PHP
PHP错误处理函数
Apr 03 #PHP
php通过curl添加cookie伪造登陆抓取数据的方法
Apr 02 #PHP
PHP函数nl2br()与自定义函数nl2p()换行用法分析
Apr 02 #PHP
You might like
php adodb连接不同数据库
2009/03/19 PHP
PHP foreach循环使用详解与实例代码
2010/05/08 PHP
关于JSON以及JSON在PHP中的应用技巧
2013/11/27 PHP
php实现图片缩略图的方法
2016/03/29 PHP
thinkPHP5.0框架整体架构总览【应用,模块,MVC,驱动,行为,命名空间等】
2017/03/25 PHP
IE中createElement需要注意的一个问题
2010/07/13 Javascript
style、 currentStyle、 runtimeStyle区别分析
2010/08/01 Javascript
浅析jquery ajax异步调用方法中不能给全局变量赋值的原因及解决方法
2014/01/10 Javascript
jQuery实现的导航条切换可显示隐藏
2014/10/22 Javascript
AngularJS中取消对HTML片段转义的方法例子
2015/01/04 Javascript
iframe里使用JavaScript控制主页转向的方法
2015/04/03 Javascript
js中flexible.js实现淘宝弹性布局方案
2020/06/23 Javascript
JavaScript对Json的增删改属性详解
2016/06/02 Javascript
聊一聊JS中this的指向问题
2016/06/17 Javascript
学习使用jQuery表单验证插件和日历插件
2017/02/13 Javascript
解决Vue axios post请求,后台获取不到数据的问题方法
2018/08/11 Javascript
深入浅析javascript函数中with
2018/10/28 Javascript
详解@angular/cli 改变默认启动端口两种方式
2018/11/29 Javascript
微信小程序登录按钮遮罩浮层效果的实现方法
2018/12/16 Javascript
Vue2 添加数据可视化支持的方法步骤
2019/01/02 Javascript
发布订阅模式在vue中的实际运用实例详解
2019/06/09 Javascript
Python3实现转换Image图片格式
2018/06/21 Python
Flask Web开发入门之文件上传(八)
2018/08/17 Python
基于wxPython的GUI实现输入对话框(2)
2019/02/27 Python
超简单的Python HTTP服务
2019/07/22 Python
利用python绘制中国地图(含省界、河流等)
2020/09/21 Python
CSS3 Media Queries详细介绍和使用实例
2014/05/08 HTML / CSS
亚瑟士美国官网:ASICS美国
2017/02/01 全球购物
分布式数据库需要考虑哪些问题
2013/12/08 面试题
八年级音乐教学反思
2014/01/09 职场文书
父亲追悼会答谢词
2014/01/17 职场文书
青年文明号口号
2014/06/17 职场文书
村安全生产责任书
2014/08/25 职场文书
党的群众路线教育实践活动对照检查材料范文
2014/09/24 职场文书
村干部四风问题整改措施
2014/09/30 职场文书
2014保险公司个人工作总结
2014/12/09 职场文书