• CRON表达格式
    • 特殊字符
      • 星号(*
      • 斜线(/
      • 逗号(,
      • 连字符(-
      • 问号(?
      • 预定义的时间表
      • 间隔
    • 示例1, 基本使用
    • 示例2, 单例定时任务
    • 示例3, 日志记录功能

    gcron模块提供了对定时任务的实现,支持类似crontab的配置管理方式,并支持最小粒度到的定时任务管理。

    使用方式

    1. import "github.com/gogf/gf/g/os/gcron"

    接口文档

    https://godoc.org/github.com/gogf/gf/g/os/gcron

    简要说明:

    1. New方法用于创建自定义的定时任务管理对象;
    2. Add方法用于添加定时任务,其中:
      • pattern 参数使用CRON语法格式(具体说明见本章后续相关说明);
      • job 参数为需要执行的任务方法(方法地址);
      • name 为非必需参数,用于给定时任务指定一个唯一的名称,注意如果已存在相同名称的任务,那么添加定时任务将会失败;
    3. AddSingleton方法用于添加单例定时任务,即同时只能有一个该任务正在运行;
    4. AddOnce方法用于添加只运行一次的定时任务,当运行一次数后该定时任务自动销毁;
    5. AddTimes方法用于添加运行指定次数的定时任务,当运行times次数后该定时任务自动销毁;
    6. Entries方法用于获取当前所有已注册的定时任务信息;
    7. Remove方法用于根据名称删除定时任务(停止并删除);
    8. Search方法用于根据名称进行定时任务搜索(返回定时任务*Entry对象指针);
    9. Start方法用于启动定时任务(Add后自动启动定时任务), 可通过name参数指定需要启动的任务名称;
    10. Stop方法用于停止定时任务(Remove会停止并删除), 可通过name参数指定需要停止的任务名称;
    11. Close方法用于关闭自定义的定时任务管理对象;

    CRON表达格式

    cron表达式表示一组时间,使用6个空格分隔的字段。

    1. Field name | Allowed values | Allowed special characters
    2. ---------- | -------------- | --------------------------
    3. Seconds | 0-59 | * / , -
    4. Minutes | 0-59 | * / , -
    5. Hours | 0-23 | * / , -
    6. Day | 1-31 | * / , - ?
    7. Month | 1-12 or JAN-DEC | * / , -
    8. Week | 0-6 or SUN-SAT | * / , - ?

    注意:月份和星期几字段值不区分大小写。 “SUN”,“Sun”,和“sun”同样被接受。

    特殊字符

    星号(*

    星号表示cron表达式将匹配所有的值。例如,在第五个字段(Month)中使用星号表示每个月。

    斜线(/

    斜杠用于描述范围的增量。例如:第二个字段使用3-59/15表示每小时的第3分钟开始到第59分钟,每隔15分钟执行。

    逗号(,

    逗号用于分隔列表的项目。例如,第五个字段使用MON,WED,FRI将指每周一,周三和周五执行。

    连字符(-

    连字符用于定义范围。例如,第三个字段使用9-17表示每天上午9点至下午5点(含)。

    问号(?

    可以使用问号而不是*来让DayWeek字段为空。

    预定义的时间表

    您可以使用几个预定义的时间来代替cron表达式。

    1. Entry | Description | Equivalent To
    2. ----- | ----------- | -------------
    3. @yearly (or @annually) | Run once a year, midnight, Jan. 1st | 0 0 0 1 1 *
    4. @monthly | Run once a month, midnight, first of month | 0 0 0 1 * *
    5. @weekly | Run once a week, midnight between Sat/Sun | 0 0 0 * * 0
    6. @daily (or @midnight) | Run once a day, midnight | 0 0 0 * * *
    7. @hourly | Run once an hour, beginning of hour | 0 0 * * * *

    间隔

    您还可以定义任务以固定的时间间隔执行,从添加时开始运行。这可以通过格式化cron规范来支持,如下所示:

    1. @every <duration>

    其中durationtime.ParseDuration接受的字符串(http://golang.org/pkg/time/#ParseDuration)。

    例如,@every 1h30m10s将表示添加任务之后每隔1小时30分10秒执行。

    注意:间隔不会考虑任务的执行时间。例如,如果一项工作需要3分钟才能执行完成,并且计划每隔5分钟运行一次,那么每次任务之间只有2分钟的空闲时间。

    示例1, 基本使用

    1. package main
    2. import (
    3. "github.com/gogf/gf/g"
    4. "github.com/gogf/gf/g/os/gcron"
    5. "github.com/gogf/gf/g/os/glog"
    6. "time"
    7. )
    8. func main() {
    9. gcron.Add("0 30 * * * *", func() { glog.Println("Every hour on the half hour") })
    10. gcron.Add("* * * * * *", func() { glog.Println("Every second") }, "second-cron")
    11. gcron.Add("@hourly", func() { glog.Println("Every hour") })
    12. gcron.Add("@every 1h30m", func() { glog.Println("Every hour thirty") })
    13. g.Dump(gcron.Entries())
    14. time.Sleep(3*time.Second)
    15. gcron.Stop("second-cron")
    16. time.Sleep(3*time.Second)
    17. gcron.Start("second-cron")
    18. time.Sleep(3*time.Second)
    19. }

    执行后,输出结果为:

    1. [
    2. {
    3. "Spec": "0 30 * * * *",
    4. "Cmd": "main.main.func1",
    5. "Time": "2018-10-25T10:05:28.898768522+08:00",
    6. "Name": "",
    7. "Status": {}
    8. },
    9. {
    10. "Spec": "* * * * * *",
    11. "Cmd": "main.main.func2",
    12. "Time": "2018-10-25T10:05:28.898773631+08:00",
    13. "Name": "second-cron",
    14. "Status": {}
    15. },
    16. {
    17. "Spec": "@hourly",
    18. "Cmd": "main.main.func3",
    19. "Time": "2018-10-25T10:05:28.89885461+08:00",
    20. "Name": "",
    21. "Status": {}
    22. },
    23. {
    24. "Spec": "@every 1h30m",
    25. "Cmd": "main.main.func4",
    26. "Time": "2018-10-25T10:05:28.89885883+08:00",
    27. "Name": "",
    28. "Status": {}
    29. }
    30. ]
    31. 2018-10-25 10:05:29.000 Every second
    32. 2018-10-25 10:05:30.000 Every second
    33. 2018-10-25 10:05:31.000 Every second
    34. 2018-10-25 10:05:35.000 Every second
    35. 2018-10-25 10:05:36.000 Every second
    36. 2018-10-25 10:05:37.000 Every second

    示例2, 单例定时任务

    单例定时任务,即同时只能有一个该任务正在运行。当第二个相同的定时任务触发执行时,如果发现已有该任务正在执行,第二个任务将会退出不执行,定时器将会继续等待下一次定时任务的触发检测,以此类推。可以使用AddSingleton添加单例定时任务。

    1. package main
    2. import (
    3. "github.com/gogf/gf/g/os/gcron"
    4. "github.com/gogf/gf/g/os/glog"
    5. "time"
    6. )
    7. func main() {
    8. gcron.AddSingleton("* * * * * *", func() {
    9. glog.Println("doing")
    10. time.Sleep(2*time.Second)
    11. })
    12. select { }
    13. }

    执行后,输出结果为:

    1. 2019-01-16 22:49:27.699 doing
    2. 2019-01-16 22:49:30.696 doing
    3. 2019-01-16 22:49:33.699 doing
    4. ...

    示例3, 日志记录功能

    gcron支持日志记录功能,并可设置日志输出的文件以及级别。默认情况下仅会输出LEVEL_WARN | LEVEL_ERRO | LEVEL_CRIT错误级别的日志(包括定时任务运行异常日志),运行日志以LEVEL_DEBUG的级别进行记录,因此默认不会记录。相关方法:

    1. func SetLogPath(path string)
    2. func SetLogLevel(level int)
    3. func GetLogPath() string
    4. func GetLogLevel() int

    使用示例:

    1. package main
    2. import (
    3. "github.com/gogf/gf/g/os/gcron"
    4. "github.com/gogf/gf/g/os/glog"
    5. "time"
    6. )
    7. func main() {
    8. gcron.SetLogLevel(glog.LEVEL_ALL)
    9. gcron.Add("* * * * * ?", func() {
    10. glog.Println("test")
    11. })
    12. time.Sleep(3 * time.Second)
    13. }

    执行后,终端输出结果为:

    1. 2019-04-08 23:29:10.119 [DEBU] [gcron] gcron-1(* * * * * ?) main.main.func1 start
    2. 2019-04-08 23:29:10.119 test
    3. 2019-04-08 23:29:10.120 [DEBU] [gcron] gcron-1(* * * * * ?) main.main.func1 end
    4. 2019-04-08 23:29:11.119 [DEBU] [gcron] gcron-1(* * * * * ?) main.main.func1 start
    5. 2019-04-08 23:29:11.119 test
    6. 2019-04-08 23:29:11.119 [DEBU] [gcron] gcron-1(* * * * * ?) main.main.func1 end