Serialization Error on BusinessListBase

Serialization Error on BusinessListBase

Old forum URL: forums.lhotka.net/forums/t/7289.aspx


pondosinat posted on Thursday, July 16, 2009

I'm trying to add a property to a BLB-derived class that is of type BO. When doing so, I get a serialization error on load. Here is the code:

Private _Note As Note.Note = New Note.Note

Public ReadOnly Property Note() As Note.Note

Get

Return _Note

End Get

End Property

Protected Overrides Sub OnGetState(ByVal info As Csla.Serialization.Mobile.SerializationInfo)

MyBase.OnGetState(info)

info.AddValue("_Note", _Note)

End Sub

Protected Overrides Sub OnSetState(ByVal info As Csla.Serialization.Mobile.SerializationInfo)

MyBase.OnSetState(info)

_Note = CType(info.Values("_Note").Value, Note.Note)

End Sub

 

And the error when loading:

Type 'Business.BusinessClasses.Note.Note' with data contract name 'Note:http://schemas.datacontract.org/2004/07/Business.BusinessClasses.Note' is not expected. Add any types not known statically to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding them to the list of known types passed to DataContractSerializer.

Is there something wrong with this approach? I haven't tried adding a child property like this to a BLB before. Am I missing something? Thanks

 

RockfordLhotka replied on Friday, July 17, 2009

The MobileFormatter (which uses the DataContractSerializer behind the scenes) only works with types that implement IMobileObject. If your Note type doesn't implement that interface (which is best done by inheriting from one of the CSLA base classes, or at least MobileObject) then it can't be serialized.

An alternative, if you absolutely can't make Note implement the right interface, is for you to manually convert the state of Note into a byte stream (string, byte[], XML string, etc) and put that into the SerializationInfo object.

pondosinat replied on Friday, July 17, 2009

Based on what you said, it sounds like this should be working. The Note object is a standard CSLA BO. I even tried creating a simple class that implements IMobileObject and uses private backing fields (a la this thread http://forums.lhotka.net/forums/thread/31394.aspx) but no luck.

I'm wondering if my problem is that I'm putting my property on a BLB object? Is this supported? 

I've changed my approach in the meantime from using a Note object to using a bunch of primitive type properties. Ideally I would like to get it working with the Note object...

RockfordLhotka replied on Friday, July 17, 2009

Ahh, it occurs to me that you need to add the Note object as a child, not as a field.

 

You are overriding OnSetState(), etc. There’s a separate pair of methods to get/set child object references in the serialization stream, because more work is done for a child object reference than for a field.

 

I don’t remember if BLB allows you to override the get/set child methods though, because it obviously uses them to get/set the contents of the collection itself. But you should check and see if they are available for override (just make sure to call the base implementations or you’ll lose the contents of the collection!).

 

Rocky

 

From: pondosinat [mailto:cslanet@lhotka.net]
Sent: Friday, July 17, 2009 10:20 AM
To: rocky@lhotka.net
Subject: Re: [CSLA .NET] Serialization Error on BusinessListBase

 

Based on what you said, it sounds like this should be working. The Note object is a standard CSLA BO. I even tried creating a simple class that implements IMobileObject and uses private backing fields (a la this thread http://forums.lhotka.net/forums/thread/31394.aspx) but no luck.

I'm wondering if my problem is that I'm putting my property on a BLB object? Is this supported? 

I've changed my approach in the meantime from using a Note object to using a bunch of primitive type properties. Ideally I would like to get it working with the Note object...



pondosinat replied on Friday, July 17, 2009

This is what I've done:

Private _Note As New Note.EventNote

Public ReadOnly Property Note() As Note.EventNote

Get

If _Note Is Nothing Then

_Note = New Note.EventNote

End If

Return _Note

End Get

End Property

Protected Overrides Sub OnGetChildren(ByVal info As Csla.Serialization.Mobile.SerializationInfo, ByVal formatter As Csla.Serialization.Mobile.MobileFormatter)

MyBase.OnGetChildren(info, formatter)

info.AddValue("_Note", _Note)

End Sub

Protected Overrides Sub OnSetChildren(ByVal info As Csla.Serialization.Mobile.SerializationInfo, ByVal formatter As Csla.Serialization.Mobile.MobileFormatter)

MyBase.OnSetChildren(info, formatter)

_Note = CType(info.Values("_Note").Value, Note.EventNote)

End Sub

 

But I'm running into the same error. I've tried making note inherit a BusinessBase object and mark it as child, but that made no difference. Does this code look ok?

Thanks

pondosinat replied on Friday, July 17, 2009

I've found the answer to my own question: calling the "AddChild" method rather than "AddValue". For future reference, below is the code that is now working (commented out code is the faild attempt):

Private _Note As New Note.EventNote

Public ReadOnly Property Note() As Note.EventNote

Get

If _Note Is Nothing Then

_Note = New Note.EventNote

End If

Return _Note

End Get

End Property

Protected Overrides Sub OnGetChildren(ByVal info As Csla.Serialization.Mobile.SerializationInfo, ByVal formatter As Csla.Serialization.Mobile.MobileFormatter)

MyBase.OnGetChildren(info, formatter)

Dim fieldManagerInfo = formatter.SerializeObject(_Note)

info.AddChild("_Note", fieldManagerInfo.ReferenceId)

'info.AddValue("_Note", _Note)

End Sub

Protected Overrides Sub OnSetChildren(ByVal info As Csla.Serialization.Mobile.SerializationInfo, ByVal formatter As Csla.Serialization.Mobile.MobileFormatter)

MyBase.OnSetChildren(info, formatter)

Dim childData = info.Children("_Note")

_Note = CType(formatter.GetObject(childData.ReferenceId), Note.EventNote)

'_Note = CType(info.Values("_Note").Value, Note.EventNote)

End Sub

Copyright (c) Marimer LLC