解决jQuery插件Uploadify上传中文文件出现乱码的问题

jQuery.Uploadify是一个方便的jqyery文件上传插件

今天项目需要拿来使用,

但是出现了个问题:上传中文文件的时候会出现乱码

 

通过一番研究,最终解决:

修改uploadify.php文件,

把move_uploaded_file($tempFile,$targetFile); 

改为 move_uploaded_file($tempFile,iconv("UTF-8","gb2312", $targetFile)); 即可。

php 上传中文文件名乱码

 一般状况下上传以中文为文件名的文件会出现形如这样的文件名: 寮€鍚疢ySql杩滅▼鐧婚檰.txt

需要使用iconv函数进行字符编码转换.
iconv(string $in_charset, string $out_charset, string $str) string
Description
    Convert string to requested character 
     encoding

Parameters
    in_charset string
    out_charset string
    str string
Returns
    string the converted string or false on failure.

用法如:
$filename=$_FILES['userfile']['name'];
$filename=iconv("utf-8","gbk",$filename); 

标签: php, 乱码

AJAX乱码解决大全【精】


1、编码
      
编码比较常用的有:UTF-8GBKGB2312ISO-8859-1,除了iso-8859-1之外的其它三个编码都能很好的支持中文,但它们都兼容ISO-8859-1的编码(就是说无论编码怎么改变,只要是ISO-8859-1中的字符,永远不会出现乱码)。
     
这四种编码中,GB2312是中国规定的汉字编码,也可以说是简体中文的字符集编码;GBKGB2312的扩展,除了兼容GB2312外,它还能显示繁体中文,还有日文的假名;UTF-8虽然也支持中文,但却GB码不兼容(编码值不同)UTF-8使用的是可变长的UNICODE编码,编码可能是116进制(即ISO-8859-1中的字符,其编码也是相同的)也有可能是2位或3位的16进制。UTF-8的优点是:1CPU字节顺序无关,可以在不同平台之间交流。2、容错能力高,任何一个字节损坏后,最多只会导致一个编码码位损失,不会链锁错误(GB码错一个字节就会整行乱码),所以在国际化处理中基本都是建议使用UTF-8作为编码。

2、文件的编码
     
文件编码最常使用的有两种:ANSIUTF-8,光看名字估计你都可以猜到了,ANSI就是我们保存文件时使用的默认编码,而UTF-8则需自己设置。对于编码的改变,我使用的工具是NOTEPADECLIPSENOTEPAD使用最简单,只要打开文件后在另存为中选择相应的编码就行了,而且它对编码的支持非常好;而在ECLIPSE中,只要稍微设置一下就行了,打开首选项,然后选择:常规->内容类型(ContentType),在右边选中你想改变保存编码的文件类型,然后在下方的缺省编码中改变其值,最后点击更新(UPDATE)按钮即可。


而在其它的编辑器中,默认保存的内容都是GB2312或者GBK(NOTEPAD中对应ANSI).而根据前面所说的UTF-8和GBK,GB2312等 的编码值是不同的这一点,可以知道,如果文件使用了UTF-8,那么字符编码就必须使用UTF-8,否则编码值的不同就可能造成乱码。而这也就是为什么那 么多的人使用了UTF-8编码后还会产生乱码的根本原因。(JS和JSP都是这个道理)
3、JSP,STRUTS等的中文乱码解决方案
     其实解决的方法只有一个:

request.setCharacterEncoding(encoding);

    方法只有一种,但处理方式就多种多样了,初学者会在JSP页面上直接使用,而有经验的程序员会使用过滤器。而现在所要说的方法也是过滤器。这里以统一使用 UTF-8作为编码作为例子说明。具体过程就不多说了,网上有很多教程。偷懒一点的,到TOMCAT中复制就行了。在TOMCAT的目录下 的"webapps"jsp-examples"WEB-INF"classes"filters"找到 SetCharacterEncodingFilter.java 这个类,放到你的程序中并配置好映射路径。配置好后基本上你的乱码问题就解决了。但要映射路径中需要注意的就是不能使用 '*'

  <filter-mapping>
    
<filter-name>Set Character Encoding</filter-name>
    
<servlet-name>*</servlet-name>
  
</filter-mapping>

像上面这样配置的话(可能也是网上大多教程的做法,想当年也是害苦了我),可能你只有JSP的乱码解决了,要解决STRUTS的乱码需要映射 *.do 或者 servletActionName。然后在初始化参数中设置encoding的值就行了。

<init-param>
      
<param-name>encoding</param-name>
      
<param-value>UTF-8</param-value>
</init-param>

当然,最重要的是要记得根据前面所说的方法,改变你所使用的编辑器保存文件的编码要与使用的字符编码一致。
而在JSP内容中,还是使用如网上教程所说的那种技俩,在所有页面的页首加入:

<%@ page language="java" contentType="text/html; charset=UTF-8"
     pageEncoding
="UTF-8"%>

至此,相信JSP,ACTION都不太可能出现乱码了。
4、资源文件的乱码解决方案
      资源文件谁都知道是国际化支持不可或缺的一部分,如果资源文件都出现乱码了那还了得?其实资源文件的乱码是很好解决的,其原因也是因为使用了UTF-8做 为JSP编码后,没有相应地改变资源文件的文件编码造成的,所以只要对资源文件保存的编码进行更正后,乱码问题也就解决了。当然,你的中文要使用 native2ascii 命令进行正确的转换。
5、调用JS时,JS内容乱码的解决方案。
     其实JS的乱码还是跟文件的编码有关系的,如果JS中有中文的话,那JS文件保存的编码就必须跟调用此JS的页面编码相同,否则,你的所有中文都要从JSP页面传给JS才会显示正常。可以看出对于调用JS出现的乱码是最容易解决的.

6、AJAX提交数据乱码,返回数据乱码的解决方案

     万变不离其宗,AJAX的乱码问题自然跟编码有关了,其实很多人跟我一样想到了对文件编码进行设置,并且在接数据时设置了requet的编码,在返回的数 据时设置了response的编码一切都以为会很顺利,可是这一切都是徒劳无功的,讨厌的乱码再一次出现在你眼前。在你试了N多种方法,包括JS自身的 escape,unescape方法后,你发现乱码仍然猖狂地出现在屏幕上。
    其实在试过这N多方法后,很多人都没发现,解决的方法其实很简单,而且其答案就在我们之前处理的JSP乱码之中。让我们先看一下AJAX的经典请求代码

xmlhttp.open( "post", url, async );
xmlhttp.setRequestHeader( "Content-Type", "text/html" );
xmlhttp.send( params );

通过前面的说明,不知道你现在看出端倪了没有。不知道是受了网上教程的影响还是其它方面影响,setRequestHeader并是万年不变的,也没人想过去改它,而问题就正好出在这个地方。回想一个JSP页面内容的编码设置,其中有这么一节:

contentType="text/html; charset=UTF-8"

现在知道问题了吧,所以我们要把第二句代码改为:

xmlhttp.setRequestHeader( "Content-Type", "text/html;charset=UTF-8" );

如果提交的是form,那么设置为"application/x-www-form-urlencoded; charset=UTF-8"

最后别忘了在返回数据时也设置上:

response.setContentType( "text/xml" );
response.setCharacterEncoding( "UTF-8" );

如果要问为什么的话,其实我们可以把xmlhttp看成是一个临时页面,它由浏览 器动态生成,主要作用是在后台获得请求的数据(可以看成是一个高级的iframe)。所以对于普通页面设置的编码,对它也要同样设置。而在servlet 中返回数据为什么要设置contentType和encoding其道理也是一样的。众所周知,jsp的最后形态就是servlet,而jsp页首设置的 那个内容其实也就是让生成的servlet中生成这么两句话:

response.setContentType( "text/html" );
response.setCharacterEncoding( "UTF-8" );

而pageEncoding则是跟jvm说明了这个页面的内容要使用什么编码保存(这跟之后生成的CLASS有关系)。所以在servlet设置response的编码也是理所当然的了。

response.setContentType("text/xml;charset=UTF-8");

response.setHeader("Pragma",   "no-cache");   //HTTP   1.0  

response.setDateHeader("Expires",   0);   //prevents   caching   at   the   proxy   server  

PrintWriter out = response.getWriter();

out.write(outXML);

out.flush();

out.close();

OK!这样向客户端写的数据中的中文也是UTF-8编码了,客户端js脚本获取到request.responseXML也好,responseText也好,里面的数据都不会有乱码了


标签: 乱码, 编码, utf, jsp

ajax中文乱码完美解决(兼容ie ff)

AJAX的中文乱码可以大概分为两中,第一种是向服务器端发送中文参数时 (xmlhttp.open(“get|post”,url,true)),服务器端接收到的为乱码,这个也是我今天遇到的问题,没做处理之前,在IE里 是正常的,但是在Firefox里面就出现了乱码,我先把接收到参数输出到一个文本里,没有发现什么问题,郁闷了,然后我就把查询语句在输出来观察(我这 里是要从数据库里查出与参数相关的东西),终于发现问题,IE和Firefox输出的参数不一样,虽然汉字上都一样,但是和前后连接上有细小的区别,于是 认定了是编码问题,在网上查找了相关资料,都没能解决问题,但是得到一些启示,因为AJAX发送数据都是采用UTF-8编码的方式发送的,所以要在服务器 端进行编码转换(我这里页面是采用GB2312编码的,如果是采用UTF-8的话应该不会有这步的问题),所以我在服务器端进行了UTF-8转 GB2312,

 

$str=iconv("UTF-8","GB2312",$str);

 

然后测试,在Firefox上顺利解决了问题,以为大公告成了,可是再到IE下测试,发现IE又出现了问题,服务器端接收到的参数没值,这下就郁闷 了,突然看到发送头设置了setRequestHeader("Content-Type","application/x-www-form- urlencoded");,就找到问题所在了,然后就在发送那里进行了参数编码:

 

geturl=encodeURI(geturl);

       geturl=encodeURI(geturl); //两次也可以写成geturl=encodeURI(encodeURI(geturl));

xmlhttp.open("GET",geturl,true);

 

然后再到服务器端进行URL解码:

 

   $str=urldecode($str); //解码

$ str =iconv("UTF-8","GB2312",$ str); //编码转换

 

   注意:解码必须在编码转换前面,不然得不到正确值

 

保存测试,IE和Firefox都能正常了。

 

第二种就是服务器端向客户端输出中文时出现乱码,这类问题网上的答案就比较多了,也都能解决,为了避免各位再去查找,我在这里就COPY下J

 

原因:AJAX在接收responseText或responseXML的值的时候是按照UTF-8的格式来解码的,如果服务器段发送的数据不是UTF-8的格式,那么接收responseText或responseXML的值有可能为乱码。


    解决办法:

 

    在服务器指定发送数据的格式:
    在jsp文件中:
    response.setContentType("text/text;charset=UTF-8");//返回的是txt文本文件
    或是
    response.setContentType("text/xml;charset=UTF-8");//返回的xml文件

     PHP:header('Content-Type:text/html;charset=GB2312');
     ASP:Response.Charset("GB2312")
     JSP:response.setHeader("Charset","GB2312");

完美解决PHP中文乱码问题

  一.首先是PHP网页的编码

  1.php文件本身的编码与网页的编码应匹配

  a.如果欲使用gb2312编码,那么php要输出头:header(“Content-Type: text/html; charset=gb2312"),静态页面添加,所有文件的编码格式为ANSI,可用记事本打开,另存为选择编码为ANSI,覆盖源文件。

  b.如果欲使用utf-8编码,那么php要输出头:header(“Content-Type: text/html; charset=utf-8"),静态页面添加,所有文件的编码格式为utf-8。保存为utf-8可能会有点麻烦,一般utf-8文件开头会有BOM, 如果使用 session就会出问题,可用editplus来保存,在editplus中,工具->参数选择->文件->UTF-8签名,选择总 是删除,再保存就可以去掉BOM信息了。

  2.php本身不是Unicode的,所有substr之类的函数得改成mb_substr(需要装mbstring扩展);或者用iconv转码。

  二.PHP与Mysql的数据交互

  PHP与数据库的编码应一致

  1.修改mysql配置文件my.ini或my.cnf,mysql最好用utf8编码

  [mysql]

  default-character-set=utf8

  [mysqld]

  default-character-set=utf8

  default-storage-engine=MyISAM

  在[mysqld]下加入:

  default-collation=utf8_bin

  init_connect='SET NAMES utf8'

  2.在需要做数据库操作的php程序前加mysql_query("set names '编码'");,编码和php编码一致,如果php编码是gb2312那mysql编码就是gb2312,如果是utf-8那mysql编码就是 utf8,这样插入或检索数据时就不会出现乱码了

  三.PHP与操作系统相关

  Windows和Linux的编码是不一样的,在Windows环境下,调用PHP的函数时参数如果是utf-8编码会出现错误,比如 move_uploaded_file()、filesize()、readfile()等,这些函数在处理上传、下载时经常会用到,调用时可能会出现下 面的错误:

  Warning: move_uploaded_file()[function.move-uploaded-file]:failed to open stream: Invalid argument in ...

  Warning: move_uploaded_file()[function.move-uploaded-file]:Unable to move '' to '' in ...

  Warning: filesize() [function.filesize]: stat failed for ... in ...

  Warning: readfile() [function.readfile]: failed to open stream: Invalid argument in ..

  在Linux环境下用gb2312编码虽然不会出现这些错误,但保存后的文件名出现乱码导致无法读取文件,这时可先将参数转换成操作系统识别的 编码,编码转换可用mb_convert_encoding(字符串,新编码,原编码)或iconv(原编码,新编码,字符串),这样处理后保存的文件名 就不会出现乱码,也可以正常读取文件,实现中文名称文件的上传、下载。

  其实还有更好的解决方法,彻底与系统脱离,也就不用考虑系统是何编码。可以生成一个只有字母和数字的序列作为文件名,而将原来带有中文的名字保 存在数据库中,这样调用move_uploaded_file()就不会出现问题,下载的时候只需将文件名改为原来带有中文的名字。实现下载的代码如下

  header("Pragma: public");

  header("Expires: 0");

  header("Cache-Component: must-revalidate, post-check=0, pre-check=0");

  header("Content-type: $file_type");

  header("Content-Length: $file_size");

  header("Content-Disposition: attachment; filename=\"$file_name\"");

  header("Content-Transfer-Encoding: binary");

  readfile($file_path);

  $file_type是文件的类型,$file_name是原来的名字,$file_path是保存在服务上文件的地址。