Reputation: 616
How should I show text from a enum column instead of its value in a jQuery DataTable, without losing its value as I'll be using it later for editing purposes?
Given a Class:
public class Person
{
[Key]
public int PersonUID { get; set; }
public string FirstName { get; set; }
public EstadoPersona Status { get; set; }
}
And a Enum:
public enum EstadoPersona
{
Active, Inactive
}
I'm populating a jQuery DataTable using the following action from Controller:
public ActionResult List()
{
var data = db.People.Select(
a => new
{
a.FirstName,
a.Status,
a.PersonUID
}).OrderByDescending(a => a.PersonUID).ToList();
return Json(data, JsonRequestBehavior.AllowGet);
}
And this is my DataTable set up:
$("#tblPersons").DataTable({
processing: true,
dom: 'Brtip',
ajax: {
type: "POST",
url: "/People/List",
dataType: "json",
contentType: "application/json; charset=utf-8",
data: function (data) {
return data = JSON.stringify(data);
},
dataSrc: "",
error: function (jqXHR, textStatus, errorThrown) {
debugger; alert("ajax error: " + textStatus);
}
},
columns: [
{data: "FirstName" },
{ data: "Status"},
{ data: "PersonUID" }
],
rowId: 'PersonUID',
},
order: [],
});
Upvotes: 3
Views: 4148
Reputation: 2507
Use Json.Net http://www.newtonsoft.com/json and decorate following attribute for the Enum type column
public class Person
{
[Key]
public int PersonUID { get; set; }
public string FirstName { get; set; }
[JsonConverter(typeof(StringEnumConverter))]
public EstadoPersona Status { get; set; }
}
to post the values as {"Status":"Active"}
or {"Status":"InActive"}
instead of {"Status":0}
or {"Status":1}
Upvotes: 4
Reputation: 2594
Note: I wrote this whole answer saying you couldn't then found out a way to do it in the question I linked to show that you couldn't (d'oh), using the JSON.NET extension. See the Edit if you are willing to use that extension (it's pretty great).
Original Answer
See this stack overflow question (quoted the important answer below)
JavaScriptSerializer
[what is used when you convert the data to JSON] serializesenums
to their numeric values and not theirstring
representation. You would need to use custom serialization to serialize the enum as its name instead of numeric value.
Unfortunately, when you convert the enum
to JSON, it has been converted to an int
and the enum
status has been lost.
This means that you can't simply send the string (and that wouldn't be good enough for you anyway, since you want to have both the string value and the numeric value).
What I'd recommend doing is changing the object that is sent to DataTables to be a KeyValuePair<string,int>
. Now, this isn't a perfect solution, since you'll have to convert from the enum
to the KeyValuePair
both before you send and after you receive the data, but it's probably the simplest way to keep the string name and numeric value attached to each other when they're used in the JavaScript.
Basically, you'll have to modify your creation of the objects sent to DataTables so that instead of just adding a.status
you can instead in that object creation, create the key-value pair.
While this isn't really what you wanted, it is an unfortunate fact that you can't serialize an enum
into JSON and keep the name, only the value. You'll have to either convert the enum
into another type that can hold two values (KeyValuePair
, an array, a Dictionary
, whatever) during the serialization process or just stop using an enum.
Edit: Upon looking further into the linked question, it looks like if you use the JSON.NET extension, you actually can serialize enums. If you're willing to use that extension, that could be a very nice solution to your problem. I've used it before, and it's pretty useful and not difficult to use.
[JsonConverter(typeof(StringEnumConverter))]
Is the syntax you'd use if you use JSON.NET. You can get some more detail in the second answer on the question I linked.
Edit 2: After seeing Vijai's answer (which shows a nice example of how you would actually add the above attribute to your class), it appears that this will only send the string name of the enum
, not both the name and the value. You may still have to send an object other than an enum
, as in my original answer, if you want both the string and int values.
Upvotes: 3