xml - 从 DotNetXmlSerializer 中省略 xmlns 和 d4p1
问题描述
我使用发送 Webrequest
var request = new RestRequest(string.Format(url, config.ApiLocale), Method.POST)
{
RequestFormat = DataFormat.Xml,
XmlSerializer = new RestSharp.Serializers.DotNetXmlSerializer("")
};
我的请求是这样构建的:
List<RequestParam> listParams = new List<RequestParam>()
{
new RequestParam("Foo1"),
new RequestParam("Foo2"),
new RequestParam(12345)
};
request.AddBody(new XmlRequest
{
MethodName = "api.Testcall",
ListParams = listParams
});
我的课程:
using RestSharp.Deserializers;
using System;
using System.Collections.Generic;
using System.Xml.Serialization;
namespace Testcall
{
[XmlRoot("methodCall")]
public class XmlRequest
{
[XmlElement(ElementName = "methodName")]
public string MethodName { get; set; }
[XmlArray(ElementName = "params")]
[XmlArrayItem("param")]
public List <RequestParam> ListParams { get; set; }
}
public class RequestParam
{
[XmlElement(ElementName = "value")]
public ParamFather Value { get; set; }
public RequestParam() { }
public RequestParam(String PassValue)
{
Value = new StringParam(PassValue);
}
public RequestParam(int PassValue)
{
Value = new IntParam(PassValue);
}
public RequestParam(Boolean PassValue)
{
Value = new BoolParam(PassValue);
}
}
[XmlInclude(typeof(StringParam))]
[XmlInclude(typeof(BoolParam))]
[XmlInclude(typeof(IntParam))]
public class ParamFather
{
[XmlElement(ElementName = "father")]
public String Content { get; set; }
}
public class StringParam : ParamFather
{
[XmlElement(ElementName = "string")]
public String StringContent { get; set; }
public StringParam() { }
public StringParam(String Content)
{
StringContent = Content;
}
}
}
但是序列化器返回一个包含 Strange d4p1 和 xmlns-Tags 的 XML。那些我想省略的!我只需要不带任何标签的普通 xml。
<methodCall>
<methodName>api.Testcall</methodName>
<params>
<param>
<value d4p1:type=\"StringParam\" xmlns:d4p1=\"http://www.w3.org/2001/XMLSchema-instance\">
<string>Foo1</string>
</value>
</param>
<param>
<value d4p1:type=\"StringParam\" xmlns:d4p1=\"http://www.w3.org/2001/XMLSchema-instance\">
<string>Foo2</string>
</value>
</param>
<param>
<value d4p1:type=\"IntParam\" xmlns:d4p1=\"http://www.w3.org/2001/XMLSchema-instance\">
<int>12345</int>
</value>
</param>
</params>
</methodCall>
我尝试使用经典的 XMLSerializer 但失败了。完全可以使用 DotNetXmlSerializer 来做到这一点吗?
解决方案
最后我通过切换到标准的 XmlSerializer 解决了这个问题。
[XmlRoot("methodCall")]
public class XmlRequest
{
[XmlElement(ElementName = "methodName")]
public string MethodName { get; set; }
[XmlArray(ElementName = "params")]
[XmlArrayItem("param")]
public List <RequestParam> ListParams { get; set; }
public string ToXML()
{
using (var stringwriter = new System.IO.StringWriter())
{
using (var xmlwriter = XmlWriter.Create(stringwriter, new XmlWriterSettings { OmitXmlDeclaration = true }))
{
XmlSerializerNamespaces ns = new XmlSerializerNamespaces(); ns.Add("", "");
new XmlSerializer(this.GetType()).Serialize(xmlwriter, this, ns);
}
return stringwriter.ToString();
}
}
}
我这样称呼它:
List<RequestParam> listParams = new List<RequestParam>()
{
new RequestParam("user"),
new RequestParam("password"),
new RequestParam(true),
new RequestParam(123)
};
request.Parameters.Clear();
XmlRequest reqObject = new XmlRequest
{
MethodName = "api.Testcall",
ListParams = listParams
};
string rawXml = reqObject.ToXML();
request.AddParameter("application/xml", rawXml, ParameterType.RequestBody);
请注意,我现在使用的是 request.AddParameter 而不是我之前使用的 request.AddBody。所以我有更多的控制权,通过标准的 XmlSerializer 创建一个字符串。OmitXmlDeclaration 抑制 xml-Document 的编码和标准开始。我的课程也发生了变化:
public class RequestParam
{
[XmlElement(ElementName = "value")]
public Alterable Value { get; set; }
public RequestParam() { }
public RequestParam(int number)
{
Value = new Alterable(number);
}
public RequestParam(String str)
{
Value = new Alterable(str);
}
public RequestParam(Boolean boo)
{
Value = new Alterable(boo);
}
}
public class Alterable
{
[XmlElement(DataType = "string",Type = typeof(string)),
XmlElement(DataType = "int",Type = typeof(int)),
XmlElement(DataType = "boolean",Type = typeof(Boolean))]
public object Changeable { get; set; }
public Alterable() { }
public Alterable(int number)
{
Changeable = number;
}
public Alterable(string str)
{
Changeable = str;
}
public Alterable(Boolean boo)
{
Changeable = boo;
}
}
我的 Alterable 类可以接受字符串、整数和布尔值,并将它们正确地打印到 XML 中。希望这可以帮助遇到同样问题的人。
结果:
<methodCall>
<methodName>api.Testcall</methodName>
<params>
<param>
<value>
<string>user</string>
</value>
</param>
<param>
<value>
<string>password</string>
</value>
</param>
<param>
<value>
<boolean>true</boolean>
</value>
</param>
<param>
<value>
<int>123</int>
</value>
</param>
</params>
</methodCall>
推荐阅读
- java - 如何使用 RETROFIT 库使用 java 或 php 从 android studio 中的 mysql 数据库中检索值?
- java - 发送 Camel HTTP Post 自定义正文
- datetime - Lotus Notes 日期时间
- scala - 在 src_managed 文件夹中时找不到对象
- node.js - Web 应用程序中用户数据的数据结构
- laravel - 如何从laravel 5.6注销
- reactjs - 动态加载 sagas 以在 redux 应用程序中进行代码拆分
- cmake - CMake 中的 FindSDL2 发生了什么?
- python - Python 只读取文本文件的某些行
- docker - 试图加入工作节点以掌握主状态就绪工作状态未准备好