![](/img/trans.png)
[英]MalformedByteSequenceException: Invalid byte 1 of 1-byte UTF-8 sequence
[英]I have UTF-8 - but still get “Invalid byte 1 of 1-byte UTF-8 sequence”
我動態創建一個XML String(不讀取文件)。 然后,我使用Cocoon 3將其通過FOP轉換為PDF。 Xerces在中間的某個地方運行。 當我使用硬編碼的東西時,一切正常。 一旦我將德國的Umlaut放入數據庫,並用該數據豐富了我的xml,我就會得到:
Caused by: org.apache.cocoon.pipeline.ProcessingException: Can't parse the XML string.
at org.apache.cocoon.sax.component.XMLGenerator$StringGenerator.execute(XMLGenerator.java:326)
at org.apache.cocoon.sax.component.XMLGenerator.execute(XMLGenerator.java:104)
at org.apache.cocoon.pipeline.AbstractPipeline.invokeStarter(AbstractPipeline.java:146)
at org.apache.cocoon.pipeline.AbstractPipeline.execute(AbstractPipeline.java:76)
at de.grobmeier.tab.webapp.modules.documents.InvoicePipeline.generateInvoice(InvoicePipeline.java:74)
... 87 more
Caused by: com.sun.org.apache.xerces.internal.impl.io.MalformedByteSequenceException: Invalid byte 1 of 1-byte UTF-8 sequence.
at com.sun.org.apache.xerces.internal.impl.io.UTF8Reader.invalidByte(UTF8Reader.java:684)
at com.sun.org.apache.xerces.internal.impl.io.UTF8Reader.read(UTF8Reader.java:554)
然后,我調試了我的應用程序,發現我的“Ä”(來自數據庫)的字節值為196,十六進制為C4。 這是我根據此期望的結果: http : //www.utf8-zeichentabelle.de/
我不知道為什么我的代碼失敗。
然后,我嘗試手動添加BOM,如下所示:
byte[] bom = new byte[3];
bom[0] = (byte) 0xEF;
bom[1] = (byte) 0xBB;
bom[2] = (byte) 0xBF;
String myString = new String(bom) + inputString;
我知道這不是很好,但是我嘗試了-當然失敗了。 我試圖在前面添加一個xml標頭:
<?xml version="1.0" encoding="UTF-8"?>
也失敗了。 然后,我將其合並。 失敗了
畢竟我嘗試過這樣的事情:
xmlInput = new String(xmlInput.getBytes("UTF8"), "UTF8");
實際上,它什么也沒做,因為它已經是UTF-8。 仍然失敗。
那么...有什么想法我做錯了什么以及Xerces對我的期望是什么?
謝謝克里斯蒂安
如果您的數據庫僅包含一個字節(值0xC4),則說明您未使用UTF-8編碼。
字符“帶DIAERESIS的拉丁文大寫字母A”的代碼點值為U + 00C4,但UTF-8不能在單個字節中對其進行編碼。 如果檢查UTF8-zeichentabelle.de上的第三列“ UTF-8(十六進制)”,您會看到UTF-8將其編碼為0xC3 84(兩個字節)。
請閱讀Joel的文章“ 絕對絕對要每個軟件開發人員絕對肯定地了解Unicode和字符集(無借口!) ”以獲取更多信息。
編輯:克里斯蒂安自己找到了答案; 原來,這是Cocoon 3 SAX組件中的問題(我想這是Alpha 3版本)。 事實證明,如果將XML作為字符串傳遞給XMLGenerator
類,則在SAX解析期間會出問題,從而導致混亂。
我查找了代碼以找到Cocoon-stax中的實際問題:
if (XMLGenerator.this.logger.isDebugEnabled()) {
XMLGenerator.this.logger.debug("Using a string to produce SAX events.");
}
XMLUtils.toSax(new ByteArrayInputStream(this.xmlString.getBytes()), XMLGenerator.this.getSAXConsumer();
如您所見,調用getBytes()
將使用JRE的默認編碼創建一個Byte數組,該數組隨后將無法解析。 這是因為XML聲明自己為UTF-8,而數據現在又以字節為單位,並且可能使用Windows代碼頁。
解決方法是,可以使用以下方法:
new org.apache.cocoon.sax.component.XMLGenerator(xmlInput.getBytes("UTF-8"),
"UTF-8");
這將觸發正確的內部動作(如Christian通過試驗API所發現的)。
我在Apache的錯誤跟蹤器中打開了一個問題 。
編輯2:該問題已修復,將包含在即將發布的版本中。
我正在將Windows 7和TextPad作為文本編輯器運行,以手動構建xml數據文件。 我正在獲取MalformedByteSequenceException
。 我在xml文件中的規格是UTF-8。 閑逛之后,我發現我的編輯器有一個工具“工具...轉換為DOS”。 我這樣做了,重新保存了文件,但異常消失了,我的代碼運行良好。
然后,我在編輯器中查看了該文件類型的默認編碼。 它是ASCII,但是當我將xml編碼參數更改為ASCII時,我得到了另一個不同的MalformedByteSequenceException
。
因此,在Windows系統上,您可以嘗試將xml編碼保留為UTF-8,但保存文件編碼的DOS。 我沒有進一步探討其工作原理。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.