2010-12-14 40 views
11

我有以下代碼(C#),它的時間太長,它拋出異常:.NET:防止XmlDocument.LoadXml從檢索DTD

new XmlDocument(). 
LoadXml("<?xml version='1.0' ?><!DOCTYPE note SYSTEM 'http://someserver/dtd'><note></note>"); 

我明白爲什麼它做到這一點。我的問題是如何讓它停止?我不關心DTD驗證。我想我可以只是正則表達式 - 替換它,但我正在尋找更優雅的解決方案。

背景:
實際的XML是從我沒有的網站收到的。當站點進行維護時,它會返回帶有DOCTYPE的XML,該DOCTYPE指向在維護期間不可用的DTD。所以我的服務變得不必要的慢,因爲它試圖爲我需要解析的每個XML獲取DTD。

這裏是異常堆棧:

Unhandled Exception: System.Net.WebException: The remote name could not be resolved: 'someserver' 
at System.Net.HttpWebRequest.GetResponse() 
at System.Xml.XmlDownloadManager.GetNonFileStream(Uri uri, ICredentials credentials) 
at System.Xml.XmlDownloadManager.GetStream(Uri uri, ICredentials credentials) 
at System.Xml.XmlUrlResolver.GetEntity(Uri absoluteUri, String role, Type ofObjectToReturn) 
at System.Xml.XmlTextReaderImpl.OpenStream(Uri uri) 
at System.Xml.XmlTextReaderImpl.DtdParserProxy_PushExternalSubset(String systemId, String publicId) 
at System.Xml.XmlTextReaderImpl.DtdParserProxy.System.Xml.IDtdParserAdapter.PushExternalSubset(String systemId, String publicId) 
at System.Xml.DtdParser.ParseExternalSubset() 
at System.Xml.DtdParser.ParseInDocumentDtd(Boolean saveInternalSubset) 
at System.Xml.DtdParser.Parse(Boolean saveInternalSubset) 
at System.Xml.XmlTextReaderImpl.DtdParserProxy.Parse(Boolean saveInternalSubset) 
at System.Xml.XmlTextReaderImpl.ParseDoctypeDecl() 
at System.Xml.XmlTextReaderImpl.ParseDocumentContent() 
at System.Xml.XmlTextReaderImpl.Read() 
at System.Xml.XmlLoader.LoadDocSequence(XmlDocument parentDoc) 
at System.Xml.XmlLoader.Load(XmlDocument doc, XmlReader reader, Boolean preserveWhitespace) 
at System.Xml.XmlDocument.Load(XmlReader reader) 
at System.Xml.XmlDocument.LoadXml(String xml) 
at ConsoleApplication36.Program.Main(String[] args) in c:\Projects\temp\ConsoleApplication36\Program.cs:line 11 

回答

10

好了,在.NET 4.0中的XmlTextReader有一個名爲DtdProcessing屬性。設置爲DtdProcessing.Ignore時,應禁用DTD處理。

+0

.NET 3.5怎麼樣? – 2010-12-17 04:17:29

+0

您應該嘗試將XmlReader.Settings.ValidationType設置爲ValidationType.None。另外,我認爲將XmlReader.Settings.XmlResolver設置爲null也可以做到這一點 – 2010-12-17 09:07:54

+13

確認的'doc.XmlResolver = null;'解決了這個問題。 – 2010-12-17 16:54:44

0

在.net 4.5.1我沒有運氣設置doc.XmlResolver爲null。

最簡單的解決方法是在調用LoadXml()之前,使用字符串替換將「xmlns =」更改爲「ignore =」。

var responseText = await response.Content.ReadAsStringAsync(); 
responseText = responseText.Replace("xmlns=", "ignore="); 
try 
{ 
    var doc = new XmlDocument(); 
    doc.LoadXml(responseText); 
    ... 
}