resin3.1处理utf-8格式的jsp时存在的问题_JAVA_编程开发_程序员俱乐部

中国优秀的程序员网站程序员频道CXYCLUB技术地图
热搜:
更多>>
 
您所在的位置: 程序员俱乐部 > 编程开发 > JAVA > resin3.1处理utf-8格式的jsp时存在的问题

resin3.1处理utf-8格式的jsp时存在的问题

 2011/10/18 6:10:45  haouziwefe  http://haouziwefe.iteye.com  我要评论(0)
  • 摘要:以前一直使用resin-3.0.x作为服务器,最近想升级到resin3.1,于是在官网上下载了resin3.1.7a,解压配置一切正常,但把应用重新部署上去的时候就出了问题,以前一直正常的页面,现在却报错:<h1>500servletexception</h1><pre><scripttype="text/javascript"><!----></script><a>[show]</a>/index
  • 标签:问题 JS
    ??? 以前一直使用resin-3.0.x作为服务器,最近想升级到resin3.1,于是在官网上下载了resin3.1.7a,解压配置一切正常,但把应用重新部署上去的时候就出了问题,以前一直正常的页面,现在却报错:
?
<h1>500 servlet exception</h1>?
<pre><script type="text/javascript"><!----></script><a>[show]</a> /index.jsp:1: contenttype 'text/vnd.wap.wml; charset=utf-8' conflicts withprevious value of contenttype 'text/html; charset=utf-8'.  check the .jspand any included .jsp files for conflicts.1:  <%@page contenttype="text/vnd.wap.wml; charset=utf-8"%>2:  <%@page import="java.util.*"%>3:  <%!</pre>?
?
??? 根据上面的提示,意思似乎是我在jsp里面第一行设置的contenttype是'text/vnd.wap.wml; charset=utf-8,和前面设置的'text/html; charset=utf-8'不同导致冲突,但这个文件的第一行就是<<a href='mailto:%@page'>%@page</a> contenttype="text/vnd.wap.wml;charset=utf-8" %>,根本没有设置过'text/html; charset=utf-8',这个提示真是让人很摸不着头脑。
??? 后来想到可能是utf8文件格式的问题,就用ue打开文件,另存了一次,选的是不带bom的utf8格式的文件,这次就可以正常显示了。但服务器上那么多文件,不可能一个一个的改,还得想其他的办法解决。在网上找了很久都没有任何头绪,似乎遇到这个问题的人很少。
??? 最后实在是没办法,只好把源代码下载下来研究一下看了,还真的找出了原因所在。
??? 因为resin在处理jsp文件的时候,会首先读取前面的几个字节来判断文件的格式,如果第一个字节是0xef、第二个字节是0xbb、第三个字节是0xbf,那么就认为这个文件是utf8格式,于是就自作主张的把contenttype设置成了text/html; charset=utf-8,然后在后面的处理过程中,因为jsp程序里面会有设置contenttype的指令,遇到这个指令会发现和之前的text/html; charset=utf-8不同,因此就抛出了异常。而如果没有bom格式的utf8,前面就不会有那三个字节的标识,所以就不会被处理了。
??? 相关代码:
<pre name='code' class='java'>    case 0xef:      if ((ch = stream.read()) != 0xbb) { stream.unread(); stream.unread();      }      else if ((ch = stream.read()) != 0xbf) { throw error(l.l("expected 0xbf in utf-8 header.  utf-8 pages with the initial byte 0xbb expect 0xbf immediately following.  the 0xbb 0xbf sequence is used by some application to suggest utf-8 encoding without a directive."));      }      else { _parsestate.setcontenttype("text/html; charset=utf-8"); _parsestate.setpageencoding("utf-8"); stream.setencoding("utf-8");      }      break;</pre>?
??? 判断冲突的代码:
??
<pre name='code' class='java'>  else if (content_type.equals(name)) {      string oldcontenttype = _parsestate.getcontenttype();            if (oldcontenttype != null &amp;&amp; ! value.equals(oldcontenttype))        throw error(l.l("contenttype '{0}' conflicts with previous value of contenttype '{1}'.  check the .jsp and any included .jsp files for conflicts.", value, oldcontenttype));            _parsestate.setcontenttype(value);      string charencoding = parsecharencoding(value);      if (charencoding != null) _parsestate.setcharencoding(charencoding);    }</pre>?
真不明白为什么resin要这么做呢,如果是web网站可能影响不大,contenttype本来就是text/html,但如果是wap或者其他contenttype的站点这么“智能”的编码判断方式问题就比较麻烦了。
?
?
附:utf-8 编码的文件可以分为no bom 和 bom两种格式(转载)
何谓bom? "ef bb bf" 这三个字节就叫bom,bom的全称叫做"byte order mard".在utf-8文件中常用bom来表明这个文件是utf-8文件,而bom的本意实在utf16中用来表示高低字节序列的。<br/>在字节流之前有bom表示采用低字节序列(低字节在前面),而utf8不用考虑字节序列,所以其实有无bom都可以。
<br/>微软的记事本 word 等只能正确打开含bom的utf8文件,然后ultraedit却恰恰相反,回把bomutf8文件 误认为ascii编码。
<br/>utf-8的bom是 efbbbf,因为ue载入utf-8文件会转成utf16,上述的efbbbf 在utf16中是fffe(unicode-le的bom),ultraedit不认识bom又加多一個bom,所以有2个fffe。<br/>文件就被它破坏了。
 
发表评论
用户名: 匿名