是否有一种方法可以通过JsonConvert或任何其他函数返回没有XML和名称空间的干净Json对象?我有一个从远程肥皂服务获取数据的websercice,我为用户提供了获取XML或Json数据的选项。我得到的XML看起来像这样。
<?xml version="1.0"?>
<ATT_ADDR_VAL_RESP xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<ADDR_VAL_RESP xmlns="http://lsr.att.com/obf/tML/UOM">
<HDR>
<MESSAGE_ID>FROMCLIENTAPPLET</MESSAGE_ID>
<MSG_TIMESTAMP>2020-03-11T16:24:07</MSG_TIMESTAMP>
<TXNUM>temP</TXNUM>
<DTSENT>202003110424PM</DTSENT>
</HDR>
<RESP_STATUS_GRP>
<RESPC>003</RESPC>
<RESPD>Address Match Found</RESPD>
</RESP_STATUS_GRP>
<ATT_ADDR_INFO>
<FEP>X</FEP>
<SVC_ADDR_GRP>
<SANO>818</SANO>
<SASD>W</SASD>
<SASN>7TH</SASN>
<TAR>001</TAR>
</SVC_ADDR_GRP>
</ATT_ADDR_INFO>
</ADDR_VAL_RESP>
</ATT_ADDR_VAL_RESP>
当我将其转换为JSON时,它看起来像这样。
{
"?xml": {
"@version": "1.0"
},
"ATT_ADDR_VAL_RESP": {
"@xmlns:xsi": "http://www.w3.org/2001/XMLSchema-instance",
"@xmlns:xsd": "http://www.w3.org/2001/XMLSchema",
"ADDR_VAL_RESP": {
"@xmlns": "http://lsr.att.com/obf/tML/UOM",
"HDR": {
"MESSAGE_ID": "FROMCLIENTAPPLET",
"MSG_TIMESTAMP": "2020-03-11T16:28:50",
"TXNUM": "temP",
"DTSENT": "202003110428PM"
},
但是我希望它看起来像这样
{
"ATT_ADDR_VAL_RESP": {
"ADDR_VAL_RESP": {
"HDR": {
"MESSAGE_ID": "FROMCLIENTAPPLET",
"MSG_TIMESTAMP": "2020-03-11T16:28:50",
"TXNUM": "temP",
"DTSENT": "202003110428PM"
}, .....
所以问题是,有没有办法做到这一点,然后将xml响应作为一部分并删除任何多余的东西,例如名称空间等,并创建一个新对象以json编码的形式返回。
答案 0 :(得分:0)
可以用许多不同的方式来解析源XML文件或字符串。我选择XmlDocument类是因为它易于使用并且直接与JSON序列化程序兼容。
XML有两个元素:
-定义XML版本的序言(但未定义编码:采用UTF-8)
-根元素(ATT_ADDR_VAL_RESP
),其中包含将XML转换为JSON格式时需要删除的属性。
XmlDocument.Load()或XmlDocument.LoadXml()方法可用于生成XML Document对象。
-前者需要一个Stream或一个表示文件路径的字符串(或Xml / Text阅读器)
-后者仅解析XML字符串
假设它是一个Stream,我们可以使用其Load()
方法生成XmlDocument:
Dim doc = New XmlDocument()
doc.Load([XML Stream])
' or doc.Load([XML File Path])
' or doc.LoadXml([XML String])
要删除prolog元素,我们可以删除XmlDocument的第一个子节点:
doc.RemoveChild(doc.FirstChild)
由于需要保留Root元素( ATT_ADDR_VAL_RESP
)(如示例结果所示),因此应删除其属性,因此我们可以使用XmlNode.Attributes集合的RemoveAll()方法来执行清理:
doc.FirstChild.Attributes.RemoveAll()
如果不是真的需要Root元素,我们还可以使用JsonConvert.SerializeXmlNode重载,该重载可以指定是否应保留Root元素:
Dim json = JsonConvert.SerializeXmlNode(doc, Formatting.Indented, True)
最后一个参数指定应省略Root元素。
Root元素的第一个子节点还包含需要删除的参数:
For Each childNode As XmlNode in doc.FirstChild.ChildNodes
childNode.Attributes.RemoveAll()
Next
所有部分组合在一起,使用Json.NET将XML序列化为JSON字符串:
Dim doc = New XmlDocument()
doc.Load([XML Stream])
' FirstChild is the prolog element
doc.RemoveChild(doc.FirstChild)
' Now FirstChild is the XML Root element
doc.FirstChild.Attributes.RemoveAll()
For Each childNode As XmlNode in doc.FirstChild.ChildNodes
childNode.Attributes.RemoveAll()
Next
' Or RemoveAllAttributes(doc)
Dim json = JsonConvert.SerializeXmlNode(doc, Formatting.Indented)
如果需要删除所有子节点的属性,则可以使用递归方法代替循环:
RemoveAllAttributes(doc)
(...)
Private Sub RemoveAllAttributes(XmlNode node)
if node.Attributes IsNot Nothing Then node.Attributes.RemoveAll()
For Each childNode As XmlNode In node.ChildNodes
If childNode.Attributes IsNot Nothing Then childNode.Attributes.RemoveAll()
If childNode.HasChildNodes Then
RemoveAllAttributes(childNode)
End if
Next
End Sub