In my company we are refactoring some applications, and one of the aspects to be refactored are the classes of data representing "user objects", that is, objects that the user creates and must be persisted locally.
We are striving for Continuous Deployment workflow, such as the application should grow in functionality, while the installed base should grow in numbers.
But since the design of each class being serialized is defined by how they support use-cases, and given that design will change as features are better understood and modeled, how should we handle the local, client-side persisted objects - which are valuable assets from each user's perspective - when eventually the design "breaks"?
The following example is just for illustration, since the problem can take many possible forms, be it the changing of property type, or the adding/removal of properties. The class below has a Platform
property that tells which platform a given device is compatible with:
public class Device
{
public PlatformEnum CompatiblePlatform {get; set;}
}
So, we deploy the system to some customers, which start to use it and persist a lot of Device
instances to their file systems.
But eventually the need/possibility arises for each Device to be compatible with more than one Platform
, and thus the class now contains a collection instead of a single value for CompatiblePlatform
:
public class Device
{
public IEnumerable<PlatformEnum> CompatiblePlatforms {get; set;}
}
So now we have a problem: how to handle the considerable amount of serialized files, so that they are automagically loaded by the new version of the design?
And, more broadly, how should I try to concile "Design up front", in the case of design of serializable classes, with the "Emergent Design" of user-story-based ATDD? Should I use some sort of versioning, or should I take some well-known set of precautions?
A common approach is to write a version number with each serialized object, and evolve the deserialization code to handle older versions. e.g. in your example, the version 2 Device
code would read a version 1 serialized Device
and load the single PlatformEnum
as a single entry in its enumeration of PlatformEnum
.