1

I have an application and I want to use a hybrid flow to call an API from my MVC web application. The API is secured and requires an access token (JWT). The code part on the API side is done. But how can I send my access token from my MVC application to the API in a service? I want to use a "generic" service for this that uses an httpclient.

I know that in controllers you can use

var accessToken = await HttpContext.GetTokenAsync("access_token");  

or

var accessToken = await HttpContext.GetUserAccessTokenAsync();

But how can I access the access token in a service? Tried this too, but didn't work

    var accessToken = _httpContextAccessor.HttpContext.Request.Headers[HeaderNames.Authorization];

Side question: how can I set the access token for the httpclient in the constructor of my service? (Using async methods is not possible) so I can't use this:

protected HttpClient HttpClient { get; private set; }

public MyGenericHttpClientService(IHttpContextAccessor httpContextAccessor)

{
            var accessToken = await httpContextAccessor.HttpContext.GetTokenAsync("access_token");
            HttpClient.SetBearerToken(accessToken);
}
6
  • Why didn’t IHttpContextAccessor work? Commented Jun 8, 2020 at 15:47
  • Can't use that one in a constructor, cause it's async. Commented Jun 8, 2020 at 15:49
  • I can do it before every method, but wanted to know if there is a better way to solve this. Commented Jun 8, 2020 at 16:02
  • 1
    how did you resolve the HttpClient? If you are using IHttpClientFactory, you can configure a DelegatingHandler in Startup that gets the token from IHttpContextAccessor and set it to outgoing requests. Commented Jun 8, 2020 at 16:13
  • 1
    see answer below Commented Jun 9, 2020 at 1:15

1 Answer 1

5

If you are using IHttpClientFactory, you can configure your HttpClient as follows by adding a DelegatingHandler in Startup.cs:

services.AddTransient<TokenHandler>();
services.AddHttpClient().AddHttpMessageHandler<TokenHandler>();

And TokenHandler can be as follows:

public class TokenHandler : DelegatingHandler
{
    private readonly IHttpContextAccessor _httpContextAccessor;

    public TokenHandler(
        IHttpContextAccessor httpContextAccessor)
    {
        _httpContextAccessor = httpContextAccessor;
    }

    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request,
        CancellationToken cancellationToken)
    {
        var token = await _httpContextAccessor.HttpContext.GetTokenAsync("access_token");
        request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", token);
        return await base.SendAsync(request, cancellationToken);
    }
}

For more information on IHttpClientFactory, you can see this article.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.