Добавление недель

В библиотеке Luxon работа с временными интервалами построена на концепции неизменяемых объектов. Любая операция модификации даты или времени не изменяет исходный экземпляр, а возвращает новый объект. Добавление недель реализуется через метод plus, который принимает объект длительности (Duration-like object), где неделя задаётся ключом weeks.


Базовый механизм добавления недель

Основной способ увеличить дату на заданное количество недель — использование метода DateTime.plus():

import { DateTime } from "luxon";

const now = DateTime.now();
const inTwoWeeks = now.plus({ weeks: 2 });

В данном примере создаётся новый объект даты, смещённый на 14 дней вперёд (2 недели × 7 дней).

Ключевой момент: weeks в Luxon интерпретируется как календарная длительность, равная 7 дням, а не как «рабочие недели» или «недели календарной сетки с учётом месяца».


Принцип неизменяемости при добавлении недель

Каждое применение plus возвращает новый экземпляр DateTime:

const base = DateTime.local(2026, 1, 1);
const shifted = base.plus({ weeks: 3 });

console.log(base.toISO());     // исходная дата
console.log(shifted.toISO());  // дата + 21 день

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


Эквивалентность недель и дней

Добавление недель эквивалентно добавлению количества дней, кратного семи:

DateTime.now().plus({ weeks: 1 });
// эквивалентно
DateTime.now().plus({ days: 7 });

Однако использование недель предпочтительнее с точки зрения семантики, поскольку код становится более выразительным и ближе к предметной области.


Отрицательные значения и метод minus

Для вычитания недель используется либо отрицательное значение в plus, либо метод minus:

const dt = DateTime.now();

const past1 = dt.minus({ weeks: 1 });
const past2 = dt.plus({ weeks: -1 });

Обе формы эквивалентны, но minus улучшает читаемость при работе с отрицательными смещениями времени.


Работа с дробными неделями

Luxon поддерживает дробные значения длительностей, включая недели:

const dt = DateTime.now().plus({ weeks: 1.5 });

В этом случае добавляется 10.5 дней (7 × 1.5). Такой подход полезен при расчётах, связанных с планированием или моделированием временных интервалов.


Влияние часовых поясов и переходов времени

При добавлении недель учитываются локальные правила часового пояса и переходы на летнее/зимнее время.

const dt = DateTime.fromISO("2026-03-25T10:00", { zone: "Europe/Berlin" });
const shifted = dt.plus({ weeks: 1 });

Если в промежутке происходит сдвиг часового пояса (DST), Luxon корректирует локальное время так, чтобы сохранить абсолютную временную точку.

Это означает:

  • интервал в 7 дней сохраняется в UTC-эквиваленте;
  • локальное время может смещаться на ±1 час в зависимости от правил региона.

Отличие от календарных недель

Важно различать:

  • добавление weeks — строгое смещение на 7 × N дней;
  • календарные недели — логическая единица, зависящая от локали, начала недели и календарной системы.

Luxon не интерпретирует weeks как «недели месяца» или «ISO-недели». Для работы с календарными неделями используются отдельные механизмы:

DateTime.now().weekNumber;
DateTime.now().weekYear;

Эти свойства позволяют определять текущую ISO-неделю, но не участвуют напрямую в арифметике добавления времени.


Комбинирование недель с другими единицами

Метод plus принимает составные длительности:

const dt = DateTime.now().plus({
  weeks: 2,
  days: 3,
  hours: 5
});

Порядок интерпретации не влияет на результат, так как Luxon нормализует длительность внутри одного вычисления.

Особенность: если одновременно заданы недели и дни, они суммируются:

.plus({ weeks: 1, days: 7 }) // эквивалентно 2 недели

Цепочки операций

Добавление недель часто используется в цепочках преобразований:

const result = DateTime.now()
  .startOf("day")
  .plus({ weeks: 4 })
  .set({ hour: 12 });

Каждый этап возвращает новый объект, формируя предсказуемую последовательность преобразований.


Использование в планировании дат

Добавление недель применяется в типичных сценариях планирования:

  • интервалы подписки;
  • регулярные отчёты;
  • расписания задач;
  • повторяющиеся события.

Пример расчёта следующего платежа:

const nextPayment = DateTime.fromISO("2026-01-01").plus({ weeks: 2 });

Особенности округления и точности

Luxon не выполняет округление при добавлении недель. Все вычисления основаны на точном количестве миллисекунд:

  • 1 неделя = 604800000 миллисекунд;
  • дробные значения масштабируются линейно.

Это исключает накопление ошибок при последовательных операциях.


Поведение при переходе между месяцами и годами

Добавление недель может пересекать границы календарных периодов:

DateTime.fromISO("2026-12-20").plus({ weeks: 3 });

Luxon корректно пересчитывает дату, не ограничиваясь текущим месяцем или годом. Перенос осуществляется через абсолютную шкалу времени, а не через календарную сетку.


Отличие от ручного добавления дней

Хотя добавление недель эквивалентно умножению на 7 дней, использование weeks предпочтительнее:

  • уменьшает вероятность ошибок при ручных расчётах;
  • повышает читаемость кода;
  • явно отражает бизнес-логику.
// предпочтительно
plus({ weeks: 6 })

// менее выразительно
plus({ days: 42 })

Использование с форматированием результата

После добавления недель результат обычно форматируется:

const dt = DateTime.now().plus({ weeks: 1 });

console.log(dt.toISO());
console.log(dt.toFormat("dd.MM.yyyy"));

Форматирование не влияет на саму операцию добавления, но важно для представления результата.


Взаимодействие с зонами UTC

При работе с UTC поведение упрощается, так как отсутствуют переходы времени:

const dt = DateTime.utc(2026, 1, 1).plus({ weeks: 10 });

В этом случае добавление недель всегда соответствует фиксированному числу миллисекунд без локальных корректировок.


Поведение при цепочках с setZone

При смене временной зоны до или после добавления недель результат может отличаться по отображению, но не по абсолютному времени:

const dt = DateTime.fromISO("2026-01-01T10:00", { zone: "UTC" })
  .plus({ weeks: 1 })
  .setZone("Asia/Almaty");

Изменяется только интерпретация локального времени, а не момент в UTC.


Практическая модель интерпретации weeks

Внутри Luxon weeks рассматривается как часть общей модели Duration:

  • 1 week = 7 days
  • days = 24 hours
  • hours = 60 minutes

Эта модель обеспечивает согласованность между всеми единицами измерения времени и делает операции предсказуемыми независимо от контекста использования.