Angular.js: $ http изменяет дату в объекте POSTED JSON (удаляет часовой пояс или сезонное смещение)

Созданный на 25 апр. 2016  ·  3Комментарии  ·  Источник: angular/angular.js

Я считаю это ошибкой.

Каково текущее поведение?

В настоящее время у меня есть хороший объект даты, который выходит из системы

Пт 29 апреля 2016 13:33:00 GMT + 0100 (BST)

Когда этот объект затем размещается через $ http, в сетевых запросах наблюдается следующее:

2016-04-28T12: 33: 00.000Z

Таким образом, объект $ http вычитает час и эффективно удаляет британское летнее время BST из времени. Таким образом, это хранится в базе данных без этого смещения. Когда мы сразу читаем эту дату, она возвращается, но как система может узнать, что нам нужно добавить час?

Итак, представьте, что пользователь находится в другом часовом поясе ... скажите на 5 часов вперед, тогда система вычтет 5 часов ... Время зависит от контекста, в котором оно создано. другими словами, информация о часовом поясе не должна удаляться.

Я вижу это в Chrome. Угловой 1.4.2

Также http://stackoverflow.com/questions/24356475/angular-js-date-changes-when-submitting-to-http-timezone-issue

Самый полезный комментарий

Во-первых, я думаю, что неправильно говорить, что объект Date не имеет информации о часовом поясе.

Я по-прежнему считаю правильным сказать, что: grin: A Date object _ "представляет отдельный момент времени [...] на основе значения времени, которое представляет собой количество миллисекунд с 1 января 1970 года по всемирному координированному времени" _ (источник: MDN ). Итак, в основном каждый экземпляр Date знает только об этом одном значении, а все другие его представления создаются на основе этой информации плюс локаль / состояние системы (например, смещение часового пояса).

#

Объект Date имеет методы getTimezoneOffset и toISOString .

Эти методы относятся к прототипу Date (источник: MDN ), а не к самим объектам Date (также известным как экземпляры).

В частности, значение getTimezoneOffset () зависит от текущей локали (настроек хост-системы). По этой причине не существует эквивалентного метода setTimezoneOffset() и почему все объекты Date в одной системе возвращают одно и то же значение для getTimezoneOffset() , например:

const d1 = new Date('December 15, 2018 12:34:56');  // No timezone; uses the current system locale.
const d2 = new Date('December 15, 2018 12:34:56 GMT+10'); // Uses GTM+10 as timezone.

d1.getTimezoneOffset() === d2.getTimezoneOffset();  // true

Таким образом, информация о часовом поясе, указанная в строковом представлении даты, переданном в Date используется только для анализа этой строки и сопоставления ее с определенным моментом времени, как описано выше. Получившийся объект Date ничего не знает о часовых поясах: smiley:

Метод toISOString () не выводит информацию о часовом поясе, как вы предложили. Он просто добавляет Z в конце, что означает UTC .

#

Во-вторых, JSON.stringify() также не удаляет значение зоны

Как объяснялось выше, он использует toISOString() , который выражает значение даты в формате UTC (таким образом, добавляя Z в конце, чтобы указать это). В возвращаемой строке нет информации о часовом поясе.

#

Поэтому я по-прежнему считаю, что если API отображает дату ISO, которая не имеет значения в миллисекундах, а пользовательский интерфейс использует какой-то datepicker, который выбирает только дату и дату изменения, тогда Angular при отправке даты обратного преобразования в формат ISO не будет иметь миллисекунд ценить.

Понятия не имею, при чем тут миллисекунды. Мы говорили об информации о часовом поясе.

Опять же, это не имеет ничего общего с AngularJS. Вот как встроенные объекты (такие как Date и JSON ) взаимодействуют друг с другом.

Все 3 Комментарий

Это не что-то специфическое для Angular. Это стандартное поведение JSON.stringify .

Обычно при публикации данных $http конвертирует их в JSON (через JSON.stringify() ). В JavaScript JSON-представление объекта Date - это его форма ISO-8601 (это то, что вы видите на вкладке сети).

В любом случае объект Date не имеет информации о часовом поясе, поэтому информация не удаляется. Текущая локаль (которая полностью не зависит от даты, представленной объектами Date) имеет смещение часового пояса, и браузер форматирует дату в соответствии с этим смещением, когда console.log ging это.

Закрытие, поскольку это не проблема Angular.

@gkalpak Во-первых, я думаю, что неправильно говорить, что объект Date не имеет информации о часовом поясе. Когда мы создаем дату с помощью new Date (), информация о часовом поясе по умолчанию является локальной. Объект Date имеет методы getTimezoneOffset и toISOString . При вызове эти методы возвращают значение зоны, ничего хорошего в браузере не печатается, это фактические значения в объекте Date.

new Date().getTimezoneOffset()
-330

new Date().toISOString()
"2018-12-04T05:40:37.399Z"

Во-вторых, JSON.stringify() также не удаляет значение зоны, вот что мы видели в консоли браузера, и это то же самое, браузер не печатает ничего приятного для нас.

JSON.stringify({d:new Date()})
"{"d":"2018-12-04T05:42:08.973Z"}"

Поэтому я по-прежнему считаю, что если API отображает дату ISO, которая не имеет значения в миллисекундах, а пользовательский интерфейс использует какой-то datepicker, который выбирает только дату и дату изменения, тогда Angular при отправке даты обратного преобразования в формат ISO не будет иметь миллисекунд ценить.

Во-первых, я думаю, что неправильно говорить, что объект Date не имеет информации о часовом поясе.

Я по-прежнему считаю правильным сказать, что: grin: A Date object _ "представляет отдельный момент времени [...] на основе значения времени, которое представляет собой количество миллисекунд с 1 января 1970 года по всемирному координированному времени" _ (источник: MDN ). Итак, в основном каждый экземпляр Date знает только об этом одном значении, а все другие его представления создаются на основе этой информации плюс локаль / состояние системы (например, смещение часового пояса).

#

Объект Date имеет методы getTimezoneOffset и toISOString .

Эти методы относятся к прототипу Date (источник: MDN ), а не к самим объектам Date (также известным как экземпляры).

В частности, значение getTimezoneOffset () зависит от текущей локали (настроек хост-системы). По этой причине не существует эквивалентного метода setTimezoneOffset() и почему все объекты Date в одной системе возвращают одно и то же значение для getTimezoneOffset() , например:

const d1 = new Date('December 15, 2018 12:34:56');  // No timezone; uses the current system locale.
const d2 = new Date('December 15, 2018 12:34:56 GMT+10'); // Uses GTM+10 as timezone.

d1.getTimezoneOffset() === d2.getTimezoneOffset();  // true

Таким образом, информация о часовом поясе, указанная в строковом представлении даты, переданном в Date используется только для анализа этой строки и сопоставления ее с определенным моментом времени, как описано выше. Получившийся объект Date ничего не знает о часовых поясах: smiley:

Метод toISOString () не выводит информацию о часовом поясе, как вы предложили. Он просто добавляет Z в конце, что означает UTC .

#

Во-вторых, JSON.stringify() также не удаляет значение зоны

Как объяснялось выше, он использует toISOString() , который выражает значение даты в формате UTC (таким образом, добавляя Z в конце, чтобы указать это). В возвращаемой строке нет информации о часовом поясе.

#

Поэтому я по-прежнему считаю, что если API отображает дату ISO, которая не имеет значения в миллисекундах, а пользовательский интерфейс использует какой-то datepicker, который выбирает только дату и дату изменения, тогда Angular при отправке даты обратного преобразования в формат ISO не будет иметь миллисекунд ценить.

Понятия не имею, при чем тут миллисекунды. Мы говорили об информации о часовом поясе.

Опять же, это не имеет ничего общего с AngularJS. Вот как встроенные объекты (такие как Date и JSON ) взаимодействуют друг с другом.

Была ли эта страница полезной?
0 / 5 - 0 рейтинги