Avatar ·

Какой правильный формат даты в JSON и как с ним работать в JavaScript?

Всем привет! Я начинающий JavaScript-разработчик, и у меня возникла проблема с передачей дат через JSON. Пишу небольшое приложение, которое отправляет данные с датами на сервер и получает их обратно. Но я запутался в форматах. Вот пример моего кода: ```javascript // Создаю объект с датой const event = { title: "Встреча", date: new Date("2024-03-15T10:00:00") }; // Отправляю на сервер fetch('/api/events', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(event) }); // Получаю обратно fetch('/api/events') .then(res => res.json()) .then(data => console.log(data.date)); // Что я получу? ``` Когда я смотрю в консоль, то вижу строку типа "2024-03-15T07:00:00.000Z" или иногда "2024-03-15T10:00:00.000+03:00". А когда пытаюсь преобразовать обратно в объект Date — то получаю разные результаты в зависимости от часового пояса. Подскажите, какой формат даты считается правильным в JSON? И как правильно работать с датами, чтобы не было проблем с часовыми поясами? Может есть какие-то лучшие практики? Заранее спасибо за помощь! <<>>

Правильный формат даты в JSON — ISO 8601

Стандарт JSON (RFC 7159) не определяет специального типа для дат. Вместо этого принято использовать строковое представление в формате ISO 8601. Это международный стандарт, который однозначно определяет дату и время.

Рекомендуемый формат: YYYY-MM-DDTHH:mm:ss.sssZ (всегда в UTC) или с указанием смещения часового пояса. Буква Z в конце означает UTC (нулевое смещение).

Почему это важно?

  • Однозначность — строка всегда интерпретируется одинаково, независимо от часового пояса клиента или сервера.
  • Сортировка — ISO-строки можно сортировать лексикографически, и это будет корректной сортировкой по времени.
  • Поддержка — все современные языки программирования умеют парсить ISO 8601.

Как правильно работать в JavaScript

Вот лучшая практика для работы с датами в JSON:

// 1. При отправке — всегда конвертируем в ISO строку UTC
const event = {
  title: "Встреча",
  date: new Date("2024-03-15T10:00:00").toISOString()
  // Результат: "2024-03-15T07:00:00.000Z" (если часовой пояс +3)
};

// 2. При получении — парсим ISO строку обратно в Date
fetch('/api/events')
  .then(res => res.json())
  .then(data => {
    const date = new Date(data.date); // data.date = "2024-03-15T07:00:00.000Z"
    console.log(date.toLocaleString()); // покажет в локальном времени пользователя
  });

// 3. Если нужно работать с датой без времени (только дата)
const birthday = {
  name: "Анна",
  date: "1990-05-20" // просто дата, без времени
};
// Для парсинга: new Date(birthday.date + "T00:00:00Z")

Что делать, если сервер присылает timestamp (миллисекунды)?

Некоторые API используют Unix timestamp (число миллисекунд с 1 января 1970 UTC). Это тоже валидный вариант:

// Получаем timestamp
const timestamp = 1710489600000; // 15 марта 2024 00:00 UTC
const date = new Date(timestamp);
console.log(date.toISOString()); // "2024-03-15T00:00:00.000Z"

// Отправляем timestamp
const data = { event_time: Date.now() };

Рекомендации для backend-разработчиков

  • Всегда храните даты в UTC на сервере и в базе данных.
  • Возвращайте даты в ISO 8601 (с Z на конце) — это стандарт де-факто.
  • Если используете timestamp, убедитесь, что это миллисекунды (а не секунды, как в некоторых языках).
  • Для сложной работы с датами (часовые пояса, форматирование) используйте библиотеку date-fns или Luxon.

Пример с библиотекой date-fns

import { format, parseISO } from 'date-fns';

const isoString = "2024-03-15T07:00:00.000Z";
const date = parseISO(isoString);

// Форматируем для пользователя
console.log(format(date, 'dd.MM.yyyy HH:mm')); // "15.03.2024 10:00" (если +3)

Итог: Используйте ISO 8601 с Z на конце (UTC) для передачи дат в JSON. Это универсальный, понятный и безопасный формат, который решает проблемы с часовыми поясами.

<<>>

Альтернативный подход: использование Unix timestamp

Некоторые разработчики предпочитают передавать даты в виде числа — Unix timestamp в миллисекундах. Это особенно удобно, когда:

  • API используется в системах с разными языками программирования
  • Нужно выполнять арифметические операции с датами (сложение, вычитание)
  • Важна компактность данных (число занимает меньше места, чем строка)
// Отправка
const data = {
  created_at: Date.now() // 1710489600000
};

// Получение и преобразование
fetch('/api/data')
  .then(res => res.json())
  .then(data => {
    const date = new Date(data.created_at);
    console.log(date.toISOString()); // "2024-03-15T00:00:00.000Z"
  });

Недостатки:

  • Человек не может прочитать дату из JSON без преобразования
  • Путаница между секундами и миллисекундами (в PHP, Python часто используют секунды)
  • Сложнее отлаживать

Компромиссный вариант: Используйте ISO 8601 для API, которые читают люди, и timestamp для высоконагруженных внутренних систем. Главное — документировать формат в спецификации API.