Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Inject Typed HttpClient in a class with other parameters

I have this class in a Worker Service application,he's constructed with 2 string parameters that need to be injected, so that can't be registered as services:

public MyService(ILogger<MyService> logger, HttpClient client, string username, string password)
{
    this._logger = logger;
    this._client = client;
    this.Username = username;
    this.Password = password;
}

and i defined this builder:

var builder = Host.CreateDefaultBuilder(args);
builder.ConfigureServices((c, s) =>
        {
            s.AddHttpClient<MyService>(client => { 
                client.BaseAddress = new Uri("http://www.myserviceurl.com"); 
            });
            s.AddTransient<IMyService>(sp => new MyService(
                sp.GetRequiredService<ILogger<MyService>>(),
                sp.GetRequiredService<HttpClient>(),
                "username", 
                "password"
            ));
        });

but the HttpClient injected via IServiceProvider.GetRequiredService() isn't the same i added in the IServiceCollection with the AddHttpClient() method because the BaseAddress (and other defaultHeaders i omitted for brevity) is empty

Instead, if i remove the other 2 string parameters from the constructor and let the IServiceProvider to resolve the dependency i get the correct instance of the HttpClient

I definitely may not have understood how GetRequiredService works and I am still learning well how the IServiceProvider works, I would like to understand what I am doing wrong.

Edit:

Also I found that if I use named client instead of typed client

s.AddHttpClient("MyService",client => { 
                client.BaseAddress = new Uri("http://www.myserviceurl.com"); 
            });

and I resolve the dependency via:

s.AddTransient<IMyService>(sp => new MyService(
                sp.GetRequiredService<ILogger<MyService>>(),
                sp.GetRequiredService<IHttpClientFactory>().CreateClient("MyService"),
                "username", 
                "password"
            ));

Everything work as expected. What's the difference from Typed HttpClient?

like image 567
exSnake Avatar asked Dec 13 '25 13:12

exSnake


1 Answers

You can use this overload of AddHttpClient:

builder.ConfigureServices((c, s) =>
{
    s.AddHttpClient<IMyService, MyService>((client, sp) =>
    {
        client.BaseAddress = new Uri("http://www.myserviceurl.com");

        return new MyService(
            sp.GetRequiredService<ILogger<MyService>>(),
            client,
            "username",
            "password"
        );
    });
});
like image 155
Dimitris Maragkos Avatar answered Dec 16 '25 03:12

Dimitris Maragkos