kx-cron (0.1.3)
Published 2026-01-14 17:48:21 +08:00 by caisin
Installation
[registry]
default = "gitea"
[registries.gitea]
index = "sparse+ " # Sparse index
# index = " " # Git
[net]
git-fetch-with-cli = truecargo add kx-cron@0.1.3About this package
KX-Cron
A robust, flexible, and high-performance cron scheduler for Rust applications.
🚀 Features
- Robust Scheduling: Full cron expression support with timezone awareness
- Error Handling: Comprehensive error types with detailed messages
- Timeout & Retry: Built-in timeout handling and configurable retry logic
- Async & Sync: Support for both async and sync task functions
- Parallel Control: Configure whether tasks can run in parallel with themselves
- Graceful Shutdown: Clean task termination with proper resource cleanup
- Builder Pattern: Intuitive API for task configuration
- Memory Safe: No memory leaks or resource conflicts
- Thread Safe: Full concurrent access support
📦 Installation
Add this to your Cargo.toml:
[dependencies]
kx-cron = "0.1"
tokio = { version = "1.0", features = ["full"] }
anyhow = "1.0"
🏃 Quick Start
use kx_cron::prelude::*;
use std::time::Duration;
#[tokio::main]
async fn main() -> anyhow::Result<()> {
// Create scheduler
let mut scheduler = CronScheduler::new();
// Schedule a task to run every 30 seconds
let task_id = scheduler.schedule(
schedules::every_seconds(30)?
.name("heartbeat")
.timeout(Duration::from_secs(5))?
.build(),
|| async {
println!("Heartbeat!");
Ok(())
}
).await?;
// Let it run
tokio::time::sleep(Duration::from_secs(120)).await;
// Graceful shutdown
scheduler.shutdown().await?;
Ok(())
}
📚 Examples
Basic Task Scheduling
use kx_cron::prelude::*;
use std::sync::{Arc, atomic::{AtomicU32, Ordering}};
let mut scheduler = CronScheduler::new();
let counter = Arc::new(AtomicU32::new(0));
let counter_clone = Arc::clone(&counter);
// Schedule every 10 seconds
let task_id = scheduler.schedule(
schedules::every_seconds(10)?.name("counter").build(),
move || {
let counter = Arc::clone(&counter_clone);
async move {
let count = counter.fetch_add(1, Ordering::SeqCst) + 1;
println!("Execution #{}", count);
Ok(())
}
}
).await?;
Advanced Configuration
use kx_cron::prelude::*;
use std::time::Duration;
let task_id = scheduler.schedule(
TaskBuilder::new()
.name("complex_task")
.schedule_str("0 */15 * * * *")? // Every 15 minutes
.timeout(Duration::from_secs(300))? // 5 minute timeout
.max_retries(3)? // Retry up to 3 times
.retry_delay(Duration::from_secs(30))? // Wait 30s between retries
.parallelizable(false) // Don't run in parallel with itself
.build(),
|| async {
// Your complex task here
heavy_computation().await?;
Ok(())
}
).await?;
Sync Functions
// Schedule a synchronous function
let task_id = scheduler.schedule_sync(
schedules::daily_at(3, 0)? // 3:00 AM daily
.name("daily_backup")
.build(),
|| {
// Synchronous backup operation
perform_backup()?;
cleanup_old_files()?;
Ok(())
}
).await?;
Schedule Builders
// Predefined schedule builders
schedules::every_seconds(30)? // Every 30 seconds
schedules::every_minutes(15)? // Every 15 minutes
schedules::every_hours(2)? // Every 2 hours
schedules::daily_at(9, 30)? // Daily at 9:30 AM
schedules::weekly_on(1, 8, 0)? // Mondays at 8:00 AM
schedules::monthly_on(1, 0, 0)? // 1st of month at midnight
// Custom cron expressions
TaskBuilder::new()
.schedule_str("0 0 12 * * MON-FRI")? // Weekdays at noon
.build()
Task Management
// Get scheduler info
let active_count = scheduler.active_task_count()?;
let tasks = scheduler.list_tasks()?;
for task in tasks {
println!("Task {}: '{}' (running: {})",
task.id, task.name, task.is_running);
}
// Cancel specific task
let cancelled = scheduler.cancel_task(task_id)?;
// Graceful shutdown with timeout
scheduler.shutdown_with_timeout(Duration::from_secs(30)).await?;
Error Handling
use kx_cron::{CronError, Result};
// Handle different error types
match scheduler.schedule(config, task_fn).await {
Ok(task_id) => println!("Task scheduled: {}", task_id),
Err(CronError::InvalidExpression { expression, .. }) => {
eprintln!("Invalid cron expression: {}", expression);
}
Err(CronError::SchedulerStopped) => {
eprintln!("Scheduler is already stopped");
}
Err(e) => eprintln!("Other error: {}", e),
}
Timezone Support
use kx_cron::{set_timezone_utc, timezone::timezones};
// Set timezone globally
set_timezone_utc(8)?; // UTC+8 (Beijing)
set_timezone_utc(-5)?; // UTC-5 (EST)
// Use predefined timezones
let tz = timezones::cst_china()?; // China Standard Time
🔧 Configuration Options
TaskBuilder Methods
.name(name)- Set task name for logging.schedule_str(cron)- Set cron expression.schedule(schedule)- Set cron Schedule object.timeout(duration)- Set execution timeout.max_retries(n)- Set retry attempts (max 10).retry_delay(duration)- Set delay between retries.parallelizable(bool)- Allow parallel execution
Predefined Schedules
every_seconds(1-60)- Every N secondsevery_minutes(1-60)- Every N minutesevery_hours(1-24)- Every N hoursdaily_at(hour, minute)- Daily at specific timeweekly_on(day, hour, minute)- Weekly (1=Monday, 7=Sunday)monthly_on(day, hour, minute)- Monthly on specific day
🚨 Error Types
pub enum CronError {
InvalidExpression { expression: String, source: Error },
Timeout { task_id: u64, timeout_seconds: u64 },
TaskNotFound { task_id: u64 },
TaskExecutionFailed { task_id: u64, source: anyhow::Error },
SchedulerStopped,
TimezoneError { message: String },
SpawnFailed { task_id: u64, source: tokio::task::JoinError },
LockPoisoned { message: String },
InvalidConfiguration { field: String, value: String, reason: String },
}
⚡ Performance
- Zero-cost abstractions - No runtime overhead when not using features
- Efficient scheduling - Uses tokio's async runtime for optimal performance
- Memory efficient - Minimal memory footprint with proper cleanup
- Scalable - Handle hundreds of concurrent tasks
🛡️ Safety
- Memory safe - No unsafe code, prevents memory leaks
- Thread safe - All operations are thread-safe
- Panic safe - Isolated task panics don't affect scheduler
- Resource cleanup - Proper cleanup on shutdown
📖 Cron Expression Format
Standard cron format with seconds:
┌───────────── second (0 - 59)
│ ┌───────────── minute (0 - 59)
│ │ ┌───────────── hour (0 - 23)
│ │ │ ┌───────────── day of month (1 - 31)
│ │ │ │ ┌───────────── month (1 - 12)
│ │ │ │ │ ┌───────────── day of week (0 - 6) (Sunday to Saturday)
│ │ │ │ │ │
│ │ │ │ │ │
* * * * * *
Special Values
*- Any value*/n- Every n unitsn-m- Range from n to mn,m,o- Specific values n, m, and o@yearly- Once a year (0 0 0 1 1 *)@monthly- Once a month (0 0 0 1 * *)@weekly- Once a week (0 0 0 * * 0)@daily- Once a day (0 0 0 * * *)@hourly- Once an hour (0 0 * * * *)
🤝 Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
📝 License
This project is licensed under the MIT License - see the LICENSE file for details.
🔗 Links
Dependencies
| ID | Version |
|---|---|
| anyhow | ^1 |
| chrono | ^0.4 |
| cron | ^0.15.0 |
| serde | ^1 |
| serde_json | ^1.0.140 |
| thiserror | ^2 |
| tokio | ^1 |
| tracing | ^0.1 |
| tracing-test | ^0.2 |
Details
2026-01-14 17:48:21 +08:00
Assets (1)
Versions (1)
View all
Cargo
3
Caisin
Caisin
29 KiB
kx-cron-0.1.3.crate
29 KiB
0.1.3
2026-01-14