Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

.Net webApi ISO datetime and IE8

.Net WebAPI uses ISO DateTime format by default when it serializes a DateTime. When IE8 tries to use this ISO DateTime format in a new Date() constructor, it breaks returning NaN.  

var d = new Date('2012-09-06T15:28:56.215Z');
alert(d);

 

Firefox handles this fine.  Haven't tried Chrome.  IE8 breaks, returning NaN.  

I'm assuming ISO dates are a good format to use in my WebAPI. I also want my Javascript client to handle converting to local time and reformatting the DateTime so it's easily readable -- that's why I'm using a Date type and not just keeping the ISO date as a string.  

Given all this, what  is the best way for me to handle the ISO DateTime format so IE8 won't choke?    

like image 727
MLH Avatar asked Sep 06 '12 17:09

MLH


1 Answers

I think the Date() constructor is just too unreliable with strings as input.

@Garrett describes the issue here --

A reliable way to set a Date is to construct one and use the setFullYear and setTime methods.

he gives a link, a function, and more details here: https://stackoverflow.com/a/2182529/644492

I modified the function to take a full ISO DateTime UTC string input and return a UTC Date object that I can later manipulate with Date getters.

I dropped milliseconds because IE8 Date constructor doesn't add milliseconds.

My modifications are probably not perfect -- regex is a little loose at the end, and that format checking block probably needs to be changed for my new input format...

/**Parses string formatted as YYYY-MM-DDThh:mm:ss.sZ 
 * or YYYY-MM-DDThh:mm:ssZ (for IE8), to a Date object.
 * If the supplied string does not match the format, an 
 * invalid Date (value NaN) is returned.
 * @param {string} dateStringInRange format YYYY-MM-DDThh:mm:ss.sZ, 
 * or YYYY-MM-DDThh:mm:ssZ - Zulu (UTC) Time Only,
 * with year in range of 0000-9999, inclusive. 
 * @return {Date} Date object representing the string.
 */

function parseISO8601(dateStringInRange) {
    var isoExp = /^\s*(\d{4})-(\d\d)-(\d\d)T(\d\d):(\d\d):(\d\d).*Z\s*$/,
        date = new Date(NaN), month,
        parts = isoExp.exec(dateStringInRange);
    if (parts) {
        month = +parts[2];
        date.setUTCFullYear(parts[1], month - 1, parts[3]);
        date.setUTCHours(parts[4]);
        date.setUTCMinutes(parts[5]);
        date.setUTCSeconds(parts[6]);
        if(month != date.getUTCMonth() + 1) {
            date.setTime(NaN);
        }
    }
    return date;
}
like image 179
MLH Avatar answered Oct 06 '22 00:10

MLH