GO 实现一个定时任务调度
package task
import (
"context"
"time"
"github.com/rs/zerolog/log"
)
type ValidateTask struct {
ctx context.Context
cancel context.CancelFunc
name string
isRunning bool
}
func NewValidateTask(name string) *ValidateTask {
ctx, cancel := context.WithCancel(context.Background())
return &ValidateTask{
ctx: ctx,
cancel: cancel,
name: name,
}
}
func (t *ValidateTask) Start(interval time.Duration, task func() error) {
if t.isRunning {
log.Info().Str("scope", t.name).Msgf("任务 '%s' 已经在运行中", t.name)
return
}
t.isRunning = true
go func() {
defer func() {
t.isRunning = false
log.Info().Str("scope", t.name).Msgf("任务 '%s' 已停止", t.name)
}()
ticker := time.NewTicker(interval)
defer ticker.Stop()
for {
select {
case <-t.ctx.Done():
log.Info().Str("scope", t.name).Msgf("任务 '%s' 收到取消信号", t.name)
return
case <-ticker.C:
if err := task(); err != nil {
log.Info().Str("scope", "index").Msgf("任务 '%s' 执行失败: %v", t.name, err)
}
log.Info().Str("scope", t.name).Msgf("任务 '%s' 执行结束", t.name)
}
}
}()
}
func (t *ValidateTask) Stop() {
log.Printf("停止任务 '%s'...", t.name)
t.cancel()
}