我正在尝试从WCF中的服务方法返回一个复杂类型。我正在使用C#和.NET 4.这种复杂类型意味着不变(与.net字符串相同)。此外,该服务仅返回它,并且从不作为参数接收它。
如果我尝试仅在属性上定义getter,则会出现运行时错误。我想这是因为没有setter导致序列化失败。不过,我认为这种类型应该是不变的。
示例:
[DataContract]
class A
{
[DataMember]
int ReadOnlyProperty {get; private set;}
}
由于序列化问题,服务无法加载。
有没有办法在WCF DataContract上创建只读属性?也许通过更换序列化器?如果是这样,怎么样?如果没有,你会对这个问题提出什么建议?
谢谢,
阿萨夫
答案 0 :(得分:14)
将[DataMember]
放在后备字段上,您将不需要设置器。
答案 1 :(得分:9)
让你的setter公开以满足序列化程序,但只是不对setter做任何事情。不是“纯粹主义者”,而是完成它
public string MyProperty
{
get {
return this._myProperty
}
set {}
}
答案 2 :(得分:4)
您不能将属性设置为只读,但是通过使字段成为合同的一部分而不是属性,您可以接近只读:
[DataContract]
public class A
{
public class A(){}
public class A(int readonlyproperty){ _readonlyproperty = readonlyproperty}
[DataMember(Name = "ReadOnlyProperty")]
internal int _readonlyproperty;
public int ReadOnlyProperty {
get {return _readonlyproperty;}
private set {_readonlyproperty = value;}
}
接下来可以在wcf:
中访问您的内部[assembly: InternalsVisibleTo("System.Runtime.Serialization")]
有关如何利用此优势的一些示例:wcf-and-datacontract-serialization-internals-and-tips
答案 3 :(得分:2)
DataMember字段不能只读,因为wcf不按原样序列化对象,每次反序列化开始时都会使用默认构造函数创建新的对象实例。调度程序使用setter在反序列化后设置字段值。
但是所有上层文字都是一个大错误:)
要使它们真正只读,请创建服务器逻辑,验证thiss字段值。
答案 4 :(得分:0)
正如其他人所说,WCF需要吸气剂和制定者。 话虽这么说,我带着同样的问题来到这里,答案让我问为什么我需要一个只读属性。如果使用MVVM模式,则服务返回的类是Model,因此不应直接由UI公开。您可以轻松地将ViewModel设置为只读。或者,您可以使用非UI目标的Facade类。
答案 5 :(得分:0)
实际上,您可以将只读字段设置为可序列化。在构造DataContractSerializer时,需要将DataContractSerializerSettings的'SerializeReadOnlyTypes'属性设置为'True',如下所示:
var xmlSerializer = new DataContractSerializer(typeof(yourTypeHere), new DataContractSerializerSettings {SerializeReadOnlyTypes=true});
请参阅MSDN说明和详细信息,此处:https://msdn.microsoft.com/en-us/library/system.runtime.serialization.datacontractserializersettings(v=vs.110).aspx
答案 6 :(得分:0)
WCF需要能够序列化/反序列化属性,而私有属性是不可能的。拥有只读属性(在复杂类型中):
[DataContract(IsReference = true)]
public class Format : ValueObject<Format>
{
[DataMember]
public int Height { get; internal set; }
}
答案 7 :(得分:-1)
您是否尝试过将setter设为私有?
类似的东西:
public string MyProperty
{
get;
private set;
}