Pregunta ¿Cómo formateo una fecha de Microsoft JSON?


Estoy tomando mi primera racha de Ajax con jQuery. Estoy obteniendo mis datos en mi página, pero estoy teniendo problemas con los datos JSON que se devuelven para los tipos de datos de fecha. Básicamente, estoy recuperando una cadena que se ve así:

/Date(1224043200000)/

De alguien totalmente nuevo a JSON: ¿cómo puedo formatear esto en un formato de fecha corta? ¿Se debe manejar esto en algún lugar del código jQuery? He intentado con jQuery.UI.datepicker plugin usando $.datepicker.formatDate() sin ningún éxito

FYI: Aquí está la solución que se me ocurrió usando una combinación de las respuestas aquí:

function getMismatch(id) {
  $.getJSON("Main.aspx?Callback=GetMismatch",
    { MismatchId: id },

    function (result) {
      $("#AuthMerchId").text(result.AuthorizationMerchantId);
      $("#SttlMerchId").text(result.SettlementMerchantId);
      $("#CreateDate").text(formatJSONDate(Date(result.AppendDts)));
      $("#ExpireDate").text(formatJSONDate(Date(result.ExpiresDts)));
      $("#LastUpdate").text(formatJSONDate(Date(result.LastUpdateDts)));
      $("#LastUpdatedBy").text(result.LastUpdateNt);
      $("#ProcessIn").text(result.ProcessIn);
    }
  );

  return false;
}

function formatJSONDate(jsonDate) {
  var newDate = dateFormat(jsonDate, "mm/dd/yyyy");
  return newDate;
}

Esta solución obtuvo mi objeto del método de devolución de llamada y mostró las fechas en la página correctamente utilizando la biblioteca de formato de fecha.


1788


origen


Respuestas:


Eval no es necesario. Esto funcionará bien:

var date = new Date(parseInt(jsonDate.substr(6)));

La función substr saca la parte "/ Fecha (", y la función parseInt obtiene el entero e ignora el ") /" al final. El número resultante se pasa al constructor de Fecha.

EDITAR: he dejado intencionalmente la raíz (el segundo argumento para analizar); ver mi comentario a continuación. Además, estoy completamente de acuerdo con El comentario de Rory: Las fechas ISO-8601 son preferibles a este formato antiguo, por lo que este formato generalmente no debe usarse para nuevos desarrollos. Mira el excelente Json.NET biblioteca para una gran alternativa que serializa las fechas usando el formato ISO-8601.

Para fechas JSON con formato ISO-8601, simplemente pase la cadena al constructor de Fecha:

var date = new Date(jsonDate); //no ugly parsing needed; full timezone support

1565



Puede usar esto para obtener una fecha de JSON:

var date = eval(jsonDate.replace(/\/Date\((\d+)\)\//gi, "new Date($1)"));

Y luego puedes usar un formato de fecha de JavaScript script (1.2 KB cuando está minificado y gzip) para mostrarlo como lo desee.


115



Para aquellos que usan Newtonsoft Json.NET, lee sobre cómo hacerlo a través de Native JSON en IE8, Firefox 3.5 plus Json.NET.

También es útil la documentación sobre cómo cambiar el formato de las fechas escritas por Json.NET: Fechas de serialización con Json.NET

Para aquellos que son demasiado vagos, aquí están los pasos rápidos. Como JSON tiene una implementación suelta de DateTime, debe usar el IsoDateTimeConverter(). Tenga en cuenta que, desde Json.NET 4.5, el formato de fecha predeterminado es ISO, por lo que no es necesario el siguiente código.

string jsonText = JsonConvert.SerializeObject(p, new IsoDateTimeConverter());

El JSON vendrá como

"fieldName": "2009-04-12T20:44:55"

Finalmente, algunos JavaScript para convertir la fecha ISO a una fecha de JavaScript:

function isoDateReviver(value) {
  if (typeof value === 'string') {
    var a = /^(\d{4})-(\d{2})-(\d{2})T(\d{2}):(\d{2}):(\d{2}(?:\.\d*)?)(?:([\+-])(\d{2})\:(\d{2}))?Z?$/.exec(value);
      if (a) {
        var utcMilliseconds = Date.UTC(+a[1], +a[2] - 1, +a[3], +a[4], +a[5], +a[6]);
        return new Date(utcMilliseconds);
      }
  }
  return value;
}

Lo usé así

$("<span />").text(isoDateReviver(item.fieldName).toLocaleString()).appendTo("#" + divName);

84



El ejemplo original:

/Date(1224043200000)/  

no refleja el formato utilizado por WCF al enviar fechas a través de WCF REST usando la serialización JSON incorporada. (al menos en .NET 3.5, SP1)

Encontré la respuesta aquí útil, pero se requiere una ligera edición de la expresión regular, ya que parece que la compensación de la zona horaria GMT se agrega al número devuelto (desde 1970) en WCF JSON.

En un servicio de WCF tengo:

[OperationContract]
[WebInvoke(
    RequestFormat = WebMessageFormat.Json,
    ResponseFormat = WebMessageFormat.Json,
    BodyStyle = WebMessageBodyStyle.WrappedRequest
    )]
ApptVisitLinkInfo GetCurrentLinkInfo( int appointmentsId );

ApptVisitLinkInfo se define simplemente:

public class ApptVisitLinkInfo {
    string Field1 { get; set; }
    DateTime Field2 { get; set; }
    ...
}

Cuando "Field2" se devuelve como Json del servicio, el valor es:

/Date(1224043200000-0600)/

Observe la compensación de zona horaria incluida como parte del valor.

La expresión regular modificada:

/\/Date\((.*?)\)\//gi

Es un poco más ansioso y atrapa todo entre los parens, no solo el primer número. El tiempo resultante sinze 1970, más el desplazamiento de la zona horaria, se pueden alimentar en la evaluación para obtener un objeto de fecha.

La línea de JavaScript resultante para el reemplazo es:

replace(/\/Date\((.*?)\)\//gi, "new Date($1)");

57



No se repita: automatice la conversión de fechas usando $.parseJSON()

Las respuestas a su publicación proporcionan la conversión de fecha manual a las fechas de JavaScript. He extendido jQuery's $.parseJSON() solo un poco, por lo que es capaz de analizar automáticamente las fechas cuando se lo indique. Procesa las fechas formateadas de ASP.NET (/Date(12348721342)/), así como las fechas con formato ISO (2010-01-01T12.34.56.789Z) que son compatibles con funciones JSON nativas en los navegadores (y bibliotecas como json2.js).

De todas formas. Si no desea repetir el código de conversión de la fecha una y otra vez, le sugiero que lea esta publicación en el blog y obtén el código que hará que tu vida sea un poco más fácil.


53



Si dices en JavaScript,

var thedate = new Date(1224043200000);
alert(thedate);

Verás que es la fecha correcta, y puedes usarla en cualquier parte del código JavaScript con cualquier marco.


50



Haga clic aquí para consultar la demostración

JavaScript / jQuery

var = MyDate_String_Value = "/Date(1224043200000)/"
var value = new Date
            (
                 parseInt(MyDate_String_Value.replace(/(^.*\()|([+-].*$)/g, ''))
            );
var dat = value.getMonth() +
                         1 +
                       "/" +
           value.getDate() +
                       "/" +
       value.getFullYear();

Resultado - "15/10/2008"


46



Actualizado

Tenemos una biblioteca de UI interna que tiene que lidiar con el formato JSON incorporado de ASP.NET de Microsoft, como /Date(msecs)/, se le preguntó aquí originalmente, y la mayoría del formato de fecha de JSON incluyendo JSON.NET, como 2014-06-22T00:00:00.0. Además, tenemos que hacer frente a la incapacidad de oldIE para hacer frente a cualquier cosa menos 3 lugares decimales.

Primero detectamos qué tipo de fecha estamos consumiendo, lo analizamos en un JavaScript normal Date objeto, luego formatee eso.

1) Detecta el formato de Microsoft Date

// Handling of Microsoft AJAX Dates, formatted like '/Date(01238329348239)/'
function looksLikeMSDate(s) {
    return /^\/Date\(/.test(s);
}

2) Detecta el formato de fecha ISO

var isoDateRegex = /^(\d\d\d\d)-(\d\d)-(\d\d)T(\d\d):(\d\d):(\d\d)(\.\d\d?\d?)?([\+-]\d\d:\d\d|Z)?$/;

function looksLikeIsoDate(s) {
    return isoDateRegex.test(s);
}

3) Formato de fecha de Parse MS:

function parseMSDate(s) {
    // Jump forward past the /Date(, parseInt handles the rest
    return new Date(parseInt(s.substr(6)));
}

4) Analizar el formato de fecha ISO.

Al menos tenemos una manera de asegurarnos de que estamos tratando con fechas ISO estándar o fechas ISO modificadas para tener siempre lugares de tres milisegundos (véase más arriba), por lo que el código es diferente según el entorno.

4a) Analizar el formato de fecha ISO estándar, hacer frente a los problemas de oldIE:

function parseIsoDate(s) {
    var m = isoDateRegex.exec(s);

    // Is this UTC, offset, or undefined? Treat undefined as UTC.
    if (m.length == 7 ||                // Just the y-m-dTh:m:s, no ms, no tz offset - assume UTC
        (m.length > 7 && (
            !m[7] ||                    // Array came back length 9 with undefined for 7 and 8
            m[7].charAt(0) != '.' ||    // ms portion, no tz offset, or no ms portion, Z
            !m[8] ||                    // ms portion, no tz offset
            m[8] == 'Z'))) {            // ms portion and Z
        // JavaScript's weirdo date handling expects just the months to be 0-based, as in 0-11, not 1-12 - the rest are as you expect in dates.
        var d = new Date(Date.UTC(m[1], m[2]-1, m[3], m[4], m[5], m[6]));
    } else {
        // local
        var d = new Date(m[1], m[2]-1, m[3], m[4], m[5], m[6]);
    }

    return d;
}

4b) Analizar el formato ISO con un decimal fijo de tres milisegundos, mucho más fácil:

function parseIsoDate(s) {
    return new Date(s);
}

5) Formatearlo:

function hasTime(d) {
    return !!(d.getUTCHours() || d.getUTCMinutes() || d.getUTCSeconds());
}

function zeroFill(n) {
    if ((n + '').length == 1)
        return '0' + n;

    return n;
}

function formatDate(d) {
    if (hasTime(d)) {
        var s = (d.getMonth() + 1) + '/' + d.getDate() + '/' + d.getFullYear();
        s += ' ' + d.getHours() + ':' + zeroFill(d.getMinutes()) + ':' + zeroFill(d.getSeconds());
    } else {
        var s = (d.getMonth() + 1) + '/' + d.getDate() + '/' + d.getFullYear();
    }

    return s;
}

6) Ate todo:

function parseDate(s) {
    var d;
    if (looksLikeMSDate(s))
        d = parseMSDate(s);
    else if (looksLikeIsoDate(s))
        d = parseIsoDate(s);
    else
        return null;

    return formatDate(d);
}

La siguiente respuesta anterior es útil para vincular este formato de fecha en el propio análisis JSON de jQuery para que pueda obtener objetos de fecha en lugar de cadenas, o si todavía está atrapado en jQuery <1.5 de alguna manera.

Vieja respuesta

Si está utilizando la función Ajax de jQuery 1.4 con ASP.NET MVC, puede convertir todas las propiedades DateTime en objetos Date con:

// Once
jQuery.parseJSON = function(d) {return eval('(' + d + ')');};

$.ajax({
    ...
    dataFilter: function(d) {
        return d.replace(/"\\\/(Date\(-?\d+\))\\\/"/g, 'new $1');
    },
    ...
});

En jQuery 1.5 puede evitar anular el parseJSON método globalmente mediante el uso de la opción de convertidores en la llamada Ajax.

http://api.jquery.com/jQuery.ajax/

Lamentablemente, debe cambiar a la ruta eval más antigua para que las fechas se analicen globalmente en el lugar; de lo contrario, deberá convertirlas en un análisis caso por caso posterior.


31