redb.Route.Quartz
4.3.0
Prefix Reserved
dotnet add package redb.Route.Quartz --version 4.3.0
NuGet\Install-Package redb.Route.Quartz -Version 4.3.0
<PackageReference Include="redb.Route.Quartz" Version="4.3.0" />
<PackageVersion Include="redb.Route.Quartz" Version="4.3.0" />
<PackageReference Include="redb.Route.Quartz" />
paket add redb.Route.Quartz --version 4.3.0
#r "nuget: redb.Route.Quartz, 4.3.0"
#:package redb.Route.Quartz@4.3.0
#addin nuget:?package=redb.Route.Quartz&version=4.3.0
#tool nuget:?package=redb.Route.Quartz&version=4.3.0
redb.Route.Quartz
Quartz.NET scheduling transport for redb.Route. Cron-expression schedules and interval timers backed by the Quartz scheduler with thread pool management.
Installation
dotnet add package redb.Route.Quartz
Usage
Fluent DSL
using redb.Route.Quartz.Fluent;
// Cron schedule — every weekday at 8:00 AM
From(Cron.Schedule("daily-report", "0 0 8 ? * MON-FRI"))
.Log("Running daily report")
.To("direct://generate-report");
// Cron with thread pool
From(Cron.Schedule("batch-job", "0 */15 * * * ?").Threads(4))
.To("direct://batch-process");
// Interval timer — every 5 seconds
From(QTimer.Every("heartbeat").Period(5000).Delay(1000))
.SetBody(_ => new { status = "alive", time = DateTime.UtcNow })
.To("direct://monitor");
// Fixed-rate timer
From(QTimer.Every("metrics").Period(10000).FixedRate().Threads(2))
.To("direct://collect-metrics");
Fluent Builder API
| Category | Methods |
|---|---|
| Cron | Cron.Schedule(name, expression), .Threads(int) |
| Timer | QTimer.Every(name), .Period(ms), .Delay(ms), .FixedRate(), .Threads(int) |
Two Schemes
| Scheme | Component | Description |
|---|---|---|
cron |
CronComponent |
Cron expression scheduling (e.g., 0 0 8 ? * MON-FRI) |
qtimer |
QuartzTimerComponent |
Interval-based timer with optional initial delay |
Both schemes are consumer-only — they generate messages on schedule.
Builder methods (Threads, Period, Delay) accept both constant values and
IExpressionfor runtime resolution via the expression engine.
The scheduler of a context
As Apache Camel's QuartzComponent, each route context has one scheduler, created by its first cron:/qtimer:
consumer — a context without such a route creates none:
- an
ISchedulerhanded to the context (context.AddService(typeof(IScheduler), scheduler)) is used as it is; its host owns it; - otherwise the context builds its own, from
QuartzSchedulerOptionswhen the context or DI has them (store, cluster, serializer, thread pool), in memory without them, named{InstanceNamePrefix}-{context id}, and shuts it down when the context stops.
Either is started once the context has started — every consumer registered before the first fire (camel-quartz
autoStartScheduler); a route started later in a running context starts it at once.
// A host shares the options, not a scheduler: every context gets its own, its own job namespace and, in a clustered
// store, a cluster of the nodes that run that context.
context.AddService(typeof(QuartzSchedulerOptions), new QuartzSchedulerOptions
{
InstanceNamePrefix = "MyCluster",
Properties = new Dictionary<string, string>
{
["quartz.jobStore.type"] = "Quartz.Impl.AdoJobStore.JobStoreTX, Quartz",
["quartz.jobStore.clustered"] = "true",
// dataSource, driverDelegateType, serializer, threadPool...
},
});
A persistent store keys the scheduler by the context id, so the context needs a given id (new RouteContext("billing")):
with a generated one the scheduler name would differ on every start and every node, and starting fails with a message.
One job, one consumer
The job key is {groupName}.{jobName} — redb and the endpoint path by default (cron://nightly → redb.nightly).
It depends on the URI only, so it is the same after a restart and on every node of a cluster. On one scheduler a job key
has one consumer: a second claimant — the same path with another schedule, cron://nightly beside qtimer://nightly, two
contexts deliberately sharing one scheduler — fails at its start, naming both endpoints, instead of silently replacing the
first one's schedule. Give it its own name: another path, or jobName= / groupName=.
A persistent or clustered store
The store is shared — with this node's next start, or with the other nodes of a cluster — so a node never decides about the schedule by itself:
- stopping a route stops this node's consumer only;
deleteJob/pauseJobapply to an in-memory store (a warning when set on a persistent one); pause or remove a schedule for the cluster explicitly; - a fire taken by a node that runs no consumer for it — a rolling upgrade, a route stopped on one node — is skipped and logged once; the job stays in the store (in memory it is cleaned up, it was the process's own);
- nodes that share a scheduler name must carry the same schedules: separate roles get separate names. With a scheduler per context the cluster of a context is made of the nodes that run it;
.Cluster(true)on a Quartz route over a clustered store is a warning when a leader-only policy is attached: Quartz already fires a job on one node, and a leader-only route loses the fires the other nodes take. A host may decline the policy for Quartz routes (redb.Tsak does); the route then runs on every node.
Part of
redb.Route — ESB & EIP Framework for .NET
Tracing
On the redb.Route activity source (AddSource("redb.Route")), with redb.system = the scheme (cron, qtimer) and
redb.route.endpoint: one Consumer span per fire, {scheme} receive. A fire carries no trace context, so the span is
a root, never a child of the activity the scheduler thread holds; the route is its child. A failed route marks it an
error; our own stop does not. RouteEngineOptions.EnableTelemetry = false opens none.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 is compatible. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 is compatible. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- Quartz (>= 3.16.0)
- redb.Route (>= 4.3.0)
-
net8.0
- Quartz (>= 3.16.0)
- redb.Route (>= 4.3.0)
-
net9.0
- Quartz (>= 3.16.0)
- redb.Route (>= 4.3.0)
NuGet packages (1)
Showing the top 1 NuGet packages that depend on redb.Route.Quartz:
| Package | Downloads |
|---|---|
|
redb.Tsak.Core
Kernel of redb.Tsak — runtime container for redb.Route contexts. Provides hot-reload module loading, REST management API, scheduler, monitoring, security and pluggable cluster bootstrap. |
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 4.3.0 | 48 | 10/14/2026 |
| 4.2.3 | 86 | 10/8/2026 |
| 4.2.2 | 135 | 10/5/2026 |
| 4.2.0 | 149 | 9/30/2026 |
| 4.1.1 | 163 | 9/25/2026 |
| 4.1.0 | 157 | 9/21/2026 |
| 4.0.1 | 166 | 9/18/2026 |
| 4.0.0 | 166 | 9/11/2026 |
| 3.7.2 | 175 | 8/26/2026 |
| 3.7.1 | 185 | 8/26/2026 |
| 3.6.0 | 177 | 8/13/2026 |
| 3.5.1 | 162 | 8/9/2026 |
| 3.5.0 | 166 | 8/6/2026 |
| 3.4.0 | 173 | 7/27/2026 |
| 3.3.3 | 256 | 7/16/2026 |
| 3.3.1 | 428 | 7/10/2026 |
| 3.3.0 | 134 | 7/8/2026 |
| 3.2.0 | 223 | 6/29/2026 |
| 3.1.0 | 166 | 6/6/2026 |