Недавно я встретил date4j, чрезвычайно простая библиотека (по существу, один класс) для работы с датами в Java. Концептуально мне очень нравится "идея" date4j. Фактически, после прочтения всего основного сайта и документации в javadoc, я в значительной степени согласен со всем заявленным.
Теперь существует может несколько причин, почему я не должен использовать date4j - ошибки, производительность, отсутствие пользователей и т.д. Я не спрашиваю об этих вещах. Я спрашиваю, концептуально, что не так с идеей date4j (для большинства приложений там)? Конечно, могут быть некоторые приложения, которые нуждаются в чем-то вроде joda или threeten, но я считаю, что эти люди находятся в меньшинстве.
Обычный совет, который люди дают пользователям, связанным с датами/временем (почти все, кто пишет java-приложение), есть что-то вроде:
- Используйте joda-time вместо java.util.Calendar
- Установите ваш веб-сервер в UTC
- Установите сервер базы данных в UTC
- Сохраняйте дату в UTC
Фактически, последние три пулевых пункта иллюстрируют проблемы с текущей ментальной моделью, которую люди имеют при работе с датами. Люди пытаются управлять часовыми поясами как на уровне приложений, так и на уровне базы данных (не говоря уже о том, что рамки ORM добавляют еще один слой абстракции, что усложняет ситуацию).
Вам не нужно делать эти вещи. Например, если вы используете java.util.Calendar, и вы управляете временем в определенном пользовательском часовом поясе:
Calendar c = Calendar.getInstance(TimeZone.getTimeZone("America/New_York"));
c.set(Calendar.YEAR, 2011);
c.set(Calendar.MONTH, 0);
c.set(Calendar.DAY_OF_MONTH, 1);
c.set(Calendar.HOUR_OF_DAY, 3);
c.set(Calendar.MINUTE, 0);
c.set(Calendar.SECOND, 0);
c.set(Calendar.MILLISECOND, 0);
Это означает "мгновение" во времени, независимо от часового пояса. Вы должны быть в состоянии сохранять это время и из базы данных, не беспокоясь о каких-либо "конверсиях". Не имеет значения, находится ли база данных в часовом поясе в Шанхае, а веб-сервер находится в часовом поясе Лос-Анджелеса - время вовремя одинаковое.
Одна из проблем заключается в том, что некоторые базы данных пытаются управлять часовыми поясами для вас (я смотрю на вас, Postgres! grr!) и ухудшает поведение на уровне драйвера JDBC зависит от поставщика - то есть PreparedStatement.setDate/getDate.
Ментальная модель, используемая date4j, по-видимому, избавляет от всякой путаницы. Например, явно принудительно использует использование для предоставления часового пояса при вызове now(). На сайте есть очень хорошие рекомендации по использованию библиотеки (эти вещи я уже делал в своем собственном приложении ранее), например:
- не использовать тип базы данных, который пытается управлять часовыми поясами
- сохранить часовой пояс в виде отдельного столбца (если требуется)
Почему больше людей не принимают библиотеку, например date4j?