XmlSerializer: how to deserialize an enum value that no longer exists

I use XMLSerializer to save this class to a file. The class has a string and an enumeration, as shown below:

public class IOPoint { string Name {get; set;} TypeEnum {get; set;} } public enum TypeEnum { Temperature, Pressure, Humidity, } 

When serialized, it looks like this.

 <IOPoint> <Name>Relative Humidity</Name> <TypeEnum>Humidity</TypeEnum> </IOPoint> 

I serialize and deserialize this object without problems for multiple versions. I no longer want to maintain Humidity, so I removed it from the listing. However, this throws an exception when deserializing from XML, because the value in the TypeEnum field, Humidity, is not a valid value for TypeEnum. It makes sense, but how to handle it?

What I would like to do is simply ignore this error. And leave the value equal to zero. I tried to implement the OnUnknownElement XmlDeserilizationEvent class. Unfortunately, this does not resolve this error.

Any ideas on how to catch and ignore this error (I can clear it after deserialization is complete).

Mitch

+8
c # xml serialization versioning deserialization
source share
4 answers

You can mark a member of the Deprecated

 public enum TypeEnum { Temperature, Pressure, [Obsolete] Humidity } 
+5
source share

It is generally considered bad practice to delete an enumeration member after your library is already in use. Why don't you leave the participant in place, but mark him with the [Obsolete] attribute to prevent future use? Specifying ObsoleteAttribute(string,bool) second constructor parameter as true will result in a compile-time error if access to the marked member is available.

 public enum TypeEnum { Temperature, Pressure, [Obsolete("It always sunny in Philadelphia", true)] Humidity, } 

To get around the error when checking deserialized values, you can compare it with the base value: typeEnum == (TypeEnum)2 .

+4
source share

You can use attributes to change node names and hide elements from xml serialization by parsing only one element manually:

 public class IOPoint { public string Name {get; set;} [XmlIgnore] public TypeEnum TypeEnum {get; set;} [XmlElement("TypeEnum")] public string LegacyTypeEnum { get { return this.TypeEnum.ToString(); } set { try { this.TypeEnum = (TypeEnum)Enum.Parse(typeof(TypeEnum),value); } catch(ArgumentException) { // Handle "Humidity" } catch(OverflowException) { } } } } 

There is some confusion in the comments; here is an example as a Visual Studio 2010 project. This approach is a simple way to manually parse only one property of an object (still using the XmlSerializer to process XML analysis).

+2
source share

You can implement IXmlSerializable where you can use something like TryParse for an enumeration.

But I agree with other posters using the Obsolete attribute.

+1
source share

All Articles