Decide on Strong Typing Approach
keithwill opened this issue · 0 comments
As part of the refactoring to reduce requirements on user defined types, there is no longer a requirement for all user defined types to share an inheritance hierarchy. When making this change, the entity store and the PrefixLookup it depends on were modified to be typed as 'object'.
While this allowed the refactoring to complete and also allowed the storage of basic types (strings, booleans, and numbers), it does have the downside that value types need to be boxed when stored and retrieved, and most stores and retrievals require casting.
It should be investigated if the current 'object' typed PrefixLookup should be replaced with strongly typed instances of PrefixLookup.
An 'AddType' method was recently added to VestPocketOptions and is necessary for VestPocket to identify types for deserialization. Since this is already used to identify runtime types by $type name or object instance, the same logic could be used to locate the appropriate PrefixLookup instance (such as from a FrozenDictionary keyed on $type name or System.Type).
The performance impact of this would need to be accessed and special consideration would need to be given to user defined types that are part of a inheritance hierarchy. Would hierarchies need to be defined at the time they are added to VestPocket with an 'AddType' call?
Would segregating the stored keys by type be a positive developer experience, or would developers be expecting to find search results across different types? I suspect that most C# developers would find keys segregated by type to be more intuitive, as then they wouldn't need to manage loosely typed string prefixes to segregate by type in cases where that is desired.
In cases where a developer wants mixed value types from a single prefix search, they should probably be creating a strong typed type to hold those values and store that with a name instead. For example, instead of guiding the library user to store:
/someEntity/intValue1 = 1
/someEntity/intValue2 = 2
/someEntity/name = "Some Value"
Instead they should be guided to store a strongly typed entity at the key /someEntity that has properties for intValue1, intValue2 and name. The problem with a prefix search on /someEntity to get the three stored values underneath is that (with the current VestPocket) code, the returned key value pairs contain values that are typed only as 'object'. Expecting the library consumer to manually switch on key names so that they can conditionally cast each key to its expected type...seems like a poor developer experience.