Acessando dados fortemente tipados XML usando XPathNavigator

Como uma instância do modelo de dados XPath 2.0, a classe de XPathNavigator pode conter dados fortemente tipados que mapeiam a Common Language Runtime (CLR) tipos. De acordo com o modelo de dados XPath 2,0, somente os elementos e atributos podem conter dados fortemente tipados. A classe XPathNavigator fornece mecanismos para acessar dados em um objeto de XPathDocument ou de XmlDocument como dados fortemente tipados bem como mecanismos para converter de um tipo de dados para outro.

Informações de tipo expostos por XPathNavigator

XML 1,0 dados é tecnicamente sem tipo, a menos que processado com um DTD, o esquema de linguagem de definição de esquema XML (XSD), ou outro mecanismo. Há um número de categorias das informações que podem ser associadas com um elemento XML ou um atributo.

  • Tipos simples de CLR: Nenhum de suporte a Common Language Runtime (CLR) linguagens de esquema tipos XML diretamente. Porque é útil poder exibir conteúdo simples de elementos e atributos porque os a maioria exibe o tipo de CLR, todo o conteúdo simples pode ser digitado como String na ausência de informações de esquema com qualquer adicionadas informações de esquema que limita potencialmente esse conteúdo a um tipo apropriado. Você pode localizar o melhor tipo correspondente de CLR de conteúdo simples de elementos e atributos usando a propriedade de ValueType . Para saber mais sobre o mapeamento de tipos internos de esquema para tipos de CLR, confira Suporte a tipo nas classes System.Xml.

  • Listas de tipos simples (de CLR): Um elemento ou atributo com conteúdo simples podem conter uma lista de valores separados por um espaço em branco. Os valores são especificados por um esquema XML para ser um "tipo de lista". Na ausência de um esquema XML, esse conteúdo simples seria tratado como um só nó de texto. Quando um esquema XML está disponível, esse conteúdo simples pode ser exposta como uma série de valores atômicos cada um que tenha um tipo simples que mapeia a uma coleção de objetos CLR. Para saber mais sobre o mapeamento de tipos internos de esquema para tipos de CLR, confira Suporte a tipo nas classes System.Xml.

  • Valor tipado: Um atributo ou um elemento esquema- validado com um tipo simples têm um valor tipado. Esse valor é um tipo primitivo como um numérico, uma cadeia de caracteres, ou um tipo de dados. Todos os tipos simples internos em XSD podem ser mapeados para os tipos de CLR de que fornece acesso ao valor de um nó como um tipo mais apropriado em vez de apenas como String. Um elemento com atributos ou filhos do elemento é considerado ser um tipo complexo. O valor tipado de um tipo complexo com conteúdo simples (somente os nós de texto como filhos) é o mesmo que o do tipo simples de seu conteúdo. O valor tipado de um tipo complexo com conteúdo complexo (um ou mais elementos filho) é o valor da cadeia de caracteres de concatenação de todos os nós filhos de texto retornados como String. Para saber mais sobre o mapeamento de tipos internos de esquema para tipos de CLR, confira Suporte a tipo nas classes System.Xml.

  • Nome do tipo específico de linguagem Esquema-: Na maioria dos casos, os tipos de CLR, que são definidos como um efeito colateral de aplicar um esquema externo, são usados para fornecer acesso ao valor de um nó. No entanto, pode haver situações onde você pode querer examinar o tipo associado com um esquema específico aplicado a um documento XML. Por exemplo, você pode desejar pesquisar por um documento XML, extraindo todos os elementos que são determinados ter o conteúdo do tipo “PurchaseOrder” de acordo com o esquema anexado. Essas informações de tipo pode ser definida somente como resultado de validação de esquema e essa informação é acessada com XmlType e as propriedades de SchemaInfo de XPathNavigator classe. Para obter mais informações, consulte a seção de Infoset (PSVI) de validação do esquema de postagem abaixo.

  • Reflexão do tipo específico de linguagem Esquema-: Em outros casos, você pode desejar obter mais detalhes de tipo específico esquema- aplicado a um documento XML. Por exemplo, ao ler um arquivo XML, você pode querer extrair o atributo de maxOccurs para cada nó válido no documento XML para executar um cálculo personalizado. Porque essa informação é definida apenas com a validação do esquema, é acessada através da propriedade de SchemaInfo da classe de XPathNavigator . Para obter mais informações, consulte a seção de Infoset (PSVI) de validação do esquema de postagem abaixo.

XPathNavigator digitou acessadores

A tabela a seguir mostra as várias propriedades e métodos de XPathNavigator classe que pode ser usado para acessar informações de tipo sobre um nó.

Propriedade Descrição
XmlType Isso contém informações de tipo o esquema XML para o nó se é válido.
SchemaInfo Isso contém a validação Infoset do esquema de postagem de nó que é adicionado após a validação. Isso inclui informações de tipo do esquema XML, bem como informações de validade.
ValueType O tipo de CLR de valor tipado de nó.
TypedValue O conteúdo do nó como um ou mais valores de CLR cujo tipo é mais próximo correspondente ao tipo de esquema XML de nó.
ValueAsBoolean O valor de String de conversão atual do nó com um valor de Boolean , de acordo com o XPath 2,0 regras para converter xs:boolean.
ValueAsDateTime O valor de String de conversão atual do nó com um valor de DateTime , de acordo com o XPath 2,0 regras para converter xs:datetime.
ValueAsDouble O valor de String de conversão atual do nó com um valor de Double , de acordo com o XPath 2,0 regras para converter xsd:double.
ValueAsInt O valor de String de conversão atual do nó com um valor de Int32 , de acordo com o XPath 2,0 regras para converter xs:integer.
ValueAsLong O valor de String de conversão atual do nó com um valor de Int64 , de acordo com o XPath 2,0 regras para converter xs:integer.
ValueAs O conteúdo do nó convertem ao tipo de destino de acordo com o XPath 2,0 regras converter.

Para saber mais sobre o mapeamento de tipos internos de esquema para tipos de CLR, confira Suporte a tipo nas classes System.Xml.

A validação Infoset (PSVI) do esquema de postagem

Um processador XML de esquema XML Infoset aceita como entrada e o converte em uma validação Infoset (PSVI) do esquema de postagem. Um PSVI é o infoset original XML de entrada com novos elementos de informações adicionados e as novas propriedades adicionadas a elementos existentes de informações. Há três classes de informações de adicionadas a Infoset XML em PSVI que são expostos por XPathNavigator.

  1. Resultados de validação: Informações se um elemento ou atributo estiverams bem-sucedida ou não. Isso expõe a propriedade de Validity de propriedade de SchemaInfo da classe de XPathNavigator .

  2. Informações padrão: Em se o valor de elemento ou atributo foi obtido através dos valores padrão especificado no esquema ou não. Isso expõe a propriedade de IsDefault de propriedade de SchemaInfo da classe de XPathNavigator .

  3. Anotações do tipo: Referências a componentes do esquema que podem ser definições de tipo ou declarações de elementos e atributos. A propriedade de XmlType de XPathNavigator contém informações de tipo específico de nó se é válido. Se a validade de um nó é desconhecida, como quando ele foi validado em editou posteriormente. a propriedade de XmlType é definida na null mas informações de tipo está disponível ainda das várias propriedades de propriedade de SchemaInfo da classe de XPathNavigator .

O exemplo a seguir ilustra usando as informações na validação Infoset do esquema de postagem expostos por XPathNavigator.

Dim settings As XmlReaderSettings = New XmlReaderSettings()  
settings.Schemas.Add("http://www.contoso.com/books", "books.xsd")  
settings.ValidationType = ValidationType.Schema  
  
Dim reader As XmlReader = XmlReader.Create("books.xml", settings)  
  
Dim document As XmlDocument = New XmlDocument()  
document.Load(reader)  
Dim navigator As XPathNavigator = document.CreateNavigator()  
navigator.MoveToChild("books", "http://www.contoso.com/books")  
navigator.MoveToChild("book", "http://www.contoso.com/books")  
navigator.MoveToChild("published", "http://www.contoso.com/books")  
  
Console.WriteLine(navigator.SchemaInfo.SchemaType.Name)  
Console.WriteLine(navigator.SchemaInfo.Validity)  
Console.WriteLine(navigator.SchemaInfo.SchemaElement.MinOccurs)  
XmlReaderSettings settings = new XmlReaderSettings();  
settings.Schemas.Add("http://www.contoso.com/books", "books.xsd");  
settings.ValidationType = ValidationType.Schema;  
  
XmlReader reader = XmlReader.Create("books.xml", settings);  
  
XmlDocument document = new XmlDocument();  
document.Load(reader);  
XPathNavigator navigator = document.CreateNavigator();  
navigator.MoveToChild("books", "http://www.contoso.com/books");  
navigator.MoveToChild("book", "http://www.contoso.com/books");  
navigator.MoveToChild("published", "http://www.contoso.com/books");  
  
Console.WriteLine(navigator.SchemaInfo.SchemaType.Name);  
Console.WriteLine(navigator.SchemaInfo.Validity);  
Console.WriteLine(navigator.SchemaInfo.SchemaElement.MinOccurs);  

O exemplo usa o arquivo books.xml como entrada.

<books xmlns="http://www.contoso.com/books">  
    <book>  
        <title>Title</title>  
        <price>10.00</price>  
        <published>2003-12-31</published>  
    </book>  
</books>  

O exemplo também usa o esquema de books.xsd como entrada.

<xs:schema xmlns="http://www.contoso.com/books"
attributeFormDefault="unqualified" elementFormDefault="qualified"
targetNamespace="http://www.contoso.com/books"
xmlns:xs="http://www.w3.org/2001/XMLSchema">  
    <xs:simpleType name="publishedType">  
        <xs:restriction base="xs:date">  
            <xs:minInclusive value="2003-01-01" />  
            <xs:maxInclusive value="2003-12-31" />  
        </xs:restriction>  
    </xs:simpleType>  
    <xs:complexType name="bookType">  
        <xs:sequence>  
            <xs:element name="title" type="xs:string"/>  
            <xs:element name="price" type="xs:decimal"/>  
            <xs:element name="published" type="publishedType"/>  
        </xs:sequence>  
    </xs:complexType>  
    <xs:complexType name="booksType">  
        <xs:sequence>  
            <xs:element name="book" type="bookType" />  
        </xs:sequence>  
    </xs:complexType>  
    <xs:element name="books" type="booksType" />  
</xs:schema>  

Obtenha valores tipados usando propriedades de ValueAs

O valor tipado de um nó pode ser recuperado acessando a propriedade de TypedValue de XPathNavigator. Em alguns casos você pode querer converter o valor tipado de um nó para um tipo diferente. Um exemplo comum é obter um valor numérico de um nó XML. Por exemplo, considere o seguinte documento XML unvalidated e sem tipo.

<books>  
    <book>  
        <title>Title</title>  
        <price>10.00</price>  
        <published>2003-12-31</published>  
    </book>  
</books>  

Se XPathNavigator é posicionado no elemento de price a propriedade de XmlType seria null, a propriedade de ValueType seria String, e a propriedade TypedValue seria a cadeia de caracteres 10.00.

No entanto, ainda é possível extrair o valor como um valor numérico usando ValueAs, ValueAsDouble, ValueAsInt, ou métodos e propriedades de ValueAsLong . O exemplo a seguir ilustra executar uma conversão usando o método ValueAs .

Dim document As New XmlDocument()  
document.Load("books.xml")  
Dim navigator As XPathNavigator = document.CreateNavigator()  
navigator.MoveToChild("books", "")  
navigator.MoveToChild("book", "")  
navigator.MoveToChild("price", "")  
  
Dim price = navigator.ValueAs(GetType(Decimal))  
Dim discount As Decimal = 0.2  
  
Console.WriteLine("The price of the book has been dropped 20% from {0:C} to {1:C}", navigator.Value, (price - price * discount))  
XmlDocument document = new XmlDocument();  
document.Load("books.xml");  
XPathNavigator navigator = document.CreateNavigator();  
navigator.MoveToChild("books", "");  
navigator.MoveToChild("book", "");  
navigator.MoveToChild("price", "");  
  
Decimal price = (decimal)navigator.ValueAs(typeof(decimal));  
  
Console.WriteLine("The price of the book has been dropped 20% from {0:C} to {1:C}", navigator.Value, (price - price * (decimal)0.20));  

Para saber mais sobre o mapeamento de tipos internos de esquema para tipos de CLR, confira Suporte a tipo nas classes System.Xml.

Confira também