Skip to content

odo/drizzle

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

18 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Drizzle

Drizzle is a Elixir application to schedule repeated tasks.

Characteristics

  • Cron notation
  • Seconds resolution
  • Time zone support per job
  • Jobs can be updated during runtime
  • Fast-forward of time spend offline due to restarts

Configuration

This basic example tells Drizzle to output "hello" every second:

config :drizzle,
      records: [%{
        crontab: "* * * * * *",
        time_zone: :utc,
        module: IO,
        function: :puts,
        args: ["hello"]
      }]

Each record consist of different fields:

  • crontab: defines when a job is run (details here)
  • timezone: either :utc or a time zone like "Europe/Berlin"
  • module, function, args: what will be called when the matching time has come

Here is a more involved example:

config :elixir, :time_zone_database, Tz.TimeZoneDatabase

config :drizzle,
      records: [%{
        crontab: "0 20 * * Sat",
        time_zone: "Australia/Adelaide",
        module: IO,
        function: :puts,
        args: ["cheers from down under"]
      }],
      last_evaluation: (case File.read("/tmp/drizzle_time") do {:error, _} -> nil; {:ok, time} -> String.to_integer(time) end),
      evaluation_time_fun: fn(time) -> File.write!("/tmp/drizzle_time", inspect(time)) end

Here we are greeting every Saturday at 8pm Australian Central Standard Time. Please note that you need to configure a time zone DB to do this.

These keys are optional:

  • last_evaluation: the last known input to evaluation_time_fun (see below)
  • evaluation_time_fun: a function to store the time stamp of the last evaluation (see below)

Drizzle counts time in Gregorian seconds (as in DateTime.utc_now |> DateTime.to_gregorian_seconds |> elem(0)). The problem is that when the application is stopped for restarts or upgrades, some seconds might not be observed. If you use evaluation_time_fun to capture and store this time, you can later pass it to last_evaluation so Drizzle can catch up and potentially trigger jobs that where scheduled while it was out.

evaluation_time_fun will be called whenever a job is executed and every 30 seconds.

Updating cron tab

You can update the cron tab at runtime: Drizzle.update([%{ crontab: "* * * * * *", time_zone: :utc, module: IO, function: :puts, args: ["olleh"] }])

Performance

Drizzle evaluates the cron tab for each second. On a modern machine evaluating one year (31536000 seconds) for one cron tab line takes about 30 CPU seconds.

Accuracy

Drizzle tries to trigger jobs as early during the corresponding second as possible but there are no guarantees. Under heavy load, triggering might be delayed due to how scheduling works in the BEAM.

Here are typical times for triggers between 0.8ms and 16ms after the second:

~U[2026-06-01 06:10:18.003031Z]
~U[2026-06-01 06:10:19.001435Z]
~U[2026-06-01 06:10:20.001111Z]
~U[2026-06-01 06:10:21.004924Z]
~U[2026-06-01 06:10:22.000842Z]
~U[2026-06-01 06:10:23.001319Z]
~U[2026-06-01 06:10:24.016850Z]
~U[2026-06-01 06:10:25.001041Z]
~U[2026-06-01 06:10:26.000944Z]
~U[2026-06-01 06:10:27.001133Z]
~U[2026-06-01 06:10:28.001860Z]
~U[2026-06-01 06:10:29.000957Z]
~U[2026-06-01 06:10:30.000943Z]
~U[2026-06-01 06:10:31.000732Z]

Installation

If available in Hex, the package can be installed by adding drizzle to your list of dependencies in mix.exs:

def deps do
  [
    {:drizzle, "~> 0.1.0"}
  ]
end

Documentation can be generated with ExDoc and published on HexDocs. Once published, the docs can be found at https://hexdocs.pm/drizzle.

About

Elixir application to schedule repeated tasks.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages