You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

异步实现Microsoft.OData.Client的SendingRequest2处理器时如何正确设置OAuth令牌

解决方案

问题根源在于SendingRequest2事件不支持异步委托:使用async void的事件处理器时,OData客户端不会等待异步操作完成就直接发送请求,导致令牌还未获取完成,请求已经发出。

提供两种可行的解决方式:

方式一:安全的同步调用(避免死锁)

用GetAwaiter().GetResult()替代.Result,这种方式不会像.Result那样轻易引发死锁,同时保持同步调用的形式,适合快速修改现有代码:

public void OnClientCreated(ClientCreatedArgs args)
{
    var client = args.ODataClient;
    client.SendingRequest2 += (s, e) =>
    {
        var token = _tokenClient.GetAccessToken().GetAwaiter().GetResult();
        
        e.RequestMessage.SetHeader(
            AppConstants.Authorization, 
            $"{AppConstants.Bearer} {token.Token}");
    };
}

方式二:基于HTTP管道的异步注入(推荐)

将令牌注入逻辑放到HTTP请求管道中,通过自定义DelegatingHandler实现完全异步的处理,符合HttpClient的最佳实践:

1. 创建OAuth消息处理器

public class OAuthDelegatingHandler : DelegatingHandler
{
    private readonly IAccessTokenClient _tokenClient;

    public OAuthDelegatingHandler(IAccessTokenClient tokenClient)
    {
        _tokenClient = tokenClient;
    }

    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {
        var token = await _tokenClient.GetAccessToken();
        request.Headers.Authorization = new AuthenticationHeaderValue(AppConstants.Bearer, token.Token);
        
        return await base.SendAsync(request, cancellationToken);
    }
}

2. 给OData客户端注入自定义处理器

public void OnClientCreated(ClientCreatedArgs args)
{
    var httpClientHandler = new HttpClientHandler();
    var oAuthHandler = new OAuthDelegatingHandler(_tokenClient)
    {
        InnerHandler = httpClientHandler
    };
    
    var httpClient = new HttpClient(oAuthHandler);
    args.ODataClient.HttpClient = httpClient;
}

这种方式把令牌处理逻辑与OData客户端的事件解耦,异步流程更可控,也便于后续扩展其他HTTP请求拦截逻辑。


内容的提问来源于stack exchange,提问作者JD Davis

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 23:45:42