crontab 表達式解析庫

什麼是 cronexpr

cronexpr 是一個高級的 crontab 解析表達式的庫,用於解析比原生 crontab 更好強大的定時任務解析器,當然,這個包是不包含定時任務功能的

安裝

GO MOD 模式下,執行:

$ go get github.com/gorhill/cronexpr

案例

這個庫實際上非常簡單,我這裏拿一個小的例子來展示一下

package main

import (
 "fmt"
 "github.com/gorhill/cronexpr"
 "log"
 "testing"
 "time"
)

func TestCron(t *testing.T) {
 _,nextTimeArr := CheckCrontabExpr("* * 10 * * * *")
 for _,v := range nextTimeArr{
  fmt.Println(v)
 }
}

func CheckCrontabExpr(crontabs string) (err error, nextTimeArr []string) {
 var nextTime []time.Time
 if _, err = cronexpr.Parse(crontabs); err != nil {
  log.Fatal(err)
  return err, nil
 }
 //返回當前crontab後的5次執行,n爲次數
 nextTime = cronexpr.MustParse(crontabs).NextN(time.Now(), 5)
 for _, v := range nextTime {
  nextTimeArr = append(nextTimeArr, v.String())
 }
 return nil, nextTimeArr
}

上面的例子是打印這個 crontab 表達式 “* * 10 * * * *” 的後五次執行時間,結果如下:

=== RUN   TestCron
2021-04-27 10:00:00 +0800 CST
2021-04-27 10:00:01 +0800 CST
2021-04-27 10:00:02 +0800 CST
2021-04-27 10:00:03 +0800 CST
2021-04-27 10:00:04 +0800 CST
--- PASS: TestCron (0.01s)
PASS

由於這個 crontab 表達式的最小粒度是秒,所以我們如果要自己寫一個定時任務的話,可以用:

for{
    var now = time.now()
    nextDoCron := cronexpr.MustParse("* * 10 * * * *").Next(now)
 if cronJob.nextTime.Before(now) || cronJob.nextTime.Equal(now) 
    ......
    ......
 select {
  case <-time.NewTimer(1 * time.Second).C:
 }
}

這樣就只需要每秒檢查一次,nextDoCron 變量就是根據當前時間 time.now() 獲取到的下一次執行時間

判斷過期了或者剛好過期時,則執行 if 中的內容即可做到定時任務的功效

他的 crontab 表達式支持非常多的定義,這裏我寫個自己的總結:

/**
 創建時間:2020-07-08 11:18:24
 根據傳入的表達式,檢查表達式是否正確:

      字段名       是否強制      支持的格式      支持的特殊格式
 ----------     ----------   --------------    --------------------
 Seconds        No           0-59              * / , -
 Minutes        Yes          0-59              * / , -
 Hours          Yes          0-23              * / , -
 Day of month   Yes          1-31              * / , - L W (L指最後last,若用L,表示月底,W指的是最近的工作日)
 Month          Yes          1-12 or JAN-DEC   * / , -
 Day of week    Yes          0-6 or SUN-SAT    * / , - L # (L指最後last,若用1L,表示本月最後一週的週一)
 Year           No           1970–2099         * / , -
 
 00 */10 08-19 * * * * * 從08點到19點,每10分鐘執行一次
 2021-04-27 08:00:00 +0800 CST
 2021-04-27 08:10:00 +0800 CST
 2021-04-27 08:20:00 +0800 CST
 2021-04-27 08:30:00 +0800 CST
 2021-04-27 08:40:00 +0800 CST
 
 00 00 17 * * 1-5 * 我們公司點加班餐的定時任務推送消息 週一到週五,每天的17點推送一次
 2021-04-27 17:00:00 +0800 CST
 2021-04-28 17:00:00 +0800 CST
 2021-04-29 17:00:00 +0800 CST
 2021-04-30 17:00:00 +0800 CST
 2021-05-03 17:00:00 +0800 CST
 
*/

總結

cronexpr 庫實際上解決了我們自己去解析表達式的苦,我記得之前我用 PHP 寫過一版 crontab 表達式解析,那叫一個心驚膽戰,生怕自己寫錯造成生產事故,定時任務有很多種實現方式,這個庫只是爲我們解決了最基本也是最關鍵的表達式解析,推薦給大家,可以看看源碼喲~

還想了解更多嗎?

    更多請查看:https://github.com/gorhill/cronexpr

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/HTHr6cXSG9IR-yCNWsjS2Q