现在的位置: 首页 > 综合 > 正文

还是有关乱码问题

2013年06月23日 ⁄ 综合 ⁄ 共 5810字 ⁄ 字号 评论关闭
文章目录


一、Include的页面乱码

现象:include进来的页面出现乱码,其它页面正常。
原因:Tomcat在缺省情况下使用ISO-8859-1编码,但是在include时有时Tomcat不能正确根据外层.jsp文件的编码解析include进来的文件,造成include进来的文件中的中文乱码。
解决:这儿可以有很多解决办法,但是对于我们的中文环境,从根本上的解决办法是将Tomcat 5.0.19的核心缺省编码从ISO-8859-1修改为GBK 。可以在下面地址下载修改过的jar文件,
    右击保存
jasper-compiler.jar,jasper-runtime.jar位于/common/lib下,其它位于/server/lib下,将新的.jar文件替代原.jar即可。

二、提交的数据乱码

现象:通过表单提交的数据出现乱码。
原因:原因未明。可能是Tomcat在接收到请求后,并没有能够根据request中的信息提前正确的编码方式。
解决:可以添加一个设置字符集的Filter。

package filters;

import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.UnavailableException;

public class SetCharacterEncodingFilter implements Filter {
    protected String encoding = null;
    protected FilterConfig filterConfig = null;
    protected boolean ignore = true;

    public void destroy() {

        this.encoding = null;
        this.filterConfig = null;

    }

    public void doFilter(ServletRequest request, ServletResponse response,
                         FilterChain chain)
    throws IOException, ServletException {

        // Conditionally select and set the character encoding to be used
        if (ignore || (request.getCharacterEncoding() == null)) {
            String encoding = selectEncoding(request);
            if (encoding != null)
                request.setCharacterEncoding(encoding);
        }

    // Pass control on to the next filter
        chain.doFilter(request, response);

    }

    public void init(FilterConfig filterConfig) throws ServletException {

    this.filterConfig = filterConfig;
        this.encoding = filterConfig.getInitParameter("encoding");
        String value = filterConfig.getInitParameter("ignore");
        if (value == null)
            this.ignore = true;
        else if (value.equalsIgnoreCase("true"))
            this.ignore = true;
        else if (value.equalsIgnoreCase("yes"))
            this.ignore = true;
        else
            this.ignore = false;

    }

    protected String selectEncoding(ServletRequest request) {

        return (this.encoding);

    }

}

配置web.xml

[pre]    <filter>
        <filter-name>Set Character Encoding</filter-name>
        <filter-class>filters.SetCharacterEncodingFilter</filter-class>
        <init-param>
            <param-name>encoding</param-name>
            <param-value>GBK</param-value>
        </init-param>
    </filter>

    <filter-mapping>
        <filter-name>Set Character Encoding</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>[/pre]

版权声明   给作者写信
本篇文章对您是否有帮助?  投票:         投票结果:     5       2


  评论人:pengkang    参与分: 102    专家分: 0    来自: 北京市海淀区三里河路五号 发表时间: 2004-3-25 上午11:38
这样作一点都不好。。根本不用修改TOMCAT的源码,这种问题没这么麻烦。。。过滤器也是TOMCAT中的例子,没必要拿到这里作为自己的东西给别人看。。

  评论人:starblue    参与分: 21    专家分: 0 发表时间: 2004-3-26 下午12:53
楼上的不知道有什么好方法。楼主现在在哪工作了?我是star.

  评论人:huangyifu    参与分: 41    专家分: 90 发表时间: 2004-3-29 下午5:39
请看我的解决方法(word格式):

Web开发笔记

  评论人:wxdcngc    参与分: 12    专家分: 0 发表时间: 2004-4-2 上午11:56
再加上<% request.setCharacterEncoding("gb2312"); %>
就可以了

客人: laoduan 发表时间: 2004-4-2 下午11:09
我说一下我的心得:
同一程序在Tomcat5.0.16(或者说是在5.0.14、5.0.18、5.0.19都会)中返回中文输入就会出现乱码,但在Tomcat4.0版本中则不会!这是一个有趣而奇怪的现象。
问题是出在处理参数传递的方法上:如果在servlet中用doGet(HttpServletRequest request, HttpServletResponse response)方法进行处理的话前面即使是写了:
request.setCharacterEncoding("GBK");
response.setContentType("text/html;charset=GBK");
也是不起作用的,返回的中文还是乱码!!!
如果把这个函数改成doPost(HttpServletRequest request, HttpServletResponse response)一切就OK了。
同样,在用两个JSP页面处理表单输入之所以能显示中文是因为用的是post方法传递的,改成get方法依旧不行。
由此可见在servlet中用doGet()方法或是在JSP中用get方法进行处理要注意。这毕竟涉及到要通过浏览器传递参数信息,很有可能引起常用字符集的冲突或是不匹配。
以上问题在Tomcat5.0.16(或者说是在5.0.14、5.0.18、5.0.19)中解决通过!

  评论人:sunleevy    参与分: 6    专家分: 0 发表时间: 2004-4-10 下午10:25
我如何看老大的解决的方法啊?

客人: sunfan 发表时间: 2004-5-13 下午4:06
修改tomcat/conf/server.xml
<Connector acceptCount='100' connectionTimeout='20000' debug='0'
      disableUploadTimeout='true' enableLookups='false'
      maxSpareThreads='75' maxThreads='150' minSpareThreads='25'
      port='8080' redirectPort='8443' URIEncoding='GBK'/>
加上:URIEncoding='GBK'即可。
如果GBK不行,试一下ISO-8859-1

最上面的filter还是要的

客人: kakab 发表时间: 2004-6-9 上午2:39
Tomcat 5.0.19中的中文,用不着这么麻烦吧,让显示,和输入post中文都正常很简单的啊。 如果Tomcat连这种问题都没准备好,还需要去改什么jar, 加什么filter, 那Tomcat做到现在也太失败了! 

客人: 刘克鸿 发表时间: 2004-6-9 上午4:34
该篇文章的处理方法具有相当的局限性。
文中对Jasper的修改,记住在对Jsp转成Java文件时的编码问题,在缺省的Jasper中,缺省使用的是ISO-8859-1, 然后把它转成UTF8(缺省情况,可以在conf/web.xml中改)。 很明显,如果一个JSP中直接输入了中文,Jasper把它当作ISO8859-1来处理是肯定有问题的,这一点,我们可以通过查看Jasper所生成的Java中间文件来确认。可是说,Jasper把Jsp源文件的编码方式限定在ISO-8859-1上了。

那么,上文作者的想法是很自然的,把Jasper中缺省所使用的ISO-8859-1改成所需的GBK编码不就可以了吗?当然,这样做不是不可以,但这样做有一个最大的问题,就是又再一次把JSP源文件限定在另外一种编码方式上:GBK.   一个Tomcat服务器只能处理GBK编码的JSP? 当然,如果使用中的确是这样固定的,没有问题,但作为一个服务器应用来说,限定它的编码方式是不合理的,比如,如果你使用同一个服务器来处理含有BIG5编码文字的JSP, 是不是就又乱码了?既然是服务器,挑三拣四是不合理的。

其实,Jasper的处理方法本身是没有错的。只是使用它的使用应该遵循java I18N规则,使用ResourceBundle来解决。JSP文件中不直接放处ISO-8859-1编码方式之外的字符串,将需要的字符串放在ResourceBundle中,可以定义不同语言的ResourceBundle, 比如 myStringRB_zh_CN.rbInfo, myStringRB_zh_TW.rbInfo, myStringRB_ja.rbInfo myStringRB_ko.rbInfo. 有了ResourceBundle以后,再结合locale设置,就可以实现同一个JSP对应不同的locale而显示不同编码的文字(这本来就是Java中ResourceBundle的精华所在)

至于说Form中的提交问题,也不用如上文中所述那么麻烦。结合了上面关于显示的问题,在JSP中将编码统一为UTF8更容易一些:
<%response.setContentType("text/html; charset=UTF-8");%>
<%@ page contentType="text/html; charset=UTF-8"%>

对于网页中所提交的数据,比如:
<input type=text name='name' value=''>
只需类似处理:
String fname = request.getParameter("name");
fname = new String(fname.getBytes("ISO8859-1"), "UTF-8");
out.print(fname);
即可正常显示。(对服务器的客制化配置可能导致其缺省编码方式不是ISO8859-1, 这时,需要调试这个地方,尝试其他编码,直到正常显示)

上面的句子可以写成一个static方法来调用,
class BSP{
....
public static String mgp(String field)
{
    return new String(request.getParameter(field).getBytes("ISO8859-1"), "UTF-8");
}
...
}

然后在接收Form提交的网页中, 使用
.....
<%response.setContentType("text/html; charset=UTF-8");%>
<%@ page contentType="text/html; charset=UTF-8"%>
.....
<%=BSP.mgp("name")%>
.....

如使用其它编码,只需将UTF-8换成所需编码方式即可。

抱歉!评论已关闭.