C# Dependency Injection In Constructor With Parameters

NET Core DI, ways of passing parameters to the constructor

This technique is useful when not all the parameters for the constructor can be created from the container. Whilst some of the parameters can be created, they need to be configured before being consumed by the constructor.{alertInfo}

In this post, I will show you how to pass parameters to the constructor of the service while resolving the dependency.
Let’s consider you have legacy code and you want to use it in our .net core application. The code is accepting some constructor parameters which .net container DI cannot inject.
Let’s create a console application to demonstrate this.

Main.cs

void Main()
{
	var container = Startup.Configure();
	var customerService = container.GetService<ICustomerService>();
	customerService.GetData();

}

Startup.cs

public class Startup
{


	public static ServiceProvider Configure()
	{
		var provider = new ServiceCollection()
					.AddScoped<IDataService,DataService>()
					.AddLogging(fs => fs.AddConsole())
					.AddTransient<ICustomerService, CustomerService>()

					.BuildServiceProvider();
		return provider;
	}

}

IDataService

public interface IDataService
{
	void GetData();
}

public interface ICustomerService
{
	void GetData();
}

DataService.cs

public class DataService : IDataService
{
	private readonly ILogger _logger;
	private readonly string _connectionString;

	public DataService(ILogger<DataService> logger, string connectionString)
	{
		_logger = logger;
		_connectionString = connectionString;

	}

	public void GetData()
	{
		_logger.LogInformation($"Getting Data From DataBase {_connectionString}");

	}

}

CustomerService

public class CustomerService : ICustomerService
{
	private readonly ILogger<CustomerService> _logger;
	private readonly IDataService _dataService;
	public CustomerService(ILoggerFactory loggerFactory, IDataService dataService)
	{
		_logger = loggerFactory.CreateLogger<CustomerService>();
		_dataService = dataService;
	}

	public void GetData()
	{
		_dataService.GetData();
	}
}

If you run the application, you will get the following error because it expects a connection string parameter. After all, that service is not resolved.

Unable to resolve service for type ‘System. String’ while attempting to activate ‘DataService’.{alertError}

To solve this issue, we can use the factory delegate of IServiceProvider.

Let’s add the factory delegate.

public class Startup
{


	public static ServiceProvider Configure()
	{
		var provider = new ServiceCollection()
					.AddScoped<IDataService>(x =>
					{
						var logger = x.GetRequiredService<ILogger<DataService>>();
						var dataService = new DataService(logger, "some conection string");
						return dataService;

					})
					.AddLogging(fs => fs.AddConsole())
					.AddTransient<ICustomerService, CustomerService>()

					.BuildServiceProvider();
		return provider;
	}

}

If you run the application, you will get the output.

info: DataService[0]
Getting Data From DataBase some conection string

Please do not post any spam link in the comment box😊

Post a Comment (0)
Previous Post Next Post