2016-07-04 3 views
1

저는 며칠 동안이 문제에 대한 저의 머리를 돌 렸습니다. Mongo 데이터베이스에서 예정된 시간에 문서를 가져 와서 (시간 일정없이) 문서 사본을 만들 수 있어야합니다.문서 생성을위한 반복 이벤트

예 :

일정 : 월요일, 수요일, 토요일

에 매 30 주

이 문서 :

{ 
    _id: 'abcxyz', 
    service: 'HVAC', 
    assignedTo: 'xyzabc', 
    details: 'Check HVAC System for problems' 
} 

나는 모든 다른 시간의 일정으로 문서의 군중이있을 것이다. 매월 셋째 달의 첫째 월요일 (분기 별)과 같은 것들도 있습니다.

나중에 js와 같은 것을 사용하려고했지만 나중에 30 weeks과 같은 것을 이해하지 못하는 것 같습니다. 왜냐하면 30 weeks은 일반적으로 crontab과 관련이 없기 때문입니다.

이 작업을 완료하려면 nextRunDate을 생성하고 오늘 nextRunDate 인 각 문서를 가져옵니다. 이 말을 듣고 난 다음에 nextRunDate을 계산할 필요가 있습니다. 현재 실행 날짜가 첫 번째 일 경우 힘들 것입니다. Monday 다음 실행 날짜를 30 주 대신 수요일로 계산하려면 어떻게해야합니까? 지금?

어쨌든이 문제에 대한 도움을 주신 데 대해 진심으로 감사드립니다. 위에서 말한 내용이 혼란 스럽다면 Google 캘린더 스케줄러와 매우 유사하다고 생각합니다.

Google Calendar Scheduler

답변

1

많은 라이브러리를 찾고 후 나는 momentjs 나중에-JS가 누락 부분 모두이 가능하게하는 것을 발견했다. 그러나 기능적으로 momentjs는 필요한 도구의 대부분을 제공합니다.

momentjs는 특정 요일, 즉 월요일, 특히 월 첫 번째 월요일의 맥락에서 타겟팅 할 수있는 기능이 부족했습니다.

later-js에는 every(30).weeks() 옵션이 없으므로 30 주를 예약하는 기능이 없습니다.

제 해결책은 first Monday of a month을 발견하고 다음 반복 날짜를 계산하는 방법을 만드는 것이 었습니다. 여기

코드가

// this will get the next date 2 months out on the 30th of the month 
    console.log(
    getSchedule({ 
     type: 'monthly', 
     months: 2, 
     day: 30, 
    }) 
); 
    // this will get the next date 2 months out on the first Wednesday 
    // of the month 
    console.log(
    getSchedule({ 
     type: 'monthly', 
     months: 2, 
     day: 3, 
     weekDay: true, 
    }) 
); 
    // this will get the next date 30 weeks out and if it is Monday it will 
    // instead of creating another date 30 weeks out it will create a new date 
    // for Wednesday. Once Wednesday comes it will then find the next Monday 
    // that is 30 weeks out 
    console.log(
    getSchedule({ 
     type: 'weekly', 
     weeks: 30, 
     days: [1, 3], 
     startDate: moment().add(1, 'weeks'), 
    }) 
); 
을 다음과 같이 그렇게

import moment from 'moment'; 

/** 
* Gets the first week day of type in a month 
* @param {Date} date the original date 
* @param {Number} day the day of the week we are looking for 
* @return {Date}   the new date object 
*/ 
const getFirstWeekDay = (date = new Date(), day = 0) => { 
    // set the date to the first of the month 
    date.setDate(1); 

    // Get the first weekday of the month 
    while (date.getDay() !== day) { 
    date.setDate(date.getDate() + 1); 
    } 
    // return the new date 
    return date; 
}; 

/** 
* Returns a starting point 
* @param {Date} startDate the date to start from 
* @return {moment}   a moment object 
*/ 
const start = (startDate) => moment(startDate).startOf('day'); 

/** 
* Calculates a Schedule on a weekly basis 
* @param {Date} startDate the date to start from 
* @param {Array} days  days of the week to create 
* @param {Number} weeks  number of weeks for recurrance 
* @return {Date}    the next run date 
*/ 
const weekly = ({ startDate, days, weeks }) => { 
    const today = start(startDate); 
    const index = _.indexOf(days, today.day()); 
    if (index === (days.length - 1)) { 
    return today.add(weeks, 'weeks').day(days[0]).toDate(); 
    } 

    return today.day(days[index + 1]).toDate(); 
}; 

/** 
* Calculates a Schedule on a monthly basis 
* @param {Date} startDate the date to start from 
* @param {Number} day   day of the week or month 
* @param {Number} months  number of months for recurrance 
* @param {Boolean} weekDay  starting at weekday or date 
* @return {Date}    the next run date 
*/ 
const monthly = ({ startDate, day, months, weekDay }) => { 
    const next = start(startDate).startOf('month').add(months, 'months'); 
    if (weekDay) { 
    return getFirstWeekDay(next.toDate(), day); 
    } 

    return next.date(day).toDate(); 
}; 

// register the function in a object so we can find them 
const schedules = { 
    weekly, 
    monthly, 
}; 

/** 
* Returns the next run date based on a config 
* @param {Object} config  the config for recurrence 
* @return {Date}    the next run date 
*/ 
export default (config) => schedules[config.type](config); 

당신은 이것을 사용할 수 있습니다하는 것입니다