CancellationToken::cancel是否等待任务完成?是否允许新任务接入?
关于CancellationToken::cancel()的行为疑问
本人与同事就CancellationToken的使用存在争议,代码如下:
async fn terminate(token: CancellationToken, name: String) -> Result<()> { let mut sigterm = signal(SignalKind::terminate())?; let mut sigint = signal(SignalKind::interrupt())?; tokio::select! { _ = sigterm.recv() => { info!("Received SIGTERM, stopping service on {}", name); }, _ = sigint.recv() => { info!("Received SIGINT, stopping service on {}", name); }, } token.cancel(); Ok(()) }
咨询两个问题:
- 调用
token.cancel()后是否会等待已有任务执行完成? - 该操作后是否还允许新任务接入?
回答
调用
token.cancel()不会等待已有任务执行完成:cancel()仅会把CancellationToken标记为已取消状态,它不会主动终止或等待任何正在运行的任务。如果你的任务需要响应取消,必须在任务内部自行处理——比如通过token.cancelled()监听取消信号,或者在tokio::select!中将任务逻辑与取消信号绑定,当取消触发时主动退出任务流程。操作后是否允许新任务接入取决于任务实现:如果新任务启动时会检查CancellationToken的状态(比如调用
token.check_cancelled(),或是在tokio::select!里包含token.cancelled()分支),那么token已取消时这类任务会直接返回取消错误,相当于无法正常启动;但如果新任务完全不依赖这个令牌的状态,它依然可以正常运行——不过这违背了使用CancellationToken管控任务生命周期的设计初衷。
内容的提问来源于stack exchange,提问作者DungeonTiger
相关产品推荐
相关产品推荐

