views:

518

answers:

3

In C#, if I want to serialize an instance with XmlSerializer, the object's type doesn't have to be marked with [Serializable] attribute. However, for other serialization approaches, such as DataContractSerializer, needs the class be marked as [Serializable] or [DataContract].

Is there any standard or pattern about serialization requirement?

+7  A: 

This is because XmlSerializer only serializes public fields/properties. Other forms of serialization can serialize private data, which constitutes a potential security risk, so you have to "opt in" using an attribute.

Eric Rosenberger
+2  A: 

Right now there are really 3 forms of serialization in the .Net Framework.

  1. XmlSerialization - By default works on public fields and properties. Can still be controlled via XmlElementAttribute, XmlAttributeAttribute, etc ...
  2. BinarySerialization - Controlled by the SerializationAttribute. Deeply integrated into the CLR
  3. WCF Seralization - DataContractAttribute, etc ...

There unfortunately is standard overall pattern for serialization. All 3 frameworks have different requirements and quirks.

JaredPar
You might want to add JavaScriptSerializer to that list - different requirements and quirks, but part of the core framework now.
Marc Gravell
@Marc, hadn't heard about that one before. Will have to look into it.
JaredPar
JP - typo? s/Serialization/Serializable. The key point here is that [Serializable] is an attribute that is meaningful to the binary serializer, and the Xml Serializer doesn't use it. Conversely, [XmlElement] is used by the latter, and the former doesn't use i.
Cheeso
IIRC, Serializer was created to support MarshalByRefObject / .NET Remoting, XmlSerializer was created to support ASMX web services, and DataContractSerializer was created to support WCF, hence the inconsistencies. :-)
Christian Hayter
+4  A: 

Security isn't the only issue; simply, serialization only makes sense for certain classes. For example, it makes little snse to serialize a "connection". A connection string, sure, but the connection itself? nah. Likewise, anything that requires an unmanaged pointer/handle is not going to serialize very well. Nor are delegates.

Additionally, XmlSerializer and DataContractSerializer (by default) are tree serializers, not graph serializers - so any recursive links (like Parent) will cause it to break.

Marking the class with the serializer's preferred token is simply a way of saying "and it should make sense".

IIRC, both [XmlSerializer and [DataContractSerializer] used to be very rigid about demanding things like [Serializable], [DataContract] or [IXmlSerializable], but they have become a bit more liberal lately.

Marc Gravell
True, and this is a good argument as to why XmlSerializer SHOULD require attributes too... there's nothing stopping you from serializing something that doesn't make sense. But I think security was the main reason they DIDN'T do this.
Eric Rosenberger
And AFAIK, XmlSerializer never required any attributing, at least back to .NET 1.1, although you could always control it with the various Xml* attributes and IXmlSerializable.
Eric Rosenberger
common misconception: Xml Serializer never required [Serializable] and was never associated with [Serializable]. The [Serializable] attribute never had any effect on the actions or behavior of the Xml Serializer. They have always been unrelated, except in people's minds!
Cheeso
@Cheeso - probably because my first use of XmlSerializer was via asmx services, does that require it>
Marc Gravell
AFAIR, SOAP serialization does require [Serializable]. But SOAP serialization is very different from XML serialization.
Anton Tykhyy
@Anton: No such thing as SOAP Serialization. That's runtime serialization using the SOAP formatter.
John Saunders