Как создать период повторения rschedule со сдвигом во времени

Я использую rSchedule для создания интервалов рабочего времени. Но часовой пояс игнорируется. Как я могу достичь этого?

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

const input = {
  workingHours:[{start:9, end:12}, {start:13, end:18}], 
  timeZone:'Europe/Berlin'
};

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

import { Schedule } from "@rschedule/core/generators";
import '@rschedule/moment-tz-date-adapter/setup';
import moment from 'moment-timezone';

const schedule = new Schedule({
      rrules: [
        {
          frequency: "MONTHLY",//frequency: "WEEKLY",
          //byDayOfWeek: ["MO", 'TU', 'WE', 'TH', 'FR'],
          duration:1000 * 60 * 60 * 3,//input.workingHours[0].end-input.workingHours[0].start,
          byHourOfDay:[12],//input.workingHours[0].end
          timezone:'Europe/Berlin',//input.timeZone,

          start: moment(Date.UTC(2019, 0, 1)),
          end: moment(Date.UTC(2020, 0, 0))
        }
      ]
    });

    schedule.occurrences().toArray().forEach(adapter => {
      console.log(
          {
            start: adapter.date.toISOString(),
            end: adapter.end.toISOString(),
          }
        )
    })

Вывод без учета часового пояса:

 { start: '2019-01-01T09:00:00.000Z', end: '2019-01-01T12:00:00.000Z' }
 { start: '2019-02-01T09:00:00.000Z', end: '2019-02-01T12:00:00.000Z' }
 { start: '2019-03-01T09:00:00.000Z', end: '2019-03-01T12:00:00.000Z' }
 { start: '2019-04-01T09:00:00.000Z', end: '2019-04-01T12:00:00.000Z' }
 { start: '2019-05-01T09:00:00.000Z', end: '2019-05-01T12:00:00.000Z' }
 { start: '2019-06-01T09:00:00.000Z', end: '2019-06-01T12:00:00.000Z' }
 { start: '2019-07-01T09:00:00.000Z', end: '2019-07-01T12:00:00.000Z' }
 { start: '2019-08-01T09:00:00.000Z', end: '2019-08-01T12:00:00.000Z' }
 { start: '2019-09-01T09:00:00.000Z', end: '2019-09-01T12:00:00.000Z' }
 { start: '2019-10-01T09:00:00.000Z', end: '2019-10-01T12:00:00.000Z' }
 { start: '2019-11-01T09:00:00.000Z', end: '2019-11-01T12:00:00.000Z' }
 { start: '2019-12-01T09:00:00.000Z', end: '2019-12-01T12:00:00.000Z' }

Ожидаемый результат:

{ start: '2019-01-01T11:00:00.000Z', end: '2019-01-01T14:00:00.000Z' },
{ start: '2019-02-01T11:00:00.000Z', end: '2019-02-01T14:00:00.000Z' },
{ start: '2019-03-01T11:00:00.000Z', end: '2019-03-01T14:00:00.000Z' },
{ start: '2019-04-01T10:00:00.000Z', end: '2019-04-01T13:00:00.000Z' },
{ start: '2019-05-01T10:00:00.000Z', end: '2019-05-01T13:00:00.000Z' },
{ start: '2019-06-01T10:00:00.000Z', end: '2019-06-01T13:00:00.000Z' },
{ start: '2019-07-01T10:00:00.000Z', end: '2019-07-01T13:00:00.000Z' },
{ start: '2019-08-01T10:00:00.000Z', end: '2019-08-01T13:00:00.000Z' },
{ start: '2019-09-01T10:00:00.000Z', end: '2019-09-01T13:00:00.000Z' },
{ start: '2019-10-01T10:00:00.000Z', end: '2019-10-01T13:00:00.000Z' },
{ start: '2019-11-01T11:00:00.000Z', end: '2019-11-01T14:00:00.000Z' },
{ start: '2019-12-01T11:00:00.000Z', end: '2019-12-01T14:00:00.000Z' }

person Mehmet Aydoğdu    schedule 08.11.2019    source источник
comment
Потому что в данный момент вы не установили часовой пояс. Вы звоните moment без установленного tz.   -  person Jorge Fuentes González    schedule 09.11.2019


Ответы (1)


Поскольку я не знаком с этими часовыми поясами (и не знаю, в каком часовом поясе должен находиться «ожидаемый результат»), немного неясно, что вы ожидаете. Но, как отметил в комментарии @JorgeFuentesGonzález, проблема вероятно заключается в том, что вы не указываете дату и время start в правильном часовом поясе.

Как указано в исходный код rSchedule (который должен удобно отображаться в виде всплывающей подсказки в таких редакторах, как VSCode -- edit я пошел дальше и разъяснил это также в документах rSchedule ), параметр конфигурации timezone для Rule объектов не изменяет часовой пояс, в котором находится правило, а изменяет часовой пояс, в котором отображается правило. Это различие важно для внутреннего функционирования rSchedule. , но я вижу в этом случае непонятно.

Таким образом, ваше правило генерирует вхождения в вашем местном часовом поясе (поскольку start: moment(Date.UTC(2019, 0, 1)) генерирует локальный moment), а затем эти вхождения преобразуются в часовой пояс 'Europe/Berlin' перед выводом. Кроме ожидания! Это не то, что происходит. Этот Rule является частью Schedule, поэтому именно часовой пояс расписания определяет выходной часовой пояс вхождений. Кажется, что в расписании нет часового пояса (поэтому он указан в местном часовом поясе). Поэтому я думаю, что правило находится в местном часовом поясе, а выходные даты - в местном часовом поясе.

  • Примечание: ведение журнала консоли с использованием toISOString() может скрывать тот факт, что выходные даты указаны в вашем местном часовом поясе, а не в ожидаемом часовом поясе.

В зависимости от того, чего вы пытаетесь достичь, я бы предложил что-то вроде следующего:

import { Schedule } from "@rschedule/core/generators";
import '@rschedule/moment-tz-date-adapter/setup';
import moment from 'moment-timezone';

const schedule = new Schedule({
  rrules: [
    {
      frequency: "MONTHLY",//frequency: "WEEKLY",
      duration:1000 * 60 * 60 * 3,//input.workingHours[0].end-input.workingHours[0].start,
      byHourOfDay:[12],//input.workingHours[0].end
      start: moment.tz(Date.UTC(2019, 0, 1), 'Europe/Berlin'),
      end: moment.tz(Date.UTC(2020, 0, 0), 'Europe/Berlin')
    }
  ],
  timezone:'Europe/Berlin'
});

демонстрация Codesandbox здесь.

Дайте мне знать, если вы все еще не видите то, что ожидаете.

person John    schedule 08.11.2019
comment
Ваше предложение сработало, спасибо @john. Дата вывода указана в формате UTC, так как я использовал date.toISOString(). В качестве комментария в качестве одного из первых пользователей библиотеки rschedule я увидел правило rschedule как интерфейс/контракт для создания дат повторения (миллисекунд с начала эпохи) независимо от выходного часового пояса. Потому что легко изменить формат вывода и часовой пояс с помощью других библиотек. Итак, я ожидал, что начало и конец снова будут миллисекундами с эпохи, а поле часового пояса будет обрабатывать сдвиги времени при генерации повторений. - person Mehmet Aydoğdu; 09.11.2019
comment
Миллисекунды с начала эпохи — это часовой пояс UTC. Если бы rSchedule обрабатывал только даты в формате UTC, он бы игнорировал сдвиги на летнее время. - person John; 09.11.2019