Freestyle076
Freestyle076

Reputation: 1556

ASP.NET Web API Serialized JSON Error: "Self Referencing loop"

Been a long struggle with this one. I'm working with an ASP.NET web API to provide clean and easy HTTP/JSON interaction with a database. I have an entity name Reservation with that looks as following:

    // Reservation
public class Reservation
{
    public int ID { get; set; } // ID (Primary key)
    public int EquipmentID { get; set; } // EquipmentID
    public string Username { get; set; } // Username
    public DateTime BeginDateTime { get; set; } // BeginDateTime
    public int? Duration { get; set; } // Duration
    public int? ReservationStateID { get; set; } // ReservationStateID
    public DateTime? CheckInDateTime { get; set; } // CheckInDateTime
    public string Note { get; set; } // Note

    // Foreign keys
    public virtual Equipment Equipment { get; set; } // FK_Reservation_EquipmentID
    public virtual ReservationState ReservationState { get; set; } //FK_Reservation_ReservationState
}

So far so good. I am running a simple python script to create a new reservation, passing along with the http request a Reservation JSON object. In a previous life I ran the reservation adding code without data validation and returned the Reservation object in the HttpActionResult. What I saw in return was a nice json object:

{u'Username': u'name', u'ReservationStateID': 1, u'Equipment': None, u'EquipmentID': 2, u'BeginDateTime': u'2014-05-31T14:00:00Z', u'Note': u'', u'CheckInDateTime': None, u'Duration': 10800, u'ReservationState': None, u'ID': 51}

I am a little concerned with the foreign keys Equipment and ReservationState being included in the returned object, which may lend to the larger problem, but that in due time. Now I try to run data validation by gathering the Equipment item referenced by my Reservation.

Equipment equipmentItem = await db.Equipment.FindAsync(newRes.EquipmentID);

Now when I try to perform the same action, using the same data on the same python script the result received is a big scary error:

"The 'ObjectContent`1' type failed to serialize the response body for content type 'application/json; charset=utf-8'.", u'StackTrace': None, u'Message': u'An error has occurred.', u'InnerException': {u'ExceptionMessage': u"Self referencing loop detected for property 'Equipment' with type...

I am 99% positive that the foreign keys in place in my database do not create circular references, but alas here I am. Again I want to point out the inclusion of the foreign keys in the "successful" json results. I'm betting if I can be rid of those I can be rid of the self referencing issue. Thanks for the help!

Upvotes: 2

Views: 8420

Answers (2)

Freestyle076
Freestyle076

Reputation: 1556

The error was caused by the EF creating proxies for the foreign key objects, the default serializer (DataContractSerializer) errors when serializing with proxies. The solution is to add the following line to the Global.asax.cs file:

GlobalConfiguration.Configuration.Formatters.JsonFormatter.SerializerSettings.ReferenceLoopHandling = Newtonsoft.Json.ReferenceLoopHandling.Ignore; 

While @SKall's answer did solve the problem, it didn't solve it throughout the project, just to properties that I gave the IgnoreDataMember attribute.

Upvotes: 6

SKall
SKall

Reputation: 5234

Mark the references with IgnoreDataMember attribute and let us know if that helped.

[IgnoreDataMember]
public virtual Equipment Equipment { get; set; }

[IgnoreDataMember]
public virtual ReservationState ReservationState { get; set; }

Upvotes: 4

Related Questions