Angular客户端取消请求后服务端未感知问题排查
我尝试在Angular客户端取消请求,Chrome网络面板显示请求已取消,但服务端始终未感知到该操作。以下是前后端代码:
前端代码
if (this.subscription) { this.subscription.unsubscribe(); } this.subscription = this._queueService.queueJob().subscribe(_ => { console.log("Done queuing!"); }); // The queueJob function... queueJob(): Observable<any> { return this._http.post(`queue`, { userId: Math.random() }); }
后端代码
[HttpPost] public async Task<IActionResult> Create(Object dto, CancellationToken cancellationToken) { var ct = HttpContext.RequestAborted; for (var i = 0; i < 50; i++) { try { ct.ThrowIfCancellationRequested(); cancellationToken.ThrowIfCancellationRequested(); await Task.Delay(100); } catch (OperationCanceledException ex) { } catch (Exception ex) { } } return Ok(new { Message = "Queued OK!" } ); }
我了解到需在Program.cs中添加services.AddMvc()或services.AddMvcCore()来确保HttpContext.RequestAborted和CancellationToken参数正确绑定,两种方式我都尝试过,也用两种方式调用了ThrowIfCancellationRequested,但均未触发取消。请问我遗漏了什么?
空catch块吞噬了取消信号:你捕获了
OperationCanceledException但没有任何终止逻辑,导致循环继续执行。取消触发后,必须在catch块中跳出循环或直接返回,比如:catch (OperationCanceledException ex) { return StatusCode(StatusCodes.Status499ClientClosedRequest); }Task.Delay未绑定取消令牌:当前
Task.Delay(100)不会响应取消信号,需传入令牌让延迟操作直接终止:await Task.Delay(100, ct);确认Angular取消逻辑的有效性:确保使用的是官方
HttpClient,且没有拦截器拦截取消操作。部分自定义拦截器可能会忽略订阅取消的信号,导致XHR请求未真正取消。检查HTTP协议与服务器配置:如果服务器启用HTTP/2,连接复用可能导致服务端无法立即感知TCP连接关闭。可切换到HTTP/1.1测试,或确认服务器对请求取消的处理逻辑。
验证CancellationToken绑定正确性:确保动作方法的
CancellationToken参数是框架自动注入的,不要手动覆盖该令牌。若方法存在路由参数,CancellationToken应放在参数列表的末尾。
内容的提问来源于stack exchange,提问作者Francis Ducharme

