php上传中文文件名乱码问题处理方案


Posted in PHP onFebruary 03, 2015

php上传文件是最最基础的一个技术点,但是深入进去也有不少问题需要解决,这不,上传中文文件后,文件名变成了乱码。

下面是问题代码,很简单:

1.问题代码

html部分:

 <html>

 <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部分:
 

 <?php

 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"]);

     }

 }

上传了一个文件名为“测试数据.txt”的文件,oh ho,文件是传上去了,但是文件名为乱码。

2.初试

网上搜索一下解决方案,将

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

改成

move_uploaded_file($_FILES["file"]["tmp_name"],"upload/" . iconv("UTF-8","gbk",$_FILES["file"]["name"]));

结果发现iconv函数返回值为false。

查一下函数手册,发现第二个参数有特别的用法,简单翻译一下就是我可以在编码的后面追加//TRANSLIT 或 //IGNORE ,前者会将无法翻译的字符转成最接近的字符,后者就是直接忽略不能转化的字符。

php上传中文文件名乱码问题处理方案

试一下:

var_dump( iconv("UTF-8","gbk//TRANSLIT",$_FILES["file"]["name"]));

var_dump( iconv("UTF-8","gbk//IGNORE",$_FILES["file"]["name"]));

结果:

bool(false) string(4) ".txt"

也就是说中文都没法转化,甚至连接近的字符都没有,看来网上介绍的方法也并非万能。

3.网上介绍方法失败,再尝试

猜测一下,也许我的系统在创建中文文件的时候会乱码,于是我将代码改写了一下:

move_uploaded_file($_FILES["file"]["tmp_name"], "upload/测试数据.txt");

结果创建成功,没有乱码。。。也就是说不是系统问题。

想一下,我的php文件本身是utf8编码的,那么

move_uploaded_file($_FILES["file"]["tmp_name"],"upload/测试数据.txt");

这个语句肯定使用的是utf8编码,那么之前上传的文件名肯定就不是utf8编码了,那么以下的语句肯定是错误的,因为源字符串本身就不是utf8编码的:

iconv("UTF-8","gbk//TRANSLIT",$_FILES["file"]["name"]);

使用函数检查源字符串的编码:

$e=mb_detect_encoding($text, array(‘UTF-8', ‘GBK','gb2312'));

echo $e;

结果是CP936,也就是源字符串编码是GBK。

试一下

move_uploaded_file($_FILES["file"]["tmp_name"],"upload/" . iconv("gbk","UTF-8",$_FILES["file"]["name"]));

问题解决,不再乱码

4.另一种解决办法

实际上还有一种解决办法,就是在html文件的head标签中间加入

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

从而使编码保持统一,也就不需要再转码了

5.下面是结论

使用iconv函数可以解决上传中文文件名乱码的问题,实际上iconv能解决各种各样的由于编码不统一造成的乱码问题。
使用iconv函数请先检查源字符串的编码,除非你已经确定了源字符串的编码。
尽量保证所有的代码的编码一致,万不得已才使用iconv函数。
吐槽一下,尽量不使用中文文件名作为服务器上保存的文件名,请将文件名转化成自己的文件名(即使是英文文件名也请转化一下)。

PHP 相关文章推荐
轻松修复Discuz!数据库
May 03 PHP
PHP扩展编写点滴 技巧收集
Mar 09 PHP
一些php技巧与注意事项分析
Feb 03 PHP
PHP 调试工具Debug Tools
Apr 30 PHP
PHP 透明水印生成代码
Aug 27 PHP
PHP--用万网的接口实现域名查询功能
Dec 13 PHP
PHP添加Xdebug扩展的方法
Feb 12 PHP
PHP解密Unicode及Escape加密字符串
May 17 PHP
php随机显示指定文件夹下图片的方法
Jul 13 PHP
PHP中SERIALIZE和JSON的序列化与反序列化操作区别分析
Oct 11 PHP
在Thinkphp中使用ajax实现无刷新分页的方法
Oct 25 PHP
PHP数据库编程之MySQL优化策略概述
Aug 16 PHP
php上传文件常见问题总结
Feb 03 #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
You might like
德生PL660的电路分析和打磨
2021/03/02 无线电
网站当前的在线人数
2006/10/09 PHP
php实现向javascript传递数组的方法
2015/07/27 PHP
thinkPHP数据库增删改查操作方法实例详解
2016/12/06 PHP
ThinkPHP5.0框架控制器继承基类和自定义类示例
2018/05/25 PHP
laravel 获取当前url的别名方法
2019/10/11 PHP
从零开始学习jQuery (十一) 实战表单验证与自动完成提示插件
2011/02/23 Javascript
最佳6款用于移动网站开发的jQuery 图片滑块插件小结
2012/07/20 Javascript
等待指定时间后自动跳转或关闭当前页面的js代码
2013/07/09 Javascript
限制textbox或textarea输入字符长度的JS代码
2013/10/16 Javascript
jquery取子节点及当前节点属性值的方法
2014/09/09 Javascript
JavaScript实现为指定对象添加多个事件处理程序的方法
2015/04/17 Javascript
js插件YprogressBar实现漂亮的进度条效果
2015/04/20 Javascript
js跨浏览器的事件侦听器和事件对象的使用方法
2015/12/17 Javascript
Vue.js中用webpack合并打包多个组件并实现按需加载
2017/02/17 Javascript
angularjs项目的页面跳转如何实现(5种方法)
2017/05/25 Javascript
javscript 数组扁平化的实现
2020/02/03 Javascript
微信小程序picker组件两列关联使用方式
2020/10/27 Javascript
微信小程序实现页面监听自定义组件的触发事件
2020/11/01 Javascript
[02:17]2016国际邀请赛中国区预选赛VG战队领队采访
2016/06/26 DOTA
一个计算身份证号码校验位的Python小程序
2014/08/15 Python
python+flask实现API的方法
2018/11/21 Python
django 使用 PIL 压缩图片的例子
2019/08/16 Python
关于Kotlin中SAM转换的那些事
2020/09/15 Python
scrapy头部修改的方法详解
2020/12/06 Python
python中doctest库实例用法
2020/12/31 Python
深入理解Python变量的数据类型和存储
2021/02/01 Python
使用CSS3来代替JS实现交互
2017/08/10 HTML / CSS
如何实现jdbc性能优化
2012/07/30 面试题
研究生自荐信
2013/10/09 职场文书
总经理助理的八要求
2013/11/12 职场文书
社区健康教育工作方案
2014/06/03 职场文书
亚运会口号
2014/06/20 职场文书
简历中自我评价范文
2015/03/11 职场文书
多属性、多分类MySQL模式设计
2021/04/05 MySQL
Python使用random模块实现掷骰子游戏的示例代码
2021/04/29 Python