kestrel_timer/
task.rs

1use std::future::Future;
2use std::pin::Pin;
3use std::sync::atomic::{AtomicU64, Ordering};
4use std::sync::Arc;
5use tokio::sync::oneshot;
6
7/// Global unique task ID generator
8/// 
9/// 全局唯一任务 ID 生成器
10static NEXT_TASK_ID: AtomicU64 = AtomicU64::new(1);
11
12/// Task Completion Reason
13///
14/// Indicates the reason for task completion, either expired or cancelled.
15/// 
16/// 任务完成原因,要么是过期,要么是取消。
17#[derive(Debug, Clone, Copy, PartialEq, Eq)]
18pub enum TaskCompletionReason {
19    /// Task expired normally
20    /// 
21    /// 任务正常过期
22    Expired,
23    /// Task was cancelled
24    /// 
25    /// 任务被取消
26    Cancelled,
27}
28
29/// Unique identifier for timer tasks
30/// 
31/// 定时器任务唯一标识符
32#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
33pub struct TaskId(u64);
34
35impl TaskId {
36    /// Generate a new unique task ID (internal use)
37    /// 
38    /// 生成一个新的唯一任务 ID (内部使用)
39    #[inline]
40    pub(crate) fn new() -> Self {
41        TaskId(NEXT_TASK_ID.fetch_add(1, Ordering::Relaxed))
42    }
43
44    /// Get the numeric value of the task ID
45    /// 
46    /// 获取任务 ID 的数值
47    #[inline]
48    pub fn as_u64(&self) -> u64 {
49        self.0
50    }
51}
52
53impl Default for TaskId {
54    #[inline]
55    fn default() -> Self {
56        Self::new()
57    }
58}
59
60/// Timer Callback Trait
61/// 
62/// Types implementing this trait can be used as timer callbacks.
63/// 
64/// 可实现此特性的类型可以作为定时器回调函数。
65/// 
66/// # Examples (示例)
67/// 
68/// ```
69/// use kestrel_timer::TimerCallback;
70/// use std::future::Future;
71/// use std::pin::Pin;
72/// 
73/// struct MyCallback;
74/// 
75/// impl TimerCallback for MyCallback {
76///     fn call(&self) -> Pin<Box<dyn Future<Output = ()> + Send>> {
77///         Box::pin(async {
78///             println!("Timer callback executed!");
79///         })
80///     }
81/// }
82/// ```
83pub trait TimerCallback: Send + Sync + 'static {
84    /// Execute callback, returns a Future
85    /// 
86    /// 执行回调函数,返回一个 Future
87    fn call(&self) -> Pin<Box<dyn Future<Output = ()> + Send>>;
88}
89
90/// Implement TimerCallback trait for closures
91/// 
92/// Supports Fn() -> Future closures, can be called multiple times, suitable for periodic tasks
93/// 
94/// 实现 TimerCallback 特性的类型,支持 Fn() -> Future 闭包,可以多次调用,适合周期性任务
95impl<F, Fut> TimerCallback for F
96where
97    F: Fn() -> Fut + Send + Sync + 'static,
98    Fut: Future<Output = ()> + Send + 'static,
99{
100    fn call(&self) -> Pin<Box<dyn Future<Output = ()> + Send>> {
101        Box::pin(self())
102    }
103}
104
105/// Callback wrapper for standardized callback creation and management
106/// 
107/// Callback 包装器,用于标准化回调创建和管理
108/// 
109/// # Examples (示例)
110/// 
111/// ```
112/// use kestrel_timer::CallbackWrapper;
113/// 
114/// let callback = CallbackWrapper::new(|| async {
115///     println!("Timer callback executed!");
116/// });
117/// ```
118#[derive(Clone)]
119pub struct CallbackWrapper {
120    callback: Arc<dyn TimerCallback>,
121}
122
123impl CallbackWrapper {
124    /// Create a new callback wrapper
125    /// 
126    /// # Parameters
127    /// - `callback`: Callback object implementing TimerCallback trait
128    /// 
129    /// # 创建一个新的回调包装器
130    /// 
131    /// # 参数
132    /// - `callback`: 实现 TimerCallback 特性的回调对象
133    /// 
134    /// # Examples (示例)
135    /// 
136    /// ```
137    /// use kestrel_timer::CallbackWrapper;
138    /// 
139    /// let callback = CallbackWrapper::new(|| async {
140    ///     println!("Timer fired!"); // 定时器触发
141    /// });
142    /// ```
143    #[inline]
144    pub fn new(callback: impl TimerCallback) -> Self {
145        Self {
146            callback: Arc::new(callback),
147        }
148    }
149
150    /// Call the callback function
151    /// 
152    /// 调用回调函数
153    #[inline]
154    pub(crate) fn call(&self) -> Pin<Box<dyn Future<Output = ()> + Send>> {
155        self.callback.call()
156    }
157}
158
159/// Completion notifier for sending notifications when tasks complete
160/// 
161/// 完成通知器,用于发送任务完成通知
162pub struct CompletionNotifier(pub oneshot::Sender<TaskCompletionReason>);
163
164/// Timer Task
165/// 
166/// Users interact via a two-step API
167/// 1. Create task using `TimerTask::new()`
168/// 2. Register task using `TimerWheel::register()` or `TimerService::register()`
169/// 
170/// 定时器任务
171/// 
172/// 用户通过两步 API 与定时器交互
173/// 1. 使用 `TimerTask::new()` 创建任务
174/// 2. 使用 `TimerWheel::register()` 或 `TimerService::register()` 注册任务
175pub struct TimerTask {
176    /// Unique task identifier
177    /// 
178    /// 唯一任务标识符
179    pub(crate) id: TaskId,
180    
181    /// User-specified delay duration
182    /// 
183    /// 用户指定的延迟时间
184    pub(crate) delay: std::time::Duration,
185    
186    /// Expiration time in ticks relative to the timing wheel
187    /// 
188    /// 相对于时间轮的过期时间(以 tick 为单位)
189    pub(crate) deadline_tick: u64,
190    
191    /// Round counter for tasks beyond the wheel's range
192    /// 
193    /// 超出时间轮范围的任务轮数计数器
194    pub(crate) rounds: u32,
195    
196    /// Async callback function, optional
197    /// 
198    /// 异步回调函数,可选
199    pub(crate) callback: Option<CallbackWrapper>,
200    
201    /// Completion notifier for sending notifications when task completes, created during registration
202    /// 
203    /// 完成通知器,用于发送任务完成通知,在注册期间创建
204    pub(crate) completion_notifier: Option<CompletionNotifier>,
205}
206
207impl TimerTask {
208    /// Create a new timer task, internal use
209    /// 
210    /// # Parameters
211    /// - `delay`: Delay duration
212    /// - `callback`: Callback function, optional
213    /// 
214    /// # Note
215    /// This is an internal method, users should use `TimerWheel::create_task()` or `TimerService::create_task()` to create tasks.
216    /// 
217    /// 
218    /// 创建一个新的定时器任务,内部使用
219    /// 
220    /// # 参数
221    /// - `delay`: 延迟时间
222    /// - `callback`: 回调函数,可选
223    /// 
224    /// # 注意
225    /// 这是一个内部方法,用户应该使用 `TimerWheel::create_task()` 或 `TimerService::create_task()` 来创建任务。
226    #[inline]
227    pub(crate) fn new(delay: std::time::Duration, callback: Option<CallbackWrapper>) -> Self {
228        Self {
229            id: TaskId::new(),
230            delay,
231            deadline_tick: 0,
232            rounds: 0,
233            callback,
234            completion_notifier: None,
235        }
236    }
237
238    /// Get task ID
239    /// 
240    /// 获取任务 ID
241    /// 
242    /// # Examples (示例)
243    /// 
244    /// ```no_run
245    /// use kestrel_timer::TimerWheel;
246    /// use std::time::Duration;
247    /// 
248    /// let task = TimerWheel::create_task(Duration::from_secs(1), None);
249    /// let task_id = task.get_id();
250    /// println!("Task ID: {:?}", task_id);
251    /// ```
252    pub fn get_id(&self) -> TaskId {
253        self.id
254    }
255
256    /// Prepare for registration (called by timing wheel during registration)
257    /// 
258    /// 准备注册(在注册期间由时间轮调用)
259    #[allow(dead_code)]
260    pub(crate) fn prepare_for_registration(
261        &mut self,
262        completion_notifier: CompletionNotifier,
263        deadline_tick: u64,
264        rounds: u32,
265    ) {
266        self.completion_notifier = Some(completion_notifier);
267        self.deadline_tick = deadline_tick;
268        self.rounds = rounds;
269    }
270
271    /// Get a clone of the callback function if present
272    /// 
273    /// 获取回调函数(如果存在)
274    #[inline]
275    pub(crate) fn get_callback(&self) -> Option<CallbackWrapper> {
276        self.callback.clone()
277    }
278}
279
280/// Task location information (including level) for hierarchical timing wheel
281/// 
282/// Memory layout optimization: level field placed first to reduce padding via struct alignment
283/// 
284/// 任务位置信息(包括层级)用于分层时间轮
285/// 
286/// 内存布局优化:将 level 字段放在第一位,通过结构体对齐来减少填充
287#[derive(Debug, Clone, Copy)]
288pub(crate) struct TaskLocation {
289    /// Slot index
290    /// 
291    /// 槽索引
292    pub slot_index: usize,
293    /// Index position of task in slot Vec for O(1) cancellation
294    /// 
295    /// 槽向量中任务的索引位置,用于 O(1) 取消
296    pub vec_index: usize,
297    /// Level: 0 = L0 (bottom layer), 1 = L1 (upper layer)
298    /// Using u8 instead of bool to reserve space for potential multi-layer expansion
299    /// 
300    /// 层级:0 = L0(底层),1 = L1(上层)
301    /// 使用 u8 而不是 bool 来保留空间,用于潜在的多层扩展
302    pub level: u8,
303}
304
305impl TaskLocation {
306    /// Create a new task location information
307    /// 
308    /// 创建一个新的任务位置信息
309    #[inline(always)]
310    pub fn new(level: u8, slot_index: usize, vec_index: usize) -> Self {
311        Self {
312            slot_index,
313            vec_index,
314            level,
315        }
316    }
317}
318