Документация

Слои ротации

Версия v2.3.1 · Обновлено

Слои ротации#

Слои ротации позволяют одной ротации содержать несколько правил расписания.

Используйте слои, когда одной линии дежурства нужны разные окна покрытия, например:

  • рабочие часы;
  • ночи;
  • выходные;
  • основное и резервное дежурство;
  • региональные расписания с разными часовыми поясами.

Базовая модель#

Rotation

Layer: Business hours
Members:
  Ivan   position 0
  Petr   position 1
  Anna   position 2
Restrictions:
  Monday-Friday 09:00-18:00

Layer: Nights
Members:
  Petr   position 0
  Anna   position 1
  Ivan   position 2
Restrictions:
  Monday-Friday 18:00-09:00

Layer: Weekend
Members:
  Anna   position 0
  Ivan   position 1
  Petr   position 2
Restrictions:
  Saturday-Sunday 00:00-00:00

Ротация выдаёт одного итогового дежурного пользователя на заданный момент времени.

Поля слоя#

Слой имеет:

  • название;
  • приоритет;
  • флаг включения;
  • дату/время начала;
  • тип ротации: ежедневная, еженедельная или пользовательская;
  • время передачи дежурства;
  • день недели передачи для еженедельных ротаций;
  • часовой пояс;
  • упорядоченные периоды членства;
  • необязательные ограничения.

Периоды членства#

Участники слоя хранятся как периоды членства.

Период членства имеет:

  • пользователя;
  • позицию;
  • starts_at;
  • ends_at;
  • флаг active.
Ivan:
  position: 0
  starts_at: 2026-06-01 09:00
  ends_at:   2026-06-05 12:00

Ivan:
  position: 2
  starts_at: 2026-06-10 09:00
  ends_at:   null

Это означает, что Иван участвовал в слое в течение первого периода, отсутствовал между периодами, а затем присоединился снова уже как новый период.

Добавление участника слоя#

При добавлении пользователя в слой вы можете задать starts_at.

{
  "user_id": 42,
  "position": 2,
  "starts_at": "2026-06-10T09:00:00"
}

Если starts_at не указан, IncidentRelay использует текущее время.

Если starts_at не содержит смещения часового пояса, IncidentRelay интерпретирует его как местное время в часовом поясе слоя и сохраняет внутренне в UTC.

Пример:

Layer timezone: Europe/Moscow
starts_at from UI/API: 2026-06-10T09:00:00
stored UTC value:      2026-06-10T06:00:00

Удаление участника слоя#

Удаление участника слоя не удаляет исторические данные.

Вместо этого IncidentRelay закрывает текущий период членства:

active = false
ends_at = current time

Прошлые смены остаются видимыми в календаре.

Будущие смены рассчитываются без этого участника.

Повторное добавление удалённого пользователя#

Повторное добавление того же пользователя создаёт новый период членства.

IncidentRelay не открывает заново старый период и не переписывает историю.

Old period:
  Ivan starts_at=2026-06-01 09:00
  Ivan ends_at=2026-06-05 12:00

New period:
  Ivan starts_at=2026-06-10 09:00
  Ivan ends_at=null

Поведение календаря:

before 2026-06-05 12:00     Ivan may be shown
2026-06-05 to 2026-06-10    Ivan is not part of the layer
after 2026-06-10 09:00      Ivan may be shown again

Позиции участников#

Участники сменяются в порядке позиций.

Position 0: Ivan
Position 1: Petr
Position 2: Anna

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

Для исторической корректности IncidentRelay закрывает старый период членства и создаёт новый с новой позицией.

Ограничения#

Ограничения определяют, когда слой активен.

Если у слоя нет ограничений, он активен круглосуточно.

Примеры:

Monday-Friday 09:00-18:00
Monday-Friday 18:00-09:00
Saturday 00:00-00:00
Sunday 00:00-00:00

00:00-00:00 означает полный день.

Ограничения интерпретируются в часовом поясе слоя.

Приоритет#

Если несколько слоёв активны одновременно, побеждает слой с более высоким приоритетом.

Пример:

Business hours: priority 10
Weekend:        priority 30

Если совпадают оба, побеждает Weekend, потому что у него более высокий приоритет.

Переопределения#

Переопределения всегда побеждают расчёт по слоям.

Итоговый порядок:

override > highest-priority active layer > no assignment

Поведение часового пояса#

Используйте часовой пояс слоя для повторяющихся правил и значений starts_at участников из интерфейса.

Пример:

Timezone: Europe/Berlin
Restriction: Monday-Friday 09:00-18:00
Member starts_at: 2026-06-10 09:00

И ограничение, и время начала участника означают местное берлинское время.

Смещения UTC могут меняться из-за перехода на летнее время.

Рекомендуемые практики#

  • Используйте одну ротацию для одной линии дежурства.
  • Используйте слои для разных окон активности внутри одной линии дежурства.
  • Используйте отдельные ротации, когда нужны отдельные календари, например для основного и резервного дежурства.
  • Держите приоритеты разнесёнными, например 10, 20, 30.
  • Используйте starts_at, когда пользователь должен присоединиться к расписанию в будущем.
  • Удаляйте участников вместо удаления пользователей, если хотите сохранить историю расписания.
  • Проверяйте итоговый результат в календаре после изменения участников, ограничений, времени передачи дежурства или часового пояса.