DEV Community

Jitendra
Jitendra

Posted on

Cron expression parser for Golang

GitHub logo adhocore / gronx

Lightweight, fast and dependency-free Cron expression parser (due checker, next/prev due date finder), task runner, job scheduler and/or daemon for Golang (tested on v1.13+) and standalone usage. If you are bold, use it to replace crontab entirely.

adhocore/gronx

Latest Version Software License Go Report Test Lint Codecov Support Tweet

gronx is Golang cron expression parser ported from adhocore/cron-expr with task runner and daemon that supports crontab like task list file. Use it programatically in Golang or as standalone binary instead of crond. If that's not enough, you can use gronx to find the next (NextTick()) or previous (PrevTick()) run time of an expression from any arbitrary point of time.

  • Zero dependency.
  • Very fast because it bails early in case a segment doesn't match.
  • Built in crontab like daemon.
  • Supports time granularity of Seconds.

Find gronx in pkg.go.dev.

Installation

go get -u github.com/adhocore/gronx
Enter fullscreen mode Exit fullscreen mode

Usage

import (
    "time"
    "github.com/adhocore/gronx"
)

gron := gronx.New()
expr := "* * * * *"

// check if expr is even valid, returns bool
gron.IsValid(expr) // true

// check if expr is due for current time, returns bool and error
gron.
Enter fullscreen mode Exit fullscreen mode

Installation



go get -u github.com/adhocore/gronx


Enter fullscreen mode Exit fullscreen mode

Usage



import (
    "time"

    "github.com/adhocore/gronx"
)

gron := gronx.New()
expr := "* * * * *"

// check if expr is even valid, returns bool
gron.IsValid(expr) // true

// check if expr is due for current time, returns bool and error
gron.IsDue(expr) // true|false, nil

// check if expr is due for given time
gron.IsDue(expr, time.Date(2021, time.April, 1, 1, 1, 0, 0, time.UTC)) // true|false, nil


Enter fullscreen mode Exit fullscreen mode

In a more practical level, you would use this tool to manage and invoke jobs in app itself and not
mess around with crontab for each and every new tasks/jobs. It doesn't yet replace that but rather supplements it.
There is a plan though #1.

In crontab just put one entry with * * * * * which points to your Go entry point that uses this tool.
Then in that entry point you would invoke different tasks if the corresponding Cron expr is due.
Simple map structure would work for this.


Cron Expression

Cron expression normally consists of 5 segments viz:



<minute> <hour> <day> <month> <weekday>


Enter fullscreen mode Exit fullscreen mode

and sometimes there can be 6th segment for <year> at the end.

For each segments you can have multiple choices separated by comma:

Eg: 0,30 * * * * means either 0th or 30th minute.

To specify range of values you can use dash:

Eg: 10-15 * * * * means 10th, 11th, 12th, 13th, 14th and 15th minute.

To specify range of step you can combine a dash and slash:

Eg: 10-15/2 * * * * means every 2 minutes between 10 and 15 i.e 10th, 12th and 14th minute.

For the 3rd and 5th segment, there are additional modifiers (optional).

And if you want, you can mix them up:

5,12-20/4,55 * * * * matches if any one of 5 or 12-20/4 or 55 matches the minute.

Real Abbreviations

You can use real abbreviations for month and week days. eg: JAN, dec, fri, SUN

Tags

Following tags are available and they are converted to real cron expressions before parsing:

  • @yearly or @annually - every year
  • @monthly - every month
  • @daily - every day
  • @weekly - every week
  • @hourly - every hour
  • @5minutes - every 5 minutes
  • @10minutes - every 10 minutes
  • @15minutes - every 15 minutes
  • @30minutes - every 30 minutes
  • @always - every minute


gron.IsDue("@5minutes")

Enter fullscreen mode Exit fullscreen mode




Modifiers

Following modifiers supported

  • Day of Month / 3rd segment:
    • L stands for last day of month (eg: L could mean 29th for February in leap year)
    • W stands for closest week day (eg: 10W is closest week days (MON-FRI) to 10th date)
  • Day of Week / 5th segment:
    • L stands for last weekday of month (eg: 2L is last monday)
    • # stands for nth day of week in the month (eg: 1#2 is second sunday)

Top comments (0)