cron icon indicating copy to clipboard operation
cron copied to clipboard

Adding entry directly

Open mewa opened this issue 5 years ago • 3 comments

At the moment adding new entries is only possible by using one of the functions:

func (c *Cron) AddFunc(spec string, cmd func()) (EntryID, error)
func (c *Cron) AddJob(spec string, cmd Job) (EntryID, error)
func (c *Cron) Schedule(schedule Schedule, cmd Job) EntryID

which delegate work to one another.

Adding another function, which accepts a raw Entry would allow certain scenarios that are impossible at the moment.

For example, if we wanted to restore a schedule from external storage where we saved the last/next execution time currently we'd have to write a separate Schedule implementation.

Even though the check would be trivial, I feel that this should belong to the cron implementation, since most of the code is already there.

I'll be glad to dontate some code since I'll be adding similar code to my fork either way.

mewa avatar Mar 13 '19 02:03 mewa

I'm not sure I fully understand the use case for accepting an Entry directly.. it seems like the Schedule and Job are indeed the only things that the user needs to / should provide. What is the scenario where the Last/Next execution time needs to be restored from storage instead of being computed from the Schedule?

robfig avatar Jun 16 '19 13:06 robfig

If I understood correctly the author wants to restart the process but keep the state of the entries, such as last execution, or even set it manually. if this is the case I am interested in this feature as well

GustavoKatel avatar Jun 05 '21 01:06 GustavoKatel

I managed to deal with this with the following:

Create a custom Schedule that wraps the default schedule so we can use use custom values when calculating the next execution time

package myPackage

import (
	"sync"
	"time"

	"github.com/robfig/cron/v3"
)

var _ cron.Schedule = (*cronScheduleCalculator)(nil)

type cronScheduleCalculator struct {
	LastRun time.Time

	BaseSchedule cron.Schedule

	HadStartedMutex sync.Mutex
	HadStarted      bool
}

func cronScheduleCalculatorNew(baseSchedule cron.Schedule, lastRun time.Time) cron.Schedule {
	return &cronScheduleCalculator{
		LastRun:         lastRun,
		BaseSchedule:    baseSchedule,
		HadStartedMutex: sync.Mutex{},
		HadStarted:      false,
	}
}

func (calc *cronScheduleCalculator) Next(time time.Time) time.Time {

	calc.HadStartedMutex.Lock()
	defer calc.HadStartedMutex.Unlock()

	if !calc.HadStarted {
		calc.HadStarted = true

		if !calc.LastRun.IsZero() {
			return calc.BaseSchedule.Next(calc.LastRun)
		}
	}

	return calc.BaseSchedule.Next(time)
}

And then use this when calling myCron.Schedule

schedule, _ := cronParser.Parse(cronExp)

schedule = cronScheduleCalculatorNew(schedule, lastRun)

entryId := myCron.Schedule(schedule, job)

GustavoKatel avatar Jun 05 '21 15:06 GustavoKatel