How to configure complex type serialization / deserialization in ServiceStack.OrmLite

I use ServiceStack.OrmLite to store data in a SQLite database and have been happy with it so far.

However, many of my objects have complex type properties that I do not want to serialize using JSV .

I need to specify the specific serialization / deserialization that should be used to store the property in the database (as a string). In the db4o world, this is equivalent to using the translation function provided by the IObjectConstructor .

A good example of complex types that cannot be serialized and deserialized correctly are the NodaTime types, although they can be easily matched with strings (I already have the serialization / deserialization functions that I used with db4o ).

What is the easiest way to achieve this? A wrapper would not be very convenient, since I would have to write and maintain one for each type that contains a property of this complex type.

+7
c # nodatime servicestack ormlite-servicestack servicestack-text
source share
3 answers

For those who may be interested in the shell template that I use to implement custom serialization using OrmLite (also works with other ORMs), here is a simple working example with NodaTime types that otherwise would not be serialized correctly: / p>

 public class BusinessObject { public class Poco { public readonly BusinessObject BusinessObject; public Poco(BusinessObject businessObject) { this.BusinessObject = businessObject; } public Poco() { this.BusinessObject = new BusinessObject(); } public string Id { get { return this.BusinessObject.Id; } set { this.BusinessObject.Id = value; } } public decimal Amount { get { return this.BusinessObject.Amount; } set { this.BusinessObject.Amount = value; } } public DateTime Dt { get { return this.BusinessObject.Dt.ToDateTime(); } set { this.BusinessObject.Dt = LocalDateTime.FromDateTime(value).Date; } } public string TimeZone { get { return this.BusinessObject.TimeZone.Id; } set { this.BusinessObject.TimeZone = DateTimeZoneProviders.Tzdb.GetZoneOrNull(value); } } public string Description { get { return this.BusinessObject.Description; } set { this.BusinessObject.Description = value; } } } public string Id { get; private set; } public decimal Amount { get; private set; } public LocalDate Dt { get; private set; } public DateTimeZone TimeZone { get; private set; } public string Description { get; private set; } public BusinessObject() { } public BusinessObject(string id, decimal amount, LocalDate dt, DateTimeZone timeZone, string description) { this.Id = id; this.Amount = amount; this.Dt = dt; this.TimeZone = timeZone; this.Description = description; } } 

I hope that soon it will be possible to define hooks / callbacks for certain types that should be handled with custom code, as well as the fact that OrmLite will allow you to reconfigure properties with private setters from a constant (currently it will work only in one direction).

Update (2014/03/08) . As a temporary workaround, it is possible that OrmLite uses custom serialization / deserialization by first calling:

 JsConfig<BusinessObject>.TreatValueAsRefType = true; 

Even if BusinessObject is a reference type. Then you can enjoy the beauty / simplicity / omnipresence:

 JsConfig<BusinessObject>.RawSerializeFn = bo => bo.Serialize(); JsConfig<BusinessObject>.RawDeserializeFn = str => BusinessObject.Deserialize(str); 

We hope that support for user matching will be added soon (so, for example, NodaTime.LocalDate can be matched with DateTime instead of a string).

+6
source share

OrmLite now supports pluggable text serializers .

Plug-in serialization allows you to specify different serialization strategies for complex types for each available RDBMS provider, for example:

 //ServiceStack JSON and JSV Format SqliteDialect.Provider.StringSerializer = new JsvStringSerializer(); PostgreSqlDialect.Provider.StringSerializer = new JsonStringSerializer(); //.NET XML and JSON DataContract serializers SqlServerDialect.Provider.StringSerializer = new DataContractSerializer(); MySqlDialect.Provider.StringSerializer = new JsonDataContractSerializer(); //.NET XmlSerializer OracleDialect.Provider.StringSerializer = new XmlSerializableSerializer(); 

You can also provide your own serialization strategy by implementing IStringSerializer :

 public interface IStringSerializer { To DeserializeFromString<To>(string serializedText); object DeserializeFromString(string serializedText, Type type); string SerializeToString<TFrom>(TFrom from); } 
+2
source share

To serialize complex types, configure your own serializer (and deserializer) to JsConfig :

 JsConfig<Foo>.SerializeFn = foo => foo.ToString("XOXO", CultureInfo.InvariantCulture); JsConfig<Foo>.DeSerializeFn = foo => { var result = Foo.Parse(foo, CultureInfo.InvariantCulture); return result; }; 

You can also tell JsConfig about UTC dates:

 JsConfig.AssumeUtc = true; 
+2
source share

All Articles