1 回答

TA貢獻1852條經驗 獲得超7個贊
嘗試使用HttpClientFactory添加了 Asp.Net Core 2.1 的 ,結合HttpMessageHandler以實現您正在嘗試做的事情。
ConfigureServices您可以在方法中注冊 HttpClient
public void ConfigureServices(IServiceCollection services)
{
services.AddHttpClient<BaseClient>(client =>
{
client.BaseAddress = new Uri("yrl");
client.DefaultRequestHeaders.Add("Accept", "application/json");
c.DefaultRequestHeaders.Add("Accept", "application/vnd.github.v3+json");
c.DefaultRequestHeaders.Add("User-Agent", "HttpClientFactory-Sample");
});
}
使用上面的代碼,您BaseClient將通過 DI 接收 HttpClient 實例。
為了驗證/檢查,AuthHeader您可以HttpMessageHandler為已注冊的HttpClient. 消息處理程序的代碼很簡單,如下所示:
public class AuthHeaderHandler : DelegatingHandler
{
protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request,
CancellationToken cancellationToken)
{
if (!request.Headers.Contains("Authorization"))
{
return new HttpResponseMessage(HttpStatusCode.Forbidden)
{
Content = new StringContent("No Authorization header is present")
};
}
return await base.SendAsync(request, cancellationToken);
}
}
為了注冊上述處理程序,您的代碼將如下所示:
public void ConfigureServices(IServiceCollection services)
{
services.AddTransient<AuthHeaderHandler>();
services.AddHttpClient<BaseClient>(client =>
{
//code omitted for brevity
...
})
.AddHttpMessageHandler<AuthHeaderHandler>();
}
如果需要,您可以在消息處理程序中注入任何需要的內容。但是,無需在BaseClient. 要閱讀有關 HttpClientFactory 和 HttpMessageHandlers 的更多信息,請參閱此鏈接和此。我希望這有幫助。
更新的答案
請查看使用 IHttpContextAccessor 并修改 HttpRequestMessage 的更具體的 HttpMessageHandler 示例,即在調用之前添加 Authorization 標頭。您可以根據需要修改邏輯。
public class AuthHeaderHandler : DelegatingHandler
{
private readonly HttpContext _httpContext;
public AuthHeaderHandler(IHttpContextAccessor contextAccessor)
{
_httpContext = contextAccessor.HttpContext;
}
protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request,
CancellationToken cancellationToken)
{
if (_httpContext != null)
{
var accessToken = await _httpContext.GetTokenAsync(TokenKeys.Access);
if (!string.IsNullOrEmpty(accessToken))
{
// modify the request header with the new Authorization token
request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", accessToken);
}
}
return await base.SendAsync(request, cancellationToken);
}
}
更新的答案 2
請查看我已上傳到 GitHub的簡單解決方案。該解決方案甚至比我最初建議的還要簡單。由于您沒有集成任何基于身份的身份驗證/授權,您可以簡單地使用我稱之為 CustomActionFilter 的 CustomActionFilterValidateAuthHeader來檢查 AuthHeader 是否存在,如果不存在則返回通常的 403。
在 中ValidateAuthHeader,我使用了您之前發布的中間件代碼。然后,您可以簡單地將此屬性添加到需要此檢查的 ActionMethods 或 Controllers 上。
請查看DataController和ValuesController。將DataController接收HttpClient將用于調用values端點的類型。ValidateAuthHeader出現在 上GetValues并將檢查 AuthHeader。如果它不存在,它將產生錯誤。
[Route("api/[controller]")]
[ApiController]
public class DataController : ControllerBase
{
private readonly MyHttpClient _client;
public DataController(MyHttpClient client)
{
_client = client;
}
[ValidateAuthHeader]
public async Task<IActionResult> GetValues()
{
var response = await _client.GetAsync("api/values");
var contents = await response.Content.ReadAsStringAsync();
return new ContentResult
{
Content = contents,
ContentType = "application/json",
StatusCode = 200
};
}
}
流程的其余部分與我最初建議的相同。調用將通過AuthHeaderHandler已HttpMessageHandler注冊的MyHttpClient. 請看一看Startup.cs。
處理程序將檢索HttpContextviaHttpContextAccessor并檢查AuthHeader. 如果存在,它將把它添加到 RequestMessage 參數中。
我希望這有幫助。如有任何問題,請隨時提出。
不使用 HttpMessageHandler 設置 Auth Header
修改 MyHttpClient 并添加一個名為的公共方法SetAuthHeader
public class MyHttpClient
{
private readonly HttpClient _httpClient;
public MyHttpClient(HttpClient client)
{
_httpClient = client;
}
public void SetAuthHeader(string value)
{
_httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", value);
}
}
然后在您的操作方法中調用此方法,因為此時您將在 HttpContext.Request 中擁有 AuthHeader
[ValidateAuthHeader]
public async Task<IActionResult> GetValues()
{
var authHeader = Request.Headers["Authorization"];
_client.SetAuthHeader(authHeader.First());
var response = await _client.GetAsync("api/values");
var contents = await response.Content.ReadAsStringAsync();
return new ContentResult
{
Content = contents,
ContentType = "application/json",
StatusCode = 200
};
}
去掉AuthHeaderHandler注冊,刪除AuthHeaderHandler。
- 1 回答
- 0 關注
- 135 瀏覽
添加回答
舉報