2010-04-18 35 views
1

我有這樣一個XML文件:比element.Elements更好的解決方案(「無論」)。First()?

<SiteConfig> 
    <Sites> 
    <Site Identifier="a" /> 
    <Site Identifier="b" /> 
    <Site Identifier="c" /> 
    </Sites> 
</SiteConfig> 

該文件是用戶可編輯的,所以我想提供合理的錯誤消息的情況下,我不能正確解析它。我大概可以爲它寫一個.xsd,但對於一個簡單的文件來說似乎有點矯枉過正。

所以無論如何,查詢<Site>節點列表時,有一對夫婦的方法,我能做到這一點:

var doc = XDocument.Load(...); 

var siteNodes = from siteNode in 
        doc.Element("SiteConfig").Element("Sites").Elements("Site") 
       select siteNode; 

但這樣做的問題是,如果用戶不包含<SiteUrls>節點(說)它只會拋出一個NullReferenceException這實際上並沒有真正向用戶說什麼實際上出了什麼問題。

另一種可能性就是使用Elements()無處不在,而不是Element(),但是,當與呼叫連接到Attribute(),例如,在以下情況不總是工作:

var siteNodes = from siteNode in 
        doc.Elements("SiteConfig") 
        .Elements("Sites") 
        .Elements("Site") 
       where siteNode.Attribute("Identifier").Value == "a" 
       select siteNode; 

(也就是說,有沒有相當於Attributes("xxx").Value

是否有內置的框架來處理這種情況好一點?我寧願是Element()(和Attribute()雖然我們在它)拋出一個異常描述(例如,「下<ABC>尋找元素<XYZ>,但沒有這樣的元素被發現」),而不是返回null版本。

我可以寫我自己的Element()Attribute()版本,但它只是似乎對我來說,這是我必須失去了一些東西,例如常見的場景...

+2

可能需要更新你上面的XML例子 - 沒有列出'SiteURLs'元素。 – 2010-04-18 11:25:03

+0

@Otaku:另一方面,也許他不應該改變它,因爲它確實證明了他想解決的問題。 – 2010-04-18 11:41:21

+0

宅男:對不起,這是我的項目中出現的一個''''''錯誤的錯誤:-) – 2010-04-18 11:58:15

回答

2

你可以實現你想要的功能擴展方法:

public static class XElementExtension 
{ 
    public static XElement ElementOrThrow(this XElement container, XName name) 
    { 
     XElement result = container.Element(name); 
     if (result == null) 
     { 
      throw new InvalidDataException(string.Format(
       "{0} does not contain an element {1}", 
       container.Name, 
       name)); 
     } 
     return result; 
    } 
} 

您將需要爲XDocument類似的東西。然後使用它是這樣的:

var siteNodes = from siteNode in 
    doc.ElementOrThrow("SiteConfig") 
     .ElementOrThrow("SiteUrls") 
     .Elements("Sites") 
    select siteNode; 

然後你會得到這樣一個例外:

 
SiteConfig does not contain an element SiteUrls 
+0

是的,我認爲這就是我要去的。我可能會同時創建一個XSD文件,因爲這還會讓Visual Studio執行智能感知的額外好處:) – 2010-04-18 13:30:47

0

你可以使用XPathSelectElements

想到的另一件事是定義一個XSD模式並根據此模式驗證您的XML文件。這將生成有意義的錯誤消息,如果該文件有效,則可以毫無問題地解析它。

相關問題