| Crates.io | taskvisor |
| lib.rs | taskvisor |
| version | 0.0.13 |
| created_at | 2025-09-26 13:25:33.270244+00 |
| updated_at | 2026-01-07 19:14:57.414977+00 |
| description | Event-driven task orchestration with restart, backoff, and user-defined subscribers |
| homepage | |
| repository | https://github.com/soltiHQ/taskvisor |
| max_upload_size | |
| id | 1855903 |
| size | 220,182 |
[dependencies]
taskvisor = "0.0"
[dependencies]
taskvisor = { version = "0.0", features = ["controller", "logging"] }
See crates.io for the latest version.
Helps you build resilient, event-driven async systems in Rust.
It's a small orchestrator that watches over your background tasks restarting, tracking, and signaling what happens.
┌────────────┐ runs & restarts ┌──────────────┐
│ Tasks │ ◄───────────────────── │ Supervisor │
└────────────┘ └──────┬───────┘
▼
emits events
▼
┌──────────────┐
│ Subscribers │ ◄─ your listeners
└──────────────┘
Use it for long-lived jobs, controllers, or background workers that must stay alive, observable, and restart safely.
Async systems grow fast: tasks, loops, background jobs, controllers.
Eventually you need structure: who runs what, what happens on failure, how to restart safely, and how to observe it all.
Taskvisor provides that structure: a small, event-driven supervision layer that keeps async work supervised and transparent.
Runs forever, restarts automatically on each completion, and emits lifecycle events:
use tokio_util::sync::CancellationToken;
use taskvisor::{
Supervisor, TaskFn, TaskSpec, SupervisorConfig, TaskRef,
TaskError, RestartPolicy, BackoffPolicy,
};
#[tokio::main(flavor = "current_thread")]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
let sup = Supervisor::new(SupervisorConfig::default(), Vec::new());
let ping: TaskRef = TaskFn::arc("ping", |ctx: CancellationToken| async move {
if ctx.is_cancelled() {
return Err(TaskError::Canceled);
}
println!("[ping] pong");
Ok(())
});
let spec = TaskSpec::new(
ping,
RestartPolicy::Always { interval: Some(std::time::Duration::from_secs(10)) },
BackoffPolicy::default(),
None,
);
sup.run(vec![spec]).await?;
Ok(())
}
cargo run --example {{ example_name }} --features {{ features }}
| Example | Description | Features |
|---|---|---|
| subscriber.rs | Custom subscriber reacting to events | - |
| control.rs | Tasks add/remove/cancel while supervisor is running | - |
| controller.rs | Tasks example with additional admissions | controller |
controller) slot-based orchestrator with admissions: Queue, Replace, and DropIfRunning.TaskFn (your async code with CancellationToken)
├─► wrapped in TaskSpec
│ (RestartPolicy + BackoffPolicy + timeout)
└─► passed to Supervisor
├─► spawns Registry
│ └─► creates TaskActor per task
│ └─► runs TaskSpec in loop
│ └─► publishes Event to Bus
└─► Bus distributes events to:
└─► Subscribe implementations (your metrics/logs)
Optional Controller (feature-gated):
ControllerSpec ─► Controller ─► Supervisor.add_task(TaskSpec)
(admission policies: Queue/Replace/DropIfRunning)
| Feature | Description | Use when |
|---|---|---|
controller |
Enables slot-based orchestration (Controller, ControllerSpec, etc.) |
Need admission control |
logging |
Enables the built-in LogWriter, demo logger |
Debugging (Demo) |
We're open to any new ideas and contributions.
Found a bug? Have an idea? We welcome pull requests and issues.