Pergunta

Eu queria desserializar uma mensagem XML contendo um elemento que pode ser marcado nil="true" em uma classe com uma propriedade do tipo int?. A única maneira que eu poderia obtê-lo para o trabalho era escrever meu próprio tipo NullableInt que implementa IXmlSerializable. Existe uma maneira melhor de fazer isso?

Eu escrevi o problema completo e da maneira que eu resolvi no meu blog .

Foi útil?

Solução

Eu acho que você precisa prefixar o nil = "true" com um espaço de nomes para que XmlSerializer para deserialise como nulo.

MSDN em xsi: nil

<?xml version="1.0" encoding="UTF-8"?>
<entities xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="array">
  <entity>
    <id xsi:type="integer">1</id>
    <name>Foo</name>
    <parent-id xsi:type="integer" xsi:nil="true"/>

Outras dicas

Meu correção é para pré-processar os nós, fixando quaisquer atributos "nada":

public static void FixNilAttributeName(this XmlNode @this)
{
    XmlAttribute nilAttribute = @this.Attributes["nil"];
    if (nilAttribute == null)
    {
        return;
    }

    XmlAttribute newNil = @this.OwnerDocument.CreateAttribute("xsi", "nil", "http://www.w3.org/2001/XMLSchema-instance");
    newNil.Value = nilAttribute.Value;
    @this.Attributes.Remove(nilAttribute);
    @this.Attributes.Append(newNil);
}

Eu Junte isso com uma pesquisa recursiva para nós filhos, de modo que para qualquer dado XmlNode (ou XmlDocument), eu posso emitir uma única chamada antes desserialização. Se você quiser manter o original estrutura em memória sem modificações, o trabalho com um Clone () do XmlNode.

A forma excepcionalmente preguiçoso para fazê-lo. É frágil para uma série de razões, mas o meu XML é simples o suficiente para justificar uma correção tão rápida e suja.

xmlStr = Regex.Replace(xmlStr, "nil=\"true\"", "xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:nil=\"true\"");
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top