I have class with constructor for logging and for access to config:
public class SendEmaiServiceProvider
{
private readonly IConfiguration _config;
private readonly IWebHostEnvironment _env;
private readonly ILogger<SendEmaiServiceProvider> _logger;
private readonly string _fromEmailAddress;
public SendEmaiServiceProvider(IConfiguration config, IWebHostEnvironment env, ILogger<SendEmaiServiceProvider> logger)
{
_config = config;
_env = env;
_logger = logger;
_fromEmailAddress = _config.GetValue<string>("AppSettings:Email:FromEmailAddress");
}
public void SayHi()
{
Console.WriteLine("Hi");
}
}
The question is - How to call method SayHi from another class without pushing logger
, env
and config
?
No I initialize new object with parameters, but I sure that it is wrong:
var sendEmaiServiceProvider = new SendEmaiServiceProvider(_config, _env, _logger);
sendEmaiServiceProvider.SayHi();
I can create an empty constructor but I will not have _fromEmailAddress
value.
CodePudding user response:
Looks like this is a netcore website. Assuming so, then:
- Create an
interface
for the dependency. - Register the dependency in
Startup.cs
- Request the dependency as needed from the netcore DI.
public interface ISendEmaiServiceProvider
{
void SayHi()
}
public class SendEmaiServiceProvider : ISendEmaiServiceProvider
{
public void SayHi() { }
}
Then in Startup.cs:
public void ConfigureServices( IServiceCollection services )
{
services.AddScoped<ISendEmaiServiceProvider, SendEmaiServiceProvider>();
}
Then in the Controller (or wherever else DI is used), request it in the .ctor
and all the dependencies for SendEmaiServiceProvider
will be filled automatically by DI.
public class HomeController : Controller
{
public readonly ISendEmaiServiceProvider _emailService;
public HomeController( ISendEmaiServiceProvider emailService )
{
_emailService = emailService
}
}
That should get you going.
CodePudding user response:
You should use dependency injection here. Better you create an interface here and resolve your 'SendEmaiServiceProvider' on the startup. And then use the interface instead of creating a new instance for SayHi() method.
public interface YourInterface
{
void SayHi()
}
public class SendEmaiServiceProvider : YourInterface
{
public void SayHi()
{
//your code
}
}
On your startup,
public void ConfigureServices( IServiceCollection services )
{
services.AddScoped<YourInterface, SendEmaiServiceProvider>();
}
On your controller/service,
public class YourController : Controller
{
public readonly YourInterface _emailSenderService;
public HomeController( YourInterface emailSenderService )
{
_emailSenderService = emailSenderService
}
public IActionResult SayHI()
{
_emailSenderService.SayHi()
}
}