Reputation: 39374
I have the following Web API action.
public IHttpActionResult Get() {
var units = Enum.GetValues(typeof(UnitType)).Cast<UnitType>().Select(x => new { Id = (Int32)x, Description = x.Attribute<DescriptionAttribute>().Description });
return Ok(units);
}
Basically, I am returning the values and descriptions of an enum.
I checked units list and I get the right values.
However, when I call the API I get the following error:
<Error><Message>An error has occurred.</Message>
<ExceptionMessage>The 'ObjectContent`1' type failed to serialize the response body for content type 'application/xml; charset=utf-8'.</ExceptionMessage>
<ExceptionType>System.InvalidOperationException</ExceptionType>
<StackTrace/><InnerException><Message>An error has occurred.</Message>
<ExceptionMessage>Type '<>f__AnonymousType0`2[System.Int32,System.String]' cannot be serialized. Consider marking it with the DataContractAttribute attribute, and marking all of its members you want serialized with the DataMemberAttribute attribute. If the type is a collection, consider marking it with the CollectionDataContractAttribute. See the Microsoft .NET Framework documentation for other supported types.</ExceptionMessage>
Why?
UPDATE
I now have:
public IHttpActionResult Get() {
IList<EnumModel> units = Enum.GetValues(typeof(UnitType)).Cast<UnitType>().Select(x => new EnumModel((Int32)x, x.Attribute<DescriptionAttribute>().Description)).ToList();
return Ok(units);
} // Get
public class EnumModel {
public Int32 Id { get; set; }
public String Description { get; set; }
public EnumModel(Int32 id, String description) {
Id = id;
Description = description;
} // EnumModel
} // EnumModel
I get the error:
<Error>
<Message>An error has occurred.</Message>
<ExceptionMessage>The 'ObjectContent`1' type failed to serialize the response body for content type 'application/xml; charset=utf-8'.</ExceptionMessage>
<ExceptionType>System.InvalidOperationException</ExceptionType>
<StackTrace/><InnerException>
<Message>An error has occurred.</Message>
<ExceptionMessage>Type 'Helpers.EnumModel' cannot be serialized. Consider marking it with the DataContractAttribute attribute, and marking all of its members you want serialized with the DataMemberAttribute attribute. If the type is a collection, consider marking it with the CollectionDataContractAttribute. See the Microsoft .NET Framework documentation for other supported types.</ExceptionMessage>
<ExceptionType>System.Runtime.Serialization.InvalidDataContractException</ExceptionType>
Any idea why?
Upvotes: 0
Views: 2054
Reputation: 5899
How are you calling your API? It looks like it is trying to use XML formatter for content negotiation. However, XML serializer does not support anonymous types. Check out this link for the details.
To fix this behaviour, you should either send Accept: application/json
header (if you are using Fiddler or tool like this), or explicitly tell your Web API that you need JSON formatter only:
config.Formatters.Clear();
var jsonFormatter = new JsonMediaTypeFormatter
{
// Use camel case formatting.
SerializerSettings =
{
ContractResolver = new CamelCasePropertyNamesContractResolver(),
}
};
config.Formatters.Add(jsonFormatter);
Upvotes: 2
Reputation: 8043
I might be wrong, but the InnerException
seems to be suggesting that anonymous types can't be serialized.
Try declaring a class such as
public class EnumInfo {
public int Id { get; set; }
public string Description { get; set; }
public EnumInfo(int id, string description) {
Id = id;
Description = description;
}
}
and turning your Select
call into
[...].Select(x => new EnumInfo((Int32)x, x.Attribute<DescriptionAttribute>().Description);
Upvotes: 0