反序列化时如何将 XML 节点值作为字符串获取 [英] How to get an XML node value as string when deserializing
问题描述
我正在向 aspnet 核心 web api 发送一个 XML.命名空间前缀 cfdi:
的值在包含节点中定义:
I am sending a XML to a aspnet core web api. The value for the namespace prefix cfdi:
is defined in a containing node:
<cfdi:Comprobante>
<cfdi:Conceptos>
</cfdi:Conceptos>
<cfdi:Addenda>
<bfa2:AddendaBuzonFiscal version="2.0" xmlns:bfa2="http://www.buzonfiscal.com/ns/addenda/bf/2"><bfa2:TipoDocumento nombreCorto="FAC" descripcion="Factura"/><bfa2:CFD totalConLetra="CINCUENTA Y DOS MIL QUINIENTOS OCHENTA Y NUEVE PESOS 64/100 M.N." observaciones="OBSERVACIONES"/><bfa2:Extra atributo="ClaveTransportista" valor="00328"/><bfa2:Extra atributo="NoRelacionPemex" valor="1-2"/>
<bfa2:Extra atributo="NoConvenio" valor="5"/>
</bfa2:AddendaBuzonFiscal>
<Encabezado NumOrden="" NumFacturaOriginal="" FechaDePedido=""/>
<Envio Calle="" NoExterior="" Colonia="" Localidad="" Municipio="" Estado="" Pais="" CodigoPostal="" NombreEnviar=""/><Detalle OrdenCompraLinea="10" GRNumber="GRN"/><Detalle OrdenCompraLinea="10" GRNumber="GRN"/><Detalle OrdenCompraLinea="10" GRNumber="GRN"/>
</cfdi:Addenda>
</cfdi:Comprobante>
为了反序列化,我创建了 Compprobante
类:
To deserialize this I made the class Comprobante
:
public class Comprobante : IValidatableObject
{
[Required]
[XmlArray("Conceptos"), XmlArrayItem(typeof(Concepto), ElementName = "Concepto")]
public List<Concepto> Conceptos { get; set; }
public Addenda Addenda { get; set; }
}
一切都映射到类属性,但 Addenda
节点可以接收任何东西——任意数量的有效 XML 节点——所以我没有类定义.IE.Addenda
节点可能包含 n 个我不知道的节点,信息在接收端进行验证.例如,客户可以要求添加具有采购订单编号的节点,另一个可以要求买方名称.等
Everything is mapped to the class properties but the Addenda
node could receive anything -- any number of valid XML nodes -- so I don´t have a class definition. I.e. the Addenda
node could contain n nodes that I don’t know about, the information is validated in the recipient end. For example a customer could ask to add a node with a PO number, another could ask for buyer name. Etc.
如果我需要将所有 Addenda
节点内容作为字符串获取,我应该如何在类中声明它?
If I need to get all the Addenda
node content as string, how should I declare it in the class?
推荐答案
您可以使用 XmlSerializer
通过使用 [XmlAnyElement]
.
You can deserialize arbitrary, free-form XML data using XmlSerializer
by marking target properties with [XmlAnyElement]
.
例如您可以按如下方式定义 Addenda
类型:
E.g. you can define your Addenda
type as follows:
[XmlRoot("Comprobante", Namespace = "http://cfdi")]
public class Comprobante : IValidatableObject
{
[Required]
[XmlArray("Conceptos"), XmlArrayItem(typeof(Concepto), ElementName = "Concepto")]
public List<Concepto> Conceptos { get; set; }
public Addenda Addenda { get; set; }
}
public class Addenda
{
[XmlAnyElement]
[XmlText]
public XmlNode[] Nodes { get; set; }
}
或者,您可以完全消除 Addenda
类型并将其替换为 XmlElement
包含类型中的属性:
Or, you could eliminate the Addenda
type completely and replace it with an XmlElement
property in the containing type:
[XmlRoot("Comprobante", Namespace = "http://cfdi")]
public class Comprobante : IValidatableObject
{
[Required]
[XmlArray("Conceptos"), XmlArrayItem(typeof(Concepto), ElementName = "Concepto")]
public List<Concepto> Conceptos { get; set; }
[XmlAnyElement("Addenda")]
public XmlElement Addenda { get; set; }
}
注意事项:
当应用没有元素名称时,
[XmlAnyElement]
指定该成员是XmlElement
或XmlNode
对象的数组,这些对象将包含所有未绑定到包含类型中的其他成员的任意 XML 数据.
When applied without an element name,
[XmlAnyElement]
specifies that the member is an array ofXmlElement
orXmlNode
objects which will contain all arbitrary XML data that is not bound to some other member in the containing type.
当应用与元素名称(和可选命名空间)时,[XmlAnyElement("Addenda")]
指定该成员是单个 XmlElement
对象或此类对象的数组,并将包含所有名为
的任意 XML 元素.使用这种形式不需要额外的 Addenda
类型.
When applied with an element name (and optional namespace), [XmlAnyElement("Addenda")]
specifies that the member is a either a single XmlElement
object or an array of such objects, and will contain all arbitrary XML elements named <Addenda>
. Using this form eliminates the need for the extra Addenda
type.
结合[XmlText]
和 [XmlAnyElement]
允许反序列化任意混合内容.
Combining [XmlText]
with [XmlAnyElement]
allows arbitrary mixed content to be deserialized.
如果您使用 .NET Core,您可能需要 nuget 系统.Xml.XmlDocument.
If you are using .NET Core you may need to nuget System.Xml.XmlDocument.
这篇关于反序列化时如何将 XML 节点值作为字符串获取的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!