2

When I enabled Fody to autogenerate Catel Properties and then run my application, I receive a runtime error saying one of my Properties (which references another entity) is invalid:

Property 'Hedge' is invalid (not serializable?)

This happens in the constructor of my EntityBase, when I try to enable the LeanAndMeanModel flag. The referenced entity is null, which is valid since the hedge property is not required.

Here is the relevant code:

[DataContract]
public class EntityBase : ModelBase, IEntityBase
{
    public EntityBase()
    {
        LeanAndMeanModel = true;
        Id = ContextTools.GenerateComb();
    }
    [Column(Order = 0)]
    [Required, Key, DataMember]
    public Guid Id { get; set; }

    // For Row Level Concurrency
    [Column(Order = 2)]
    [Timestamp, DataMember]
    public Byte[] RowVersion { get; set; }

    /// <summary>
    /// Called after loading objects using Entity Framework
    /// to improve performance and enable proper function
    /// of Catel ModelBase features.
    /// 
    /// https://catelproject.atlassian.net/wiki/display/CTL/Using+ModelBase+as+base+for+entities
    /// 
    /// https://catelproject.atlassian.net/wiki/display/CTL/Performance+considerations
    /// 
    /// </summary>
    public void PostLoadSetup()
    {
        IsDirty = false;
        LeanAndMeanModel = false;
    }
}

[DataContract]
public class TransactionalBase :EntityBase, ITransactionalBase
{
    // Convenience field to make querying
    // for specific rows easier on the Database Side
    [Column(Order = 1), DataMember]
    [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public int RowNumber { get; set; }
}


[DataContract]
public class Trade : TransactionalBase, ITrade
{
    // Foreign Key
    [DataMember]
    public Guid? HedgeId { get; set; }

    // Navigation Property
    [DataMember]
    public Hedge Hedge { get; set; }

    [DataMember, Required]
    public DateTime TradeDate { get; set; }

    [DataMember, Required]
    public DateTime SettleDate { get; set; }

    // More properties follow
    // ...
    // ...
    // ...
}

[DataContract]
public class Hedge : TransactionalBase, IHedge
{
    [DataMember, Required]
    public DateTime HedgeDate { get; set; }

    [DataMember, Required]
    public DateTime SettleDate { get; set; }

    [DataMember, Required]
    public PurchaseType BuySell { get; set; }

    // Navigation property
    public virtual List<Trade> HedgedTrades { get; set; }

    // More properties follow
    // ...
    // ...
    // ...
}
Bitfiddler
  • 3,942
  • 7
  • 36
  • 51
  • Turns out it's nothing to do with the leanandmeanmodel, if I comment out everything in the constructor, the same error comes up. I also added a "[DefualtValue(null)]" to the attributes of the Trade.Hedge property. Still no luck. – Bitfiddler Nov 19 '13 at 22:09
  • When I remove the Hedge property, everything works. – Bitfiddler Nov 19 '13 at 23:04
  • Loading a hedge works properly as well (once the navigation property is removed). It appears Catel does not play well with EF6 navigation properties. – Bitfiddler Nov 19 '13 at 23:11
  • So I have downloaded the code for Catel and it appears that Catel is marking the property as non-serializable. Is this normal for all reference types? – Bitfiddler Nov 19 '13 at 23:46
  • 1
    Okay, it's not Catel marking it as non-serializable. It's coming from .net reflection. Adding the [AllowNonSerializableMembers] attribute to my trade class fixes this error. I am still curious why the class is being reflected as non-serializable though. – Bitfiddler Nov 20 '13 at 00:10
  • Okay, more digging reveals it is Catel marking the property as non-serializable (via Catel.Data.PropertyData). Anyone out there know why Catel is marking an entity that derives from ModelBase (serializable) and has all its properties as primitive types (I commented out all reference properties other than the Guid Id) as being non-Serializable? – Bitfiddler Nov 20 '13 at 00:40
  • It's probably just the [Serializable] attribute missing. We can additional code to allow both types with the [Serializable] and ModelBase classes. – Geert van Horrik Nov 20 '13 at 08:57
  • 1
    That was it (adding serializable attribute). I thought ModelBase implemented Serializable because of (https://catelproject.atlassian.net/wiki/display/CTL/ModelBase) where it says "Fully Serializable". Does the attribute need to be on all subclasses of ModelBase for it to work? – Bitfiddler Nov 20 '13 at 17:09
  • I think so. If I remember correctly, the binary serializer will break if it's not. But again, we might reconsider that. Just open a ticket in the ticket system and it will be looked at. – Geert van Horrik Nov 20 '13 at 20:22
  • Where did you add [Serializable] attribute, because I have the same problem... – MegaMilivoje Nov 26 '13 at 21:16
  • 1
    @MegaMilivoje I added it to the entity that was causing the error, so in my case the Hedge entity: [DataContract, Serializable] public class Hedge : TransactionalBase, IHedge – Bitfiddler Dec 09 '13 at 16:51

0 Answers0