php 文件上传详细解析

简析

我们用php获取前端(H5)上传的文件时,借用php的超全局变量$_FILES输出内容时,会得到如下结果:

array(2) {
 ["img1"]=> array(5) { ["name"]=> string(11) "aow_drv.log" ["type"]=> string(0) "" ["tmp_name"]=> string(0) "" ["error"]=> int(1) ["size"]=> int(0) } 
 ["img2"]=> array(5) { ["name"]=> string(10) "splode.log" ["type"]=> string(24) "application/octet-stream" ["tmp_name"]=> string(22) "C:\Windows\php3014.tmp" ["error"]=> int(0) ["size"]=> int(642) } 
 } 

可以看到当文件上传没有错误(即error = 1)时;$_FILES[‘img2’][‘tmp_name’]=C:\Windows\php3014.tmp,这就是临时文件,其中C:\Windows时服务器的默认临时目录,具体查看方法可参考查看win10系统/用户临时文件路径。也可通过php超全局变量$_SERVER[‘SystemRoot’]或函数sys_get_temp_dir来获取。

原理

由‘简析’可以看出,我们在处理一些上传的文件事情(如上传excle)时,一般会利用copy函数将临时文件复制到想要放置的目标目录,即copy($_FILES[‘img2’][‘tmp_name’],$goalDir)。
之所以会这样,是因为我们上传文件经历了两段。

在这里插入图片描述
第二步的服务器临时文件目录是可以自己配置的,在php.ini文件的upload_tmp_dir参数,其解释如下:

Temporary directory for HTTP uploaded files (will use system default if not specified.

即如果设置了则优先使用设置的临时文件目录,否则使用服务器默认临时文件目录。
这里要注意的是程序结束(脚本执行完)后会自动删除临时文件,所以要及时移动文件(copy或move_uploaded_file函数都可以处理)或处理文件。可以让脚本sleep十几秒来观察临时文件存在否 。

为什么要这样做

这个是这样,你应该去了解一下web的工作原理,文件上传这一过程和php是没关系的,是由web服务器来做的,所以放到临时目录也是有web服务器去做的,任何语言对http请求再说封装之后,去临时文件去copy,而且这里只是一个文件移动的过程,是由操作系统来完成的,并不会因此占用php的内容,不然不是分分钟内存就爆掉了。即使没有php,也不影响文件上传。php做的只是从临时文件目录把临时文件拿出来的工作。参考文章 为什么上传文件需要先传到临时目录再拷贝?

上传大文件时PHP配置

一般上传或下载大的文件时间比较久,占内存高,所以此时要对php配置作用特殊处理,如下:
php.ini中与文件上传直接相关的参数:
;是否允许通过HTTP文件上传。默认值为On允许HTTP文件上传,此选项不能设置为Off。
file_uploads = On

; 临时文件目录,默认不做配置,使用系统默认临时文件目录
;upload_tmp_dir =

;设置允许上传文件大小,默认2M
upload_max_filesize = 2M

; 设置允许同一个http请求同时上传文件数量,默认20个
max_file_uploads = 20

另外还有一些间接影响文件上传或下载的参数:

  1. post_max_size = 8M
    指通过表单POST给PHP的所能接收的最大值,包括表单里的所有值。默认为8M。如果POST数据超出限制,那么$_POST和$_FILES将会为空。
    文件上传是通过Http的post请求进行的。
    要上传大文件,你必须设定该选项值大于upload_max_filesize选项的值,例如你设置了upload_max_filesize = 50M ,这里可以把post_max_size = 100M。
    另外如果启用了内存限制,那么该值应当小于memory_limit 选项的值。
  2. memory_limit = 128M
    这个选项用来设置单个PHP脚本所能申请到的最大内存空间。这有助于防止写得不好的脚本消耗光服务器上的可用内存。如果不需要任何内存上的限制将其设为 -1。所以在处理大量数据时会报错,提示内存耗光,PHP Fatal error: Allowed memory size of 268 435 456 bytes exhausted,就是这个参数做了限制。
  3. max_execution_time = 30
    每个PHP脚本运行的最大时间值(单位秒),默认30秒。当我们上传一个较大的文件,例如50M的文件,很可能要几分钟才能上传完,但php默认页面最久 执行时间为30秒,超过30秒,该脚本就停止执行,这就导致出现无法打开网页的情况。因此我们可以把值设置的较大些,如 max_execution_time = 600。 如果设置为0,则表示无时间限制。
  4. max_input_time = 60
    每个PHP脚本解析请求数据所用的时间(单位秒),默认60秒。当我们上传大文件时,可以将这个值设置的较大些。 如果设置为0,则表示无时间限制。

最后提示一点:要求 memory_limit > post_max_size > upload_max_filesize

当然,我们在写代码是,不能因为一个上传文件的功能就去修改服务器参数配置,这是很不方便的。一般这样处理:

  1. set_time_limit(0);
    动态设置max_execution_time=0

  2. ini_set(‘memory_limit’, ‘256M’);
    动态设置memory_limit=256M

##参考
1:官方文档

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值