我发现今天MVC4使用的XML和Json序列化器之间存在相当大的差异。
我试图返回一个如下所示的对象:
public class Person
{
public string FirstName {get;set;}
public string LastName {get;set;}
public string FullName{ get{ return FirstName + " " + LastName }}
}
当客户端请求json作为结果时,我得到FirstName
,LastName
和FullName
返回的预期值。
但是,当客户端要求提供XML数据时,他只会获得FirstName
和LastName
。
这在我看来非常糟糕,因为这意味着客户端将根据他们请求的格式获得不同的数据。
这似乎是故意的,因为Json序列化程序的文档默认包含只读属性,默认情况下,Xml序列化程序包含它们。
所以我的问题是:如何修改MVC4使用的Xml序列化程序,默认情况下包含那些只读。我知道它设法,因为如果你将DataContract
属性添加到类,并且DataMember
属性添加到类的每个属性,它也返回只读变量,但我真的不我想这样做。
答案 0 :(得分:0)
您必须使用datacontractserializer并使用DataContract属性标记您的实体,并使用DataMember序列化每个成员。
datacontractserializer允许序列化只读属性。
答案 1 :(得分:0)
首先,我会推荐这篇文章:
因为它在WebAPI / MVC中提供了一个很好的序列化概要,包括展示如何告诉MVC使用什么序列化程序(如果你决定实现自己来解决只读问题)
现在,如果你想使用默认的序列化程序(DataContract或Xml),遗憾的是你不能告诉它自动序列化只读属性;这是设计 - 如果你考虑它,它会产生某种意义;因为XML序列化的典型用例是
我认为这是因为传统上(在您可能希望通过HTTP将此数据发送到基于弱类型浏览器的语言的概念之前),将只读属性序列化很少或没有意义 - 因为您无法反序列化回原始类型,因为该字段是只读的!
当然,现在很有意义的是你可能需要这些,我确信JSON序列化程序人员在决定为JSON默认包含只读属性时会考虑到这一点,因为更典型的用途 - 这种情况不是序列化回强类型实例而是动态类型java脚本对象。
即 给定
public class Foo
{
public int Bar { get; set; }
public string BarName { get { return "This is Bar# " + Bar; } }
}
我们假设默认情况下Xml或DataContract Serializer产生了这个:
<Foo>
<Bar>10</Bar>
<BarName>This is Bar# 10</BarName>
</Foo>
您希望以下代码如何工作?
var xs = new XmlSerializer(typeof(Foo));
var y = xs.Deserialize(new StreamReader(@"C:\foo.xml")) as Foo;
没有抛出BarName
是只读属性的异常?
不可设置属性的全部要点是构成getter
返回值的条件对调用者来说是未知的(即私有),因此无法序列化...
因此DataContract
和DataMembers
允许您覆盖默认行为。