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 相关文章推荐
新闻分类录入、显示系统
Oct 09 PHP
php chr() ord()中文截取乱码问题解决方法
Sep 08 PHP
兼容性比较好的PHP生成缩略图的代码
Jan 12 PHP
php遍历目录与文件夹的多种方法详解
Nov 14 PHP
php将字符串转化成date存入数据库的两种方式
Apr 28 PHP
PHP中调用SVN命令更新网站方法
Jan 07 PHP
php实现的IMEI限制的短信验证码发送类
May 05 PHP
php技术实现加载字体并保存成图片
Jul 27 PHP
php中注册器模式类用法实例分析
Nov 03 PHP
CI(Codeigniter)的Setting增强配置类实例
Jan 06 PHP
PHP基于单例模式实现的数据库操作基类
Jan 15 PHP
php常用的工具开发整理
Sep 26 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
php简单实现多字节字符串翻转的方法
2015/03/31 PHP
php防止网站被攻击的应急代码
2015/10/21 PHP
深入解析PHP中SESSION反序列化机制
2017/03/01 PHP
JavaScript与C# Windows应用程序交互方法
2007/06/29 Javascript
JavaScript修改css样式style
2008/04/15 Javascript
jquery checkbox实现单选小例
2013/11/27 Javascript
生成二维码方法汇总
2014/12/26 Javascript
jQuery实现单击弹出Div层窗口效果(可关闭可拖动)
2015/09/19 Javascript
jQuery EasyUI 菜单与按钮之创建简单的菜单和链接按钮
2015/11/18 Javascript
JavaScript、jQuery与Ajax的关系
2016/01/24 Javascript
jquery checkbox的相关操作总结
2016/10/17 Javascript
javascript稀疏数组(sparse array)和密集数组用法分析
2016/12/28 Javascript
js 事件的传播机制(实例讲解)
2017/07/20 Javascript
layui.js实现的表单验证功能示例
2017/11/15 Javascript
原生nodejs使用websocket代码分享
2018/04/07 NodeJs
在react中使用vuex的示例代码
2018/07/30 Javascript
在vue中实现点击选择框阻止弹出层消失的方法
2018/09/15 Javascript
JS实现横向轮播图(初级版)
2020/06/24 Javascript
JavaScript实现简单的图片切换功能(实例代码)
2020/04/10 Javascript
[02:40]2014DOTA2 国际邀请赛中国区预选赛 四大豪门抵达华西村
2014/05/23 DOTA
[35:34]Liquid vs Winstrike 2018国际邀请赛小组赛BO2 第一场 8.18
2018/08/19 DOTA
使用Python的PEAK来适配协议的教程
2015/04/14 Python
python按综合、销量排序抓取100页的淘宝商品列表信息
2018/02/24 Python
python 内置模块详解
2019/01/01 Python
python3.x+pyqt5实现主窗口状态栏里(嵌入)显示进度条功能
2019/07/04 Python
Python Sympy计算梯度、散度和旋度的实例
2019/12/06 Python
python读取dicom图像示例(SimpleITK和dicom包实现)
2020/01/16 Python
如何学习Python time模块
2020/06/03 Python
CSS3实现淘宝留白的方法
2020/06/05 HTML / CSS
HTML5轻松实现全屏视频背景的示例
2018/04/23 HTML / CSS
全球最大运动品牌的男装、女装和童装官方库存商:A&A Sports
2021/01/17 全球购物
违纪检讨书2000字
2014/02/08 职场文书
2015年社区科普工作总结
2015/05/13 职场文书
党支部审查意见
2015/06/02 职场文书
2019各种保证书范文
2019/06/24 职场文书
2019年学校消防安全责任书(2篇)
2019/10/09 职场文书