轉自
一個BUG的快速解決方法.希望能給大家的一些啟示朋友打來電話,他們公司新裝了TOMCAT5,然后在編譯JSP時,被INCLUDE的JSP都出現了問題.就是編譯后被INCLUDE的地方多了兩個"??"而其它正常,而如果手工把被INCLUDE的內容COPY上去測沒有問題.
他們的工程師都不知道是什么問題,因為周一要發布出去,所以非常著急.
我不知道大家聽到這種情況會如何,我知道大多數人比我聰明,你肯定想到了,所以你沒有必要再看了.我下面的內容只是對沒有想到的人而言.
其實他電話還沒打完 ,我就知道問題99%是他的jsp在編輯的時候是存為UTF-8而不是ANSI格式,否則沒有道理出現這種問題,事實正是如此,我讓他用UE打開看看果然前面多了幾個UTF字符.
重要的是TOMCAT這種容器竟然有這樣的BUG,不能正確讀取UTF-8格式的文件,你總不能強求用戶編輯JSP文件時一定要存為什么格式吧?
費話少說,下載tomcat5的src,進入jakarta-tomcat-jasper\jasper2\src\share\org\apache\jasper\compiler,找到JspUtil.java,找到
public static InputStream getInputStream(String fname, JarFile jarFile,
JspCompilationContext ctxt,
ErrorDispatcher err)
throws JasperException, IOException {
InputStream in = null;
if (jarFile != null) {
String jarEntryName = fname.substring(1, fname.length());
ZipEntry jarEntry = jarFile.getEntry(jarEntryName);
if (jarEntry == null) {
err.jspError("jsp.error.file.not.found", fname);
}
in = jarFile.getInputStream(jarEntry);
} else {
in = ctxt.getResourceAsStream(fname);
}
if (in == null) {
err.jspError("jsp.error.file.not.found", fname);
}
return in;
}
在return in前加上判斷,改成:
public static InputStream getInputStream(String fname, JarFile jarFile,
JspCompilationContext ctxt,
ErrorDispatcher err)
throws JasperException, IOException {
InputStream in = null;
if (jarFile != null) {
String jarEntryName = fname.substring(1, fname.length());
ZipEntry jarEntry = jarFile.getEntry(jarEntryName);
if (jarEntry == null) {
err.jspError("jsp.error.file.not.found", fname);
}
in = jarFile.getInputStream(jarEntry);
} else {
in = ctxt.getResourceAsStream(fname);
}
if (in == null) {
err.jspError("jsp.error.file.not.found", fname);
}
PushbackInputStream testin = new PushbackInputStream(in);
int ch = testin.read();
if (ch != 0xef) {
testin.unread(ch);
}
else if ((ch = testin.read()) != 0xbb) {
testin.unread(ch);
testin.unread(0xef);
}
else if ((ch = testin.read()) != 0xbf) {
throw new IOException("錯誤的UTF-8格式文件");
}
else{
//fStream.setEncoding("UTF-8");
testin.read();
}
return testin;
}
編譯,重新打包,替換原來的包,運行TOMCAT,OK!
整個問題解決除了遠程登錄他的服務器傳送文件的時間,總共只有4-5分鐘.其實只要問題定位準確,就不難解決了.我一再強調的是經熟悉底層,你如果知道內
存中每個byte從哪兒來要到哪兒去,就可以非常容易地解決問題.在此之前我連TOMCAT5下載都沒有下過,更別說試用了.但只要你對JDK有深入的了
解,就可以準確地定位問題的所在.
希望本文能給不是高手的朋友一點幫助和啟發,對于高手的朋友你可以棄之一笑.
UTF-8文件的Unicode簽名BOM(Byte Order Mark)問題utf-8編碼include頁面空格Django下碰到EF BB BF問題php utf-8編碼include頁面空格