Як відформатувати дату Microsoft JSON?


1999

Я беру свій перший тріск в Ajax за допомогою jQuery. Я заношу свої дані на свою сторінку, але у мене виникають проблеми з даними JSON, які повертаються для типів даних Date. В основному я отримую рядок назад, який виглядає приблизно так:

/Date(1224043200000)/

Від абсолютно нового в JSON - Як я відформатую це у форматі короткої дати? Чи слід це обробляти десь у коді jQuery? Я пробував jQuery.UI.datepickerплагін, використовуючи $.datepicker.formatDate()без успіху.

FYI: Ось рішення, яке я придумав, використовуючи комбінацію відповідей тут:

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;
}

Це рішення отримало мій об’єкт від методу зворотного виклику та відображало дати на сторінці належним чином, використовуючи бібліотеку формату дат.


26
Це може бути цікаво: hanselman.com/blog/…
citronas

6
Формат /Date(...)/ характерний для вбудованого формату дати JSON Microsoft - він не є частиною будь-якого стандарту, а JSON, що надходить з Javascript, має стандарт: Формат ISO Javascript визначає: stackoverflow.com/a / 15952652/176877 Отже, це питання є специфічним для формату дати JSON Microsoft від Microsoft. Я змінив заголовок, щоб уточнити це.
Кріс Москіні

15
Ти знущаєшся! Microsoft наклала власний спін на JSON! і на побачення !! Коли вони навчаться!
Nick.McDermaid

Використовуйте Newtonsoft JSON на стороні .NET і щоб мати гарні набрані значення на стороні JS, просто використовуйте: github.com/RickStrahl/json.date-extensions
baHI

Ви можете використовувати JSON ++ замість JSON. JSON ++ такий же, як JSON, але з підтримкою таких типів JavaScript, як Date.
брилянт

Відповіді:


1688

eval()не потрібно. Це буде добре працювати:

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

substr()Функція виймає /Date(частина, а parseInt()функція отримує ціле число і ігнорує )/в кінці. Отримане число передається в Dateконструктор.


Я навмисно залишив радікс (другий аргумент до parseInt); дивіться мій коментар нижче .

Також я повністю погоджуюся з коментарем Рорі : Дати ISO-8601 віддають перевагу цьому старому формату - тому цей формат взагалі не слід використовувати для нових розробок. Дивіться чудову бібліотеку Json.NET, щоб отримати чудову альтернативу, яка серіалізує дати у форматі ISO-8601.

Для дат JSON у форматі ISO-8601 просто переведіть рядок у Dateконструктор:

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

4
@Broam: Обидва способи (функція заміни та ця відповідь) повинні були змінитися, якщо MS змінить формат.
Рой Тінкер

23
Чи можете ви, будь ласка, оновити його за допомогою radix var date = new Date (parseInt (jsonDate.substr (6), 10));
Джеймс Кібурз

6
@JamesKyburz: Кожне правило має винятки, і я думаю, що це стосується випадків, коли застосовується виняток. Номери дати JSON з .NET ніколи не мають провідних "0", тому ми можемо сміливо не залишати радіус.
Рой Тінкер

22
Варто відзначити, що цей формат дати є досить поганим, і загальним кроком є ​​дати, відформатовані ISO-8601 в JSON. Дивіться hanselman.com/blog/…
Rory

4
Цей підхід не враховує часовий пояс, тому може спричинити серйозні проблеми, коли ваш сервер та користувачі знаходяться в різних часових поясах. Я розмістив відповідь нижче, в якій пояснюється дуже швидкий і простий спосіб впоратися з цим на сторонах WCF та Javascript: stackoverflow.com/a/10743718/51061
Скотт Віллеке

135

Ви можете використовувати це, щоб отримати побачення з JSON:

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

А потім ви можете використовувати скрипт формату JavaScript JavaScript (1,2 КБ при мінімізації та gzipped), щоб відобразити його так, як вам потрібно.


7
З рядком немає нічого поганого, послідовність - \ //. Перша косою рисою не обходиться, тому вона не вважається коментарем. Це ваш редактор обдурить вас, рядок буде добре працювати.
andreialecu

152
@rball, нісенітниця:jsonDate = new Date(+jsonDate.replace(/\/Date\((\d+)\)\//, '$1'));
безслідність

39
pst було правильним, це можна зробити різними способами без 'eval'. Крокфорд каже, що "eval Is Evil", тому що він менш читабельний і менш захищений, крім того, він може ще більше підкреслити, що він менш ефективний і небезпечніший, оскільки потрапляє на компілятор javascript.
Марк Роджерс

13
@Edy: new Functionмайже так само погано, як eval: dev.opera.com/articles/view/efficient-javascript/…
Марсель Корпель,

5
@Edy: Це ще одна форма eval, і це так само, як "зло". Натомість проаналізуйте рядок (див. Мою відповідь нижче)
Рой Тінкер

98

Для тих, хто використовує Newtonsoft Json.NET , прочитайте, як це зробити через Native JSON в IE8, Firefox 3.5 плюс Json.NET .

Також корисна документація щодо зміни формату дат, написаних Json.NET: Серіалізація дат за допомогою Json.NET

Для тих, хто занадто лінивий, ось швидкі кроки. Оскільки JSON має слабку реалізацію DateTime, вам потрібно використовувати IsoDateTimeConverter(). Зауважте, що оскільки Json.NET 4.5 формат дати за замовчуванням є ISO, тому код нижче не потрібен.

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

JSON перейде як

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

Нарешті, деякі JavaScript для перетворення дати ISO в дату 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;
}

Я використовував це так

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

6
Конструктор JavaScript Date може проаналізувати рядок для вас:new Date("2009-04-12T20:44:55")
David Hogue

5
Попередження - Формати конструктора Date () та їх розбір є нестандартними перед ECMAScript 6. Наприклад, IE 9 розглядає дату, яку ви надаєте конструктору, як місцевий час, навіть якщо він є в IS0-8601, який мається на увазі як UCT скрізь. Не підтримуйте конструктор дат, якщо ви підтримуєте старіші веб-переглядачі. codeofmatt.com/2013/06/07/…
DanO

Надсилання дати, що не є UTC, рано чи пізно потрапить у проблеми.
tymtam

Трохи запізнюємось на вечірку тут, але що б (+ a [1], + a [2] - 1, + a [3], + a [4], + a [5], + a [6]) ; представляти в цьому контексті?
Янант

@yanant - і +a[1]т. д. представляє шматки масиву регулярного вираження, і він +би додав його до числа, тому +a[1]дорівнює 2009і т. д. Ось розбивка масиву: 0: "2009-04-12T20:44:55" 1: "2009" 2: "04" 3: "12" 4: "20" 5: "44" 6: "55"
Джейсон Джонг,

67

Оригінальний приклад:

/Date(1224043200000)/  

не відображає форматування, використовуване WCF при надсиланні дат через WCF REST за допомогою вбудованої JSON серіалізації. (принаймні на .NET 3.5, SP1)

Я знайшов відповідь тут корисною, але потрібна невелика редакція регулярного виразу, оскільки, схоже, зміщення GMT часового поясу додається до поверненого номера (з 1970 року) у WCF JSON.

У службі WCF я маю:

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

ApptVisitLinkInfo визначається просто:

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

Коли "Field2" повертається як Json з сервісу, значення становить:

/Date(1224043200000-0600)/

Зверніть увагу на зміщення часового поясу, включене як частина значення.

Змінений регулярний вираз:

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

Це трохи більш нетерпляче і хапає все між паренами, а не лише перше число. Отриманий час синхронізації 1970 року, а також зміщення часового поясу може бути передано в eval, щоб отримати об'єкт дати.

Отриманий рядок JavaScript для заміни:

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

10
це неправильно, нова дата (1224043200000-0600) буде віднімати лише 600 від дати, в цьому випадку 600 мілісекунд, а не 6 годин як слід.
аріель


Я думаю, що зміщення часового поясу включається лише в тому випадку, якщо у вас є часовий пояс на об’єкті DateTime в .NET (що є поведінкою за замовчуванням). Якщо ваша дата в UTC, використовуйте DateTime.SpecifyKind (дата, DateTimeKind.UTC), і ви отримаєте відповідне значення UTC, коли воно буде серіалізуватися, без зміщення, яке ви зможете перетворити назад у часовий пояс користувача за потребою. Якщо це місцевий час, використовуйте .ToUniversalTime (), і він перетвориться на UTC, і "Kind" вже вказано для вас.
jvenema

в javascript -0100 буде двійковою рядком, тому будьте обережні!
verbedr

як тільки ви отримаєте дату, перетворену з WCF в JS, як щодо реверсу. У вас має бути дата як ціле число (використовуючи date.getTime ()), яке ви хочете передати тому ж WCF?
NitinSingh

65

Не повторіть себе - автоматизуйте перетворення дат за допомогою $.parseJSON()

Відповіді на ваш пост забезпечують ручне перетворення дат на дати JavaScript. Я розширив jQuery $.parseJSON()лише трохи, тому він може автоматично розбирати дати, коли ви доручаєте це. Він обробляє дати, відформатовані ASP.NET ( /Date(12348721342)/), а також дати у форматі ISO ( 2010-01-01T12.34.56.789Z), які підтримуються нативними функціями JSON у браузерах (та бібліотеках, таких як json2.js).

У всякому разі. Якщо ви не хочете повторювати код перетворення дати, я пропоную вам прочитати цю публікацію в блозі та отримати код, який полегшить ваше життя трохи легше.


61

Якщо ви говорите в JavaScript,

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

ви побачите, що це правильна дата, і ви можете використовувати це будь-де в коді JavaScript з будь-якою рамкою.


3
Це те, що я міг би подумати, за винятком того, що це: var thedate = / Дата (1224043200000) /; принаймні для мене ...
rball

2
Дата () та Дата (1224043200000) дають однаковий результат як у Chrome, так і в Firefox. Не впевнений, чи це працювало в старих браузерах, але ця відповідь зараз не працює в браузерах.
Джеймс

@James, так, це дає поточну дату браузера. :(
vissu

9
Вам потрібно записати це як "нова дата (1224043200000)".
BrainSlugs83

60

Клацніть тут, щоб перевірити демонстрацію

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();

Результат - "15.10.2008"


Просто вдосконалення методу, описаного вище. функція formatearFecha (fec) {var value = new Date (parseInt (fec.replace (/ (^. * () | ([+ -]. * $) / g, ''))); var mes = value.getMonth (); var dia = value.getDate (); var date = dia + "/" + mes + "/" + value.getFullYear (); if (dia <10) date = date.substr (0, 0) + '0' + dia + date.substr (1); if (mes <10) date = date.substr (0, 3) + '0' + mes + date.substr (4); дата повернення;} дата відформатована у привіт, привіт!
Matias

38

Оновлено

У нас є внутрішня бібліотека інтерфейсу користувача, яка повинна справлятися як з вбудованим форматом JSON, як ASP.NET Microsoft, як /Date(msecs)/, наприклад , запитували тут спочатку, а також більшість форматів дати JSON, включаючи JSON.NET, як 2014-06-22T00:00:00.0. Крім того, нам потрібно впоратися зі нездатністю oldIE впоратися ні з чим, крім трьох знаків після коми .

Ми спочатку виявляємо, яку дату ми споживаємо, аналізуємо її на звичайний Dateоб’єкт JavaScript , а потім відформатуємо її.

1) Виявити формат дати Microsoft

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

2) Виявити формат дати 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) Розбір формату дати MS:

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

4) Проаналізуйте формат дати ISO.

У нас є принаймні спосіб бути впевненим, що ми маємо справу зі стандартними датами ISO або датами ISO, модифікованими завжди на три мілісекундні місця ( див. Вище ), тому код відрізняється залежно від середовища.

4a) Розбирайте стандартний формат дати ISO, справляйтеся з проблемами 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) Розбираємо формат ISO з фіксованими трьома мілісекундними десятковими знаками - набагато простіше:

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

5) Відформатуйте його:

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) Зв’яжіть все разом:

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

    return formatDate(d);
}

Наведена нижче відповідь корисна для прив’язки форматування цієї дати до власного розбору JSON jQuery, щоб ви отримали об'єкти Date замість рядків або якщо ви все ще застрягли в jQuery <1,5.

Стара відповідь

Якщо ви використовуєте функцію Ajax jjaery 1.4 з ASP.NET MVC, ви можете перетворити всі властивості DateTime в об'єкти дати за допомогою:

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

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

У jQuery 1.5 ви можете уникнути зміни parseJSONметоду в усьому світі, використовуючи опцію перетворювачів у виклику Ajax.

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

На жаль, вам доведеться перейти на старіший маршрут eval, щоб дати датам проаналізувати всесвітнє місце - інакше вам потрібно перетворити їх на кожному конкретному випадку після аналізу.


27

У JSON не існує вбудованого типу дати . Це виглядає як кількість секунд / мілісекунд з якоїсь епохи. Якщо ви знаєте епоху, ви можете створити дату, додавши потрібну кількість часу.


Це неправильно, JSON використовує дати Javascript з доданою інформацією про часовий пояс - епоха така ж, як епоха класу javascript Date (з очевидних причин).
BrainSlugs83

3
@ BrainSlug83 - ця відповідь дає посилання на твердження про те, що JSON не має вбудованого типу дати. Якщо ви не згодні, надайте альтернативну довідку. (Ви не думаєте про конкретний фреймворк, який визначив формат рядка для відображення дат, чи не так? Це не є частиною стандарту JSON. Дійсно, це не могло бути, тому що неможливо було б включити рядок, який не є передбачається вважати датою, але у неї буває набір символів, що відповідають шаблону дати.)
nnnnnn

25

Мені також довелося шукати рішення цієї проблеми, і, врешті-решт, я натрапив на moment.js, який є приємною бібліотекою, яка може проаналізувати цей формат дати та багато іншого.

var d = moment(yourdatestring)

Це врятувало мені певний головний біль, тому я подумав, що поділюся з вами. :)
Більше інформації про це можна знайти тут: http://momentjs.com/


24

Нарешті я додав символи до регулярного виразу Panos, щоб позбутися тих, що створюються серіалізатором Microsoft для запису об'єктів у вбудований сценарій:

Отже, якщо у вас є властивість у вашому коді C # , це щось подібне

protected string JsonObject { get { return jsSerialiser.Serialize(_myObject); }}

І у вашій aspx є

<script type="text/javascript">
    var myObject = '<%= JsonObject %>';
</script>

Ви отримаєте щось на кшталт

var myObject = '{"StartDate":"\/Date(1255131630400)\/"}';

Зауважте подвійні лапки.

Щоб перетворити це у форму, яку евал правильно десеріалізує, я використав:

myObject = myObject.replace(/"\/Date\((\d+)\)\/"/g, 'new Date($1)');

Я використовую прототип і до його використання я додав

String.prototype.evalJSONWithDates = function() {
    var jsonWithDates = this.replace(/"\/Date\((\d+)\)\/"/g, 'new Date($1)');
    return jsonWithDates.evalJSON(true);
}

22

У jQuery 1.5, якщо у вас є json2.js для покриття для старих браузерів, ви можете дезаріалізувати всі дати, що надходять з Ajax, наступним чином:

(function () {
    var DATE_START = "/Date(";
    var DATE_START_LENGTH = DATE_START.length;

    function isDateString(x) {
        return typeof x === "string" && x.startsWith(DATE_START);
    }

    function deserializeDateString(dateString) {
        var dateOffsetByLocalTime = new Date(parseInt(dateString.substr(DATE_START_LENGTH)));
        var utcDate = new Date(dateOffsetByLocalTime.getTime() - dateOffsetByLocalTime.getTimezoneOffset() * 60 * 1000);
        return utcDate;
    }

    function convertJSONDates(key, value) {
      if (isDateString(value)) {
        return deserializeDateString(value);
      }
      return value;
    }

    window.jQuery.ajaxSetup({
      converters: {
        "text json": function(data) {
          return window.JSON.parse(data, convertJSONDates);
        }
      }
    });
}());

Я включив логіку, яка передбачає, що ви надсилаєте всі дати з сервера як UTC (що вам слід); Потім споживач отримує об’єкт JavaScript, Dateякий має належне значення кліщів для відображення цього. Тобто, виклик getUTCHours()тощо у дату поверне те саме значення, що і на сервері, а виклик getHours()поверне значення у локальному часовому поясі користувача, визначене їх браузером.

Це не враховує формат WCF із зміщенням часового поясу, хоча це було б відносно легко додати.


Як зауваження: для роботи коду потрібно створити метод startWith типу рядка
Hugo Zapata

21

Використання інтерфейсу jQuery UI - насправді має сенс лише якщо ви вже включаєте інтерфейс jQuery:

$.datepicker.formatDate('MM d, yy', new Date(parseInt('/Date(1224043200000)/'.substr(6)))); 

вихід:

15 жовтня 2008 року


20

Не передумуйте це. Як ми це робили десятиліттями, пройдіть числовий зсув із стандартної епохи фактичного факту 1 січня 1970 року опівночі GMT / UTC / & c за кількість секунд (або мілісекунд) з цієї епохи. JavaScript це подобається, Java йому подобається, C це любить, і Інтернет це любить.


2
І дуже погано, що є більше 20 епох на вибір. en.wikipedia.org/wiki/Epoch_(reference_date)
Джертер


18

Кожен із цих відповідей має одне спільне: всі вони зберігають дати як єдине значення (зазвичай це рядок).

Інший варіант - скористатися притаманною структурою JSON та представити дату як список номерів:

{ "name":"Nick",
  "birthdate":[1968,6,9] }

Звичайно, вам слід переконатися, що обидва кінці розмови домовляються про формат (рік, місяць, день), а також поля, які мають бути датами, ... але це має перевагу повністю уникати дати дати перетворення рядків. Це всі цифри - взагалі немає рядків. Також, використовуючи замовлення: рік, місяць, день, також можна правильно сортувати за датою.

Думаючи, що тут не вказано - дата JSON не повинна зберігатися як рядок.

Ще один бонус за це таким чином полягає в тому, що ви можете легко (і ефективно) вибрати всі записи за даний рік або місяць, використовуючи спосіб, яким CouchDB обробляє запити на значення масивів.


Там є стандартним форматом дати в форматі JSON, який є формат RFC 3339.
gnasher729

@gnasher, це було б добре, але це не так. Немає посилань від RFC 7159 до 3339 або навпаки. Не існує стандартного формату дати JSON де-юре . Залишилися фактично стандарти, кожен з яких має свої плюси та мінуси. Це приємна річ у стандартах.
Марк Л.

17

Публікація у приголомшливій темі:

var d = new Date(parseInt('/Date(1224043200000)/'.slice(6, -2)));
alert('' + (1 + d.getMonth()) + '/' + d.getDate() + '/' + d.getFullYear().toString().slice(-2));

1
Хороша ідея, але що робити, якщо включено зміщення часового поясу? Краще використовувати substr (6) у цьому випадку замість зрізу (6, -2) - дивіться мою відповідь нижче.
Рой Тінкер

17

Просто додати тут ще один підхід, "підхід кліщів", ​​який застосовує WCF , схильний до проблем із часовими поясами, якщо ви не дуже обережні, як описано тут та в інших місцях. Тому я зараз використовую формат ISO 8601, який підтримує належну підтримку .NET і JavaScript, що включає зміщення часового поясу. Нижче наведено деталі:

У WCF / .NET:

Де CreationDate є System.DateTime; ToString ("o") використовує специфікатор формату .NET для зворотного переходу, який генерує ISO 8601-сумісний рядок дати

new MyInfo {
    CreationDate = r.CreationDate.ToString("o"),
};

У JavaScript

Одразу після отримання JSON я перебираю дати, які будуть об’єктами дати JavaSript Date, використовуючи конструктор Date, який приймає рядок дати ISO 8601 ...

$.getJSON(
    "MyRestService.svc/myinfo",
    function (data) {
        $.each(data.myinfos, function (r) {
            this.CreatedOn = new Date(this.CreationDate);
        });
        // Now each myinfo object in the myinfos collection has a CreatedOn field that is a real JavaScript date (with timezone intact).
       alert(data.myinfos[0].CreationDate.toLocaleString());
    }
)

Коли у вас є дата JavaScript, ви можете використовувати всі зручні та надійні методи дати , такі як toDateString , toLocaleString тощо.


16
var newDate = dateFormat(jsonDate, "mm/dd/yyyy"); 

Чи є інший варіант без використання бібліотеки jQuery?


Це нове питання, і його слід задавати як власне питання, а не вбудовувати тут.
Спенсер Салліван

11

Це може вам також допомогти.

 function ToJavaScriptDate(value) { //To Parse Date from the Returned Parsed Date
        var pattern = /Date\(([^)]+)\)/;
        var results = pattern.exec(value);
        var dt = new Date(parseFloat(results[1]));
        return (dt.getMonth() + 1) + "/" + dt.getDate() + "/" + dt.getFullYear();
    }

10

Нижче представлено досить просте рішення для розбору дат JSON. Використовуйте наведені нижче функції відповідно до вашої потреби. Вам просто потрібно передати дану функцію формату JSON як параметр нижче:

function JSONDate(dateStr) {
    var m, day;
    jsonDate = dateStr;
    var d = new Date(parseInt(jsonDate.substr(6)));
    m = d.getMonth() + 1;
    if (m < 10)
        m = '0' + m
    if (d.getDate() < 10)
        day = '0' + d.getDate()
    else
        day = d.getDate();
    return (m + '/' + day + '/' + d.getFullYear())
}

function JSONDateWithTime(dateStr) {
    jsonDate = dateStr;
    var d = new Date(parseInt(jsonDate.substr(6)));
    var m, day;
    m = d.getMonth() + 1;
    if (m < 10)
        m = '0' + m
    if (d.getDate() < 10)
        day = '0' + d.getDate()
    else
        day = d.getDate();
    var formattedDate = m + "/" + day + "/" + d.getFullYear();
    var hours = (d.getHours() < 10) ? "0" + d.getHours() : d.getHours();
    var minutes = (d.getMinutes() < 10) ? "0" + d.getMinutes() : d.getMinutes();
    var formattedTime = hours + ":" + minutes + ":" + d.getSeconds();
    formattedDate = formattedDate + " " + formattedTime;
    return formattedDate;
}

10

Ви також можете використовувати бібліотеку JavaScript moment.js , яка стане в нагоді, коли ви плануєте мати справу з різними локалізованими форматами та виконувати інші операції зі значеннями дат:

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

    function (result) {
        $("#AuthMerchId").text(result.AuthorizationMerchantId);
        $("#SttlMerchId").text(result.SettlementMerchantId);
        $("#CreateDate").text(moment(result.AppendDts).format("L"));
        $("#ExpireDate").text(moment(result.ExpiresDts).format("L"));
        $("#LastUpdate").text(moment(result.LastUpdateDts).format("L"));
        $("#LastUpdatedBy").text(result.LastUpdateNt);
        $("#ProcessIn").text(result.ProcessIn);
    }
    );
    return false;
}

Налаштування локалізації так само просто, як додавання файлів конфігурації (ви отримуєте їх на momentjs.com) до свого проекту та налаштування мови:

moment.lang('de');

9

Я отримую дату приблизно так:

"/Date(1276290000000+0300)/"

У деяких прикладах дата є дещо іншими форматами:

"/Date(12762900000000300)/"
"Date(1276290000000-0300)"

тощо.

Тому я придумав наступний RegExp:

/\/+Date\(([\d+]+)\)\/+/

і остаточний код:

var myDate = new Date(parseInt(jsonWcfDate.replace(/\/+Date\(([\d+-]+)\)\/+/, '$1')));

Сподіваюся, це допомагає.

Оновлення: Я знайшов це посилання від Microsoft: Як серіалізувати дати з JSON?

Це схоже на той, кого ми всі шукаємо.


1
Заміни Regexp повільні ... Набагато швидше схопити цілу частину за допомогою substr (6) і передати її до parseInt () - див. Мою відповідь нижче.
Рой Тінкер


9

Перевірте дату стандарту ISO; такого типу:

yyyy.MM.ddThh:mm

Це стає 2008.11.20T22:18.


Згідно схеми JSON, формат "дата-час" відповідає RFC 3339, розділ 5.6. Отже, ви повинні написати "yyyy-MM-ddTHH: mm: ssZ" для дат у GMT, або Z замінити на часовий пояс типу + hh: mm.
gnasher729

Проблема полягає в тому, що WCF та інша "стара" серіалізація MS JSON не використовують цей формат, і це потрібно враховувати.
Марк Л.

9

Це засмучує. Моє рішення полягало в тому, щоб розібрати "/ і /" зі значення, сформованого JavaScript Aeria.Serializer ASP.NET, так що, хоча JSON може не мати літеральної дати, він все ще інтерпретується браузером як датою, що є все, що я насправді хочу:{"myDate":Date(123456789)}

Спеціальний JavaScriptConverter для DateTime?

Треба підкреслити точність коментаря Роя Тінкера. Це не є законним JSON. Це брудне, брудне злом на сервері, щоб усунути проблему, перш ніж це стане проблемою для JavaScript. Це задушить аналізатор JSON. Я використовував це для сходження з землі, але цим більше не користуюся. Однак я все ще вважаю, що найкраща відповідь полягає у зміні того, як сервер формує дату, наприклад, ISO, як згадується в інших місцях.


2
Це не законно JSON. Він працюватиме лише тоді, коли буде зрівнятися з інтерпретатором Javascript. Але якщо ви використовуєте декодер JSON, він задушиться.
Рой Тінкер

1
Домовились. І якби я просто мав справу з цією частиною даних, я б не вважав це. Але якщо я маю справу з об'єктом декількох дат та іншими властивостями, простіше оцінити () всю справу, ніж вибирати властивості по одному. Зрештою, основним питанням є відсутність (законної) дати JSON. Доки це не існує, ми залишаємось нашими творчими хаками.
StarTrekRedneck

8

Пізній пост, але для тих, хто шукав цю публікацію.

Уявіть собі це:

    [Authorize(Roles = "Administrator")]
    [Authorize(Roles = "Director")]
    [Authorize(Roles = "Human Resources")]
    [HttpGet]
    public ActionResult GetUserData(string UserIdGuidKey)
    {
        if (UserIdGuidKey!= null)
        {
            var guidUserId = new Guid(UserIdGuidKey);
            var memuser = Membership.GetUser(guidUserId);
            var profileuser = Profile.GetUserProfile(memuser.UserName);
            var list = new {
                              UserName = memuser.UserName,
                              Email = memuser.Email ,
                              IsApproved = memuser.IsApproved.ToString() ,
                              IsLockedOut = memuser.IsLockedOut.ToString() ,
                              LastLockoutDate = memuser.LastLockoutDate.ToString() ,
                              CreationDate = memuser.CreationDate.ToString() ,
                              LastLoginDate = memuser.LastLoginDate.ToString() ,
                              LastActivityDate = memuser.LastActivityDate.ToString() ,
                              LastPasswordChangedDate = memuser.LastPasswordChangedDate.ToString() ,
                              IsOnline = memuser.IsOnline.ToString() ,
                              FirstName = profileuser.FirstName ,
                              LastName = profileuser.LastName ,
                              NickName = profileuser.NickName ,
                              BirthDate = profileuser.BirthDate.ToString() ,
            };
            return Json(list, JsonRequestBehavior.AllowGet);
        }
        return Redirect("Index");
    }

Як бачите, я використовую функцію C # 3.0 для створення "Автоматичної" Generics. Це трохи ліниво, але мені це подобається і це працює. Лише зауваження: профіль - це спеціальний клас, який я створив для свого проекту веб-додатків.


тому кожен раз, коли ви додаєте нову роль [Авторизація (Ролі = "Людські ресурси")], вам доведеться компілювати та розгортати? ух .... :)
Алекс Ноласко

1
Якщо це служба JSON, то переспрямування здається неправильним. Я б повернув 404 Not Found, якщо ключ введення настільки недійсний, його неможливо знайти (а також 404, якщо він справді не знайдений). Коли мої користувачі не ввійшли в систему, я повертаю 403 Заборонено.
Річард Корфілд

Це "багаторазовий" метод. Наприклад, якщо я хотів отримати дані користувачів з іншого представлення даних, я можу отримати його доти, поки я надаю ідентифікатор. Однак якщо Id не надається, сторінка перенаправляє до списку користувачів (Index), щоб вибрати користувача. Просте рішення, необхідне для програми, саме так, як мій мозок готував його в той час.
Рей Ліндер

8

FYI, для всіх, хто використовує Python на стороні сервера: datetime.datetime (). Ctime () повертає рядок, який в початковому порядку проаналізується "new Date ()". Тобто, якщо ви створюєте новий екземпляр datetime.datetime (наприклад, з datetime.datetime.now), рядок може бути включений у рядок JSON, і тоді ця рядок може бути передана як перший аргумент конструктору Date. Я ще не знайшов жодних винятків, але теж не перевірив це занадто жорстко.


8

Рішення Mootools:

new Date(Date(result.AppendDts)).format('%x')

Потрібні mootools-більше. Тестували за допомогою mootools-1.2.3.1-more на Firefox 3.6.3 та IE 7.0.5730.13


8
var obj = eval('(' + "{Date: \/Date(1278903921551)\/}".replace(/\/Date\((\d+)\)\//gi, "new Date($1)") + ')');
var dateValue = obj["Date"];

8

Додайте на свою сторінку плагін jQuery UI :

function DateFormate(dateConvert) {
    return $.datepicker.formatDate("dd/MM/yyyy", eval('new ' + dateConvert.slice(1, -1)));
};

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.