В Moment.js работа с длительностями реализована через объект
Duration, создаваемый с помощью
moment.duration(). Длительность представляет собой
промежуток времени, не привязанный к конкретной дате или времени, и
позволяет извлекать значения в различных единицах измерения.
Ключевая особенность работы с длительностями заключается в том, что одни и те же данные могут быть представлены в разных масштабах: от миллисекунд до лет, при этом часть единиц является условной (например, месяцы и годы зависят от контекста календаря).
Получение значений длительности начинается с её создания:
const duration = moment.duration(5000); // 5000 миллисекунд
Также поддерживаются альтернативные формы:
moment.duration(2, 'hours');
moment.duration({ hours: 2, minutes: 30 });
moment.duration('PT2H30M'); // ISO 8601
После создания объекта становится доступен набор методов для извлечения значений в нужных единицах.
Moment.js предоставляет методы, возвращающие количество целых единиц времени, содержащихся в длительности.
const duration = moment.duration(125000); // 125000 ms
duration.milliseconds(); // 125000
duration.seconds(); // 125
duration.minutes(); // 2
Каждый метод возвращает значение без остатка в рамках собственной единицы измерения. При этом важно учитывать, что методы не пересчитывают длительность полностью, а извлекают компонент.
Пример:
const duration = moment.duration(90, 'seconds');
duration.seconds(); // 30
duration.minutes(); // 1
Здесь 90 секунд разбиваются на 1 минуту и 30 секунд, но каждый метод возвращает только «свою» часть.
const duration = moment.duration(3700, 'seconds');
duration.seconds(); // 40
duration.minutes(); // 1
duration.hours(); // 1
Поведение аналогично: каждый метод возвращает остаток в пределах своей единицы, не учитывая «перенос» в более крупные значения.
Для получения общего количества часов используется другой подход.
Метод as() возвращает общую длительность, выраженную в
заданной единице измерения.
const duration = moment.duration(3, 'hours');
duration.as('minutes'); // 180
duration.as('seconds'); // 10800
В отличие от методов .hours() или
.minutes(), здесь выполняется полное преобразование всей
длительности без остаточного деления.
Типичные варианты использования:
duration.as('milliseconds');
duration.as('seconds');
duration.as('minutes');
duration.as('hours');
duration.as('days');
duration.as('weeks');
duration.as('years');
Метод get() позволяет извлекать значения по ключу,
аналогично объектной модели.
const duration = moment.duration(2, 'days');
duration.get('days'); // 2
duration.get('hours'); // 0
duration.get('milliseconds'); // 0
Допустимые ключи включают:
yearsmonthsweeksdayshoursminutessecondsmillisecondsОсобенность заключается в том, что get() возвращает
внутренние компоненты хранения, а не пересчитанное значение.
Moment.js хранит длительность в виде набора значений по единицам, не выполняя автоматической нормализации в единую шкалу.
const duration = moment.duration({
hours: 1,
minutes: 120
});
duration.hours(); // 1
duration.minutes(); // 0
duration.asHours(); // 3
Здесь видно различие между компонентным и агрегированным представлением.
Метод toObject() возвращает структурированное
представление всех единиц времени:
const duration = moment.duration({
days: 2,
hours: 5,
minutes: 10
});
duration.toObject();
Результат:
{
years: 0,
months: 0,
weeks: 0,
days: 2,
hours: 5,
minutes: 10,
seconds: 0,
milliseconds: 0
}
Это представление удобно для сериализации или дальнейшей обработки.
Месяцы и годы в Moment.js считаются условными единицами, так как их продолжительность зависит от календаря.
const duration = moment.duration(1, 'year');
duration.asDays(); // примерно 365
Однако точное значение может варьироваться:
Поэтому методы .months() и .years()
работают как компонентные значения, а .as() — как
приблизительное преобразование.
Базовая единица хранения в Moment.js — миллисекунды. Метод
valueOf() возвращает числовое представление
длительности:
const duration = moment.duration(1500, 'milliseconds');
duration.valueOf(); // 1500
Этот метод используется при арифметических операциях:
const total = +moment.duration(2, 'seconds');
Результатом будет число миллисекунд.
Для понимания извлечения значений важно различать два подхода:
duration.hours()duration.minutes()duration.seconds()Возвращают остаток внутри единицы.
duration.asHours()duration.asMinutes()duration.asSeconds()Возвращают полное значение всей длительности.
const duration = moment.duration(1, 'hours')
.add(45, 'minutes')
.add(30, 'seconds');
duration.hours(); // 1
duration.minutes(); // 45
duration.seconds(); // 30
duration.asMinutes(); // 105.5
Компонентные методы отражают структуру, агрегированные — общую величину.
При создании длительности из строки ISO 8601:
const duration = moment.duration('P2DT3H4M');
Доступ к значениям осуществляется аналогично:
duration.days(); // 2
duration.hours(); // 3
duration.minutes(); // 4
И агрегированное значение:
duration.asHours(); // 51
При извлечении значений следует учитывать:
const duration = moment.duration(1.5, 'hours');
duration.hours(); // 1
duration.minutes(); // 30
Компоненты не показывают дробную часть, она распределяется по младшим единицам.
Длительности могут быть отрицательными:
const duration = moment.duration(-90, 'seconds');
duration.seconds(); // 30
duration.asSeconds(); // -90
Компонентные методы могут возвращать положительные остатки, тогда как агрегированные сохраняют знак.
При преобразовании длительности в различные единицы применяется математическое деление:
const duration = moment.duration(2000, 'seconds');
duration.asMinutes(); // 33.333...
Округление не выполняется автоматически, результат сохраняет точность с плавающей точкой.
Система извлечения значений длительности в Moment.js строится на двух принципах:
Это позволяет использовать длительности как для точных вычислений, так и для представления человекочитаемых временных интервалов без дополнительной конвертации.