Asp.Net MVC Jsonresult Date Format

ASP.NET MVC JsonResult Date Format

Just to expand on casperOne's answer.

The JSON spec does not account for Date values. MS had to make a call, and the path they chose was to exploit a little trick in the javascript representation of strings: the string literal "/" is the same as "\/", and a string literal will never get serialized to "\/" (even "\/" must be mapped to "\\/").

See http://msdn.microsoft.com/en-us/library/bb299886.aspx#intro_to_json_topic2 for a better explanation (scroll down to "From JavaScript Literals to JSON")

One of the sore points of JSON is the
lack of a date/time literal. Many
people are surprised and disappointed
to learn this when they first
encounter JSON. The simple explanation
(consoling or not) for the absence of
a date/time literal is that JavaScript
never had one either: The support for
date and time values in JavaScript is
entirely provided through the Date
object. Most applications using JSON
as a data format, therefore, generally
tend to use either a string or a
number to express date and time
values. If a string is used, you can
generally expect it to be in the ISO
8601 format. If a number is used,
instead, then the value is usually
taken to mean the number of
milliseconds in Universal Coordinated
Time (UTC) since epoch, where epoch is
defined as midnight January 1, 1970
(UTC). Again, this is a mere
convention and not part of the JSON
standard. If you are exchanging data
with another application, you will
need to check its documentation to see
how it encodes date and time values
within a JSON literal. For example,
Microsoft's ASP.NET AJAX uses neither
of the described conventions. Rather,
it encodes .NET DateTime values as a
JSON string, where the content of the
string is /Date(ticks)/ and where
ticks represents milliseconds since
epoch (UTC). So November 29, 1989,
4:55:30 AM, in UTC is encoded as
"\/Date(628318530718)\/".

A solution would be to just parse it out:

value = new Date(parseInt(value.replace("/Date(", "").replace(")/",""), 10));

However I've heard that there is a setting somewhere to get the serializer to output DateTime objects with the new Date(xxx) syntax. I'll try to dig that out.


The second parameter of JSON.parse() accepts a reviver function where prescribes how the value originally produced by, before being returned.

Here is an example for date:

var parsed = JSON.parse(data, function(key, value) {
if (typeof value === 'string') {
var d = /\/Date\((\d*)\)\//.exec(value);
return (d) ? new Date(+d[1]) : value;
}
return value;
});

See the docs of JSON.parse()

ASP.NET 4.6 MVC How to return a Json result including datetime data with correct timezone?

The problem is that ASP.NET uses a custom Microsoft JSON date format, that encodes DateTime values as /Date(ticks)/, where ticks represents milliseconds since epoch (UTC).

So November 29, 1989, 4:55:30 AM, in UTC is encoded as /Date(628318530718)/ (see here for more).

Example:

  • Microsoft JSON date format: /Date(1563464520158)/
  • ISO 8601 format: 2019-07-18T15:42:02.4592008Z

If a DateTime has an Unspecified kind, it will be assumed as Local and the value will be conveted to UTC in order to get the ticks since epoch.

This json format is still used in MVC, but not in Web API: this means that when you are in a Controller and serialize the result with Json(...) you'll get the non-ISO format, but if you're in an ApiController the default serializer is Json.NET, which supports the ISO 8601 format and won't convert the DateTime value.

So, to fix this behavior either you switch to Web APIs, or if you want to keep using the MVC controller, you can see the answers to these questions:

  • Setting the default JSON serializer in ASP.NET MVC
  • Using JSON.NET as the default JSON serializer in ASP.NET MVC 3
  • How to use Json.NET for JSON modelbinding in an MVC5 project

...or you could force the DateTime Kind to be Utc right before the json serialization, but I wouldn't recommend that.


class TestRepo
{
public IEnumerable<DateTime> GetDates()
{
var now = DateTime.Now;

// Use DateTime instances with different Kind
// showing that it doesn't impact the serialization format.
var utc = DateTime.SpecifyKind(new DateTime(now.Ticks), DateTimeKind.Utc);
var local = DateTime.SpecifyKind(new DateTime(now.Ticks), DateTimeKind.Local);
var unspecified = DateTime.SpecifyKind(new DateTime(now.Ticks), DateTimeKind.Unspecified);

return new DateTime[] { utc, local, unspecified };
}
}
// MVC controller
public class MVCValuesController : Controller
{
public ActionResult Index()
{
IEnumerable<DateTime> dates = new TestRepo().GetDates();
return Json(dates, JsonRequestBehavior.AllowGet);
}
}

// json result:
[
"/Date(1563465361835)/", // <-- Utc
"/Date(1563458161835)/", // <-- Local
"/Date(1563458161835)/" // <-- Unspecified
]
// Web API controller
public class ValuesController : ApiController
{
public IEnumerable<DateTime> Get()
{
IEnumerable<DateTime> dates = new TestRepo().GetDates();
return dates;
}
}

// json result:
[
"2019-07-18T15:56:03.6401158Z", // <-- Utc
"2019-07-18T15:56:03.6401158+02:00", // <-- Local
"2019-07-18T15:56:03.6401158" // <-- Unspecified
]

MVC action returning json object with a date field

The comments link better answers and explanations, but personally I just use a quick dirty javascript function like so

function date(s) { 
return new Date(parseFloat(/Date\(([^)]+)\)/.exec(s)[1]));
}

var jsDate = date(jsonDateFromDotNet);

Return Json from MVC controller but Date format not proper in javascript

its not javascript issue i think you need to formate you date in you code as you required i.e in C# code only.

somthing like below might help you ..

List<IEmployeeEntity> list = new Employee(connectionString).GetEmployeeRecord();
list.All(x => { x.mydate = x.mydate.ToString("dd/MM/yyyy"); return true; })

or

try this solution when your property is of type datetime because in first one it will give you an error if the property type is datetime

var q = from o in MyList
select new { mydate = x.mydate.ToString("dd/MM/yyyy"),
prop1 = o.prop1,
prop2 = o.prop2
};

Pass a JSON format DateTime to ASP.NET MVC

The problem, as you suspected, is a model binding issue.

To work around it, create a custom type, and let's call it JsonDateTime. Because DateTime is a struct, you cannot inherit from it, so create the following class:

public class JsonDateTime
{
public JsonDateTime(DateTime dateTime)
{
_dateTime = dateTime;
}

private DateTime _dateTime;

public DateTime Value
{
get { return _dateTime; }
set { _dateTime = value; }
}
}

Change CreateDate to this type. Next, we need a custom model binder, like so:

public class JsonDateTimeModelBinder : IModelBinder  
{
public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
var value = bindingContext.ValueProvider.GetValue(bindingContext.ModelName).ToString();
return new DateTime(Int64.Parse(
value.Substring(6).Replace(")/",String.Empty))); // "borrowed" from skolima's answer
}
}

Then, in Global.asax.cs, in Application_Start, register your custom ModelBinder:

ModelBinders.Binders.Add(typeof(JsonDateTime), new JsonDateTimeModelBinder());

How to convert json date from angular in asp.net mvc

Use this to convert JSON date

new Date(parseInt("/Date(813694500000)/".substr(6)))

Result : Sat Oct 14 1995 23:45:00 GMT+0530 (India Standard Time)

Prevent JsonResult from auto-formatting Dates

I finally ended up getting the proper results, with many modifications to my application. I did a lot of stuff to make this happen... First, I implemented timezone.JS to get a listing of timezones that will be used within the application, and used jstz to get current timezone of browser loading the page. Next, I have to make (for mvc) an file get method that accesses the timezones to load into timezoneJS.

Next, on save of the timezone, I specified pst as the type, and then convert back to utc on roundtrip to update the interface.

On formatting of my Json date, I run the timezoneJS method and get the timezone name from jstz, and set the new date value like such:

var timezone = jstz.determine();
timezoneJS.timezone.zoneFileBasePath = '/Item/GetTz'; // get file method
var dt = new timezoneJS.Date(parseInt(jsonDate.substr(6), timezone.name())); // strips out date from json date
dt.setTimezone('America/Los_Angeles');

This allows on the cloud projects to be ran on any server, and displayed in any browser regardless of timezone, and allow the user to view and configure timezone sensitive data natively, and allow for users to see the start/end date of configurable database values.



Related Topics



Leave a reply



Submit