A Golang job scheduling library that lets you run Go functions at pre-determined intervals using cron expressions, fixed durations, daily, weekly, monthly, or one-time schedules with support for distributed deployments.
Guide to understanding and managing job lifecycle in gocron.
Every job in gocron goes through distinct lifecycle phases from creation to removal.
Jobs are created using NewJob:
j, err := s.NewJob(
gocron.DurationJob(time.Minute),
gocron.NewTask(myFunc),
)At creation, gocron:
After Start(), scheduler begins tracking next run times:
s.Start()Scheduler maintains internal queue of upcoming runs.
At scheduled time, job executes:
After execution:
AfterJobRuns, AfterJobRunsWithError)Jobs can be explicitly removed:
err := s.RemoveJob(j.ID())Or removed automatically (one-time jobs after execution).
Monitor lifecycle with event listeners:
j, _ := s.NewJob(
gocron.DurationJob(time.Minute),
gocron.NewTask(myFunc),
gocron.WithEventListeners(
gocron.BeforeJobRuns(func(jobID uuid.UUID, jobName string) {
log.Printf("Starting: %s", jobName)
}),
gocron.AfterJobRuns(func(jobID uuid.UUID, jobName string) {
log.Printf("Completed: %s", jobName)
}),
gocron.AfterJobRunsWithError(func(jobID uuid.UUID, jobName string, err error) {
log.Printf("Failed: %s - %v", jobName, err)
}),
),
)[Created] --Start()--> [Scheduled] --Trigger--> [Running] --Complete--> [Scheduled]
|
+--Remove()--> [Removed]One-time jobs:
[Created] --Start()--> [Scheduled] --Trigger--> [Running] --Complete--> [Removed]// Get next run time
nextRun, err := j.NextRun()
// Get last run time
lastRun, err := j.LastRun()
// Get job name
name := j.Name()
// Get job ID
id := j.ID()// Update job (replace definition)
newJob, err := s.Update(j.ID(),
gocron.DurationJob(2*time.Minute),
gocron.NewTask(newFunc),
)// Trigger immediate execution
err := j.RunNow()s, _ := gocron.NewScheduler()
// Add jobs...
s.Start() // Begin scheduling// Graceful shutdown
err := s.Shutdown()Shutdown process:
WithStopTimeout)s, _ := gocron.NewScheduler(
gocron.WithStopTimeout(30*time.Second),
)
defer s.Shutdown()
ctx, cancel := signal.NotifyContext(context.Background(), os.Interrupt)
defer cancel()
go func() {
<-ctx.Done()
if err := s.Shutdown(); err != nil {
log.Printf("Shutdown error: %v", err)
}
}()
s.Start()
select {} // blockSpecial lifecycle for one-time jobs:
j, _ := s.NewJob(
gocron.OneTimeJob(
gocron.OneTimeJobStartDateTime(time.Now().Add(time.Hour)),
),
gocron.NewTask(initializeSystem),
)After execution, automatically removed from scheduler.
Handle context cancellation:
j, _ := s.NewJob(
gocron.DurationJob(time.Minute),
gocron.NewTask(func(ctx context.Context) {
for {
select {
case <-ctx.Done():
log.Println("Job cancelled, cleaning up...")
return
default:
doWork()
time.Sleep(time.Second)
}
}
}),
)Use SchedulerMonitor for detailed lifecycle tracking:
type myMonitor struct{}
func (m *myMonitor) JobScheduled(jobID uuid.UUID, job gocron.Job) {
log.Printf("Scheduled: %s", job.Name())
}
func (m *myMonitor) JobStarted(jobID uuid.UUID, job gocron.Job) {
log.Printf("Started: %s", job.Name())
}
func (m *myMonitor) JobCompleted(jobID uuid.UUID, job gocron.Job, err error) {
if err != nil {
log.Printf("Failed: %s - %v", job.Name(), err)
} else {
log.Printf("Completed: %s", job.Name())
}
}Install with Tessl CLI
npx tessl i tessl/golang-github-com-go-co-op-gocron-v2@2.19.1docs
api
examples
guides