Skip to content

Commit 8dae061

Browse files
committed
增加HttpMessageHandlers
1 parent 32347d9 commit 8dae061

File tree

4 files changed

+118
-35
lines changed

4 files changed

+118
-35
lines changed

WebApiClientCore.Extensions.OAuths/HttpMessageHandlers/OAuthTokenHandler.cs

Lines changed: 11 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1,70 +1,46 @@
1-
using System.Net;
2-
using System.Net.Http;
1+
using System.Net.Http;
32
using System.Net.Http.Headers;
43
using System.Threading;
54
using System.Threading.Tasks;
5+
using WebApiClientCore.HttpMessageHandlers;
66

77
namespace WebApiClientCore.Extensions.OAuths.HttpMessageHandlers
88
{
99
/// <summary>
1010
/// 表示token应用的http消息处理程序
1111
/// </summary>
12-
public class OAuthTokenHandler : DelegatingHandler
12+
public class OAuthTokenHandler : AuthorizationHandler
1313
{
1414
/// <summary>
1515
/// token提供者
1616
/// </summary>
17-
private readonly ITokenProvider tokenProvider;
17+
private readonly ITokenProvider tokenProvider;
1818

1919
/// <summary>
2020
/// token应用的http消息处理程序
2121
/// </summary>
2222
/// <param name="tokenProvider">token提供者</param>
2323
public OAuthTokenHandler(ITokenProvider tokenProvider)
24-
{
24+
{
2525
this.tokenProvider = tokenProvider;
2626
}
2727

2828
/// <summary>
29-
/// 检测响应是否未授权
30-
/// 未授权则重试请求一次
29+
/// 设置请求的授权信息
3130
/// </summary>
32-
/// <param name="request"></param>
33-
/// <param name="cancellationToken"></param>
31+
/// <param name="reason">授权原因</param>
32+
/// <param name="request">请求</param>
33+
/// <param name="cancellationToken">取消令牌</param>
3434
/// <returns></returns>
35-
protected sealed override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
35+
protected sealed override async Task SetAuthorizationAsync(AuthorizationReason reason, HttpRequestMessage request, CancellationToken cancellationToken)
3636
{
37-
var response = await this.SendCoreAsync(request, cancellationToken).ConfigureAwait(false);
38-
if (await this.IsUnauthorizedAsync(response).ConfigureAwait(false) == true)
37+
if (reason == AuthorizationReason.SetForResend)
3938
{
4039
this.tokenProvider.ClearToken();
41-
response = await this.SendCoreAsync(request, cancellationToken).ConfigureAwait(false);
4240
}
43-
return response;
44-
}
4541

46-
/// <summary>
47-
/// 发送http请求
48-
/// </summary>
49-
/// <param name="request"></param>
50-
/// <param name="cancellationToken"></param>
51-
/// <returns></returns>
52-
private async Task<HttpResponseMessage> SendCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken)
53-
{
5442
var tokenResult = await this.tokenProvider.GetTokenAsync().ConfigureAwait(false);
5543
this.UseTokenResult(request, tokenResult);
56-
return await base.SendAsync(request, cancellationToken).ConfigureAwait(false);
57-
}
58-
59-
/// <summary>
60-
/// 返回响应是否为未授权状态
61-
/// 反回true则强制清除token以支持下次获取到新的token
62-
/// </summary>
63-
/// <param name="response"></param>
64-
protected virtual Task<bool> IsUnauthorizedAsync(HttpResponseMessage? response)
65-
{
66-
var state = response != null && response.StatusCode == HttpStatusCode.Unauthorized;
67-
return Task.FromResult(state);
6844
}
6945

7046
/// <summary>
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
using System.ComponentModel;
2+
using System.Net;
3+
using System.Net.Http;
4+
using System.Threading;
5+
using System.Threading.Tasks;
6+
7+
namespace WebApiClientCore.HttpMessageHandlers
8+
{
9+
/// <summary>
10+
/// 表示授权应用的抽象http消息处理程序
11+
/// </summary>
12+
public abstract class AuthorizationHandler : DelegatingHandler
13+
{
14+
/// <summary>
15+
/// 检测响应是否未授权
16+
/// 未授权则重试请求一次
17+
/// </summary>
18+
/// <param name="request"></param>
19+
/// <param name="cancellationToken"></param>
20+
/// <returns></returns>
21+
[EditorBrowsable(EditorBrowsableState.Never)]
22+
protected sealed override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
23+
{
24+
await this.SetAuthorizationAsync(AuthorizationReason.SetForSend, request, cancellationToken).ConfigureAwait(false);
25+
var response = await base.SendAsync(request, cancellationToken).ConfigureAwait(false);
26+
27+
if (await this.IsUnauthorizedAsync(response).ConfigureAwait(false) == true)
28+
{
29+
await this.SetAuthorizationAsync(AuthorizationReason.SetForResend, request, cancellationToken).ConfigureAwait(false);
30+
response = await base.SendAsync(request, cancellationToken).ConfigureAwait(false);
31+
}
32+
return response;
33+
}
34+
35+
/// <summary>
36+
/// 设置请求的授权信息
37+
/// </summary>
38+
/// <param name="reason">授权原因</param>
39+
/// <param name="request">请求</param>
40+
/// <param name="cancellationToken">取消令牌</param>
41+
/// <returns></returns>
42+
protected abstract Task SetAuthorizationAsync(AuthorizationReason reason, HttpRequestMessage request, CancellationToken cancellationToken);
43+
44+
/// <summary>
45+
/// 返回响应是否为未授权状态
46+
/// 反回true则强制清除token以支持下次获取到新的token
47+
/// </summary>
48+
/// <param name="response"></param>
49+
protected virtual Task<bool> IsUnauthorizedAsync(HttpResponseMessage? response)
50+
{
51+
var state = response != null && response.StatusCode == HttpStatusCode.Unauthorized;
52+
return Task.FromResult(state);
53+
}
54+
}
55+
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
namespace WebApiClientCore.HttpMessageHandlers
2+
{
3+
/// <summary>
4+
/// 设置授权原因
5+
/// </summary>
6+
public enum AuthorizationReason
7+
{
8+
/// <summary>
9+
/// 用于发送
10+
/// </summary>
11+
SetForSend,
12+
13+
/// <summary>
14+
/// 用于重试发送
15+
/// </summary>
16+
SetForResend
17+
}
18+
}
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
using System.Net.Http;
2+
using System.Threading;
3+
using System.Threading.Tasks;
4+
5+
namespace WebApiClientCore.HttpMessageHandlers
6+
{
7+
/// <summary>
8+
/// 表示cookie授权验证的抽象http消息处理程序
9+
/// </summary>
10+
public abstract class CookieAuthorizationHandler : AuthorizationHandler
11+
{
12+
/// <summary>
13+
/// 设置请求的授权信息
14+
/// </summary>
15+
/// <param name="reason">授权原因</param>
16+
/// <param name="request">请求</param>
17+
/// <param name="cancellationToken">取消令牌</param>
18+
/// <returns></returns>
19+
protected sealed override async Task SetAuthorizationAsync(AuthorizationReason reason, HttpRequestMessage request, CancellationToken cancellationToken)
20+
{
21+
if (reason == AuthorizationReason.SetForResend)
22+
{
23+
await this.RefreshCookieAsync().ConfigureAwait(false);
24+
}
25+
}
26+
27+
/// <summary>
28+
/// 刷新CookieContainer的cookie
29+
/// 一般情况下,登录操作就得到最新的cookie,且自动覆盖到CookieContainer
30+
/// </summary>
31+
/// <returns></returns>
32+
protected abstract Task RefreshCookieAsync();
33+
}
34+
}

0 commit comments

Comments
 (0)