I have an ASP.NET 6 API project and having an issue with logging from methods that are run by a hangfire background job.
I setup Serilog just like this video
It works great in the controller or any other class/method that is called from the controller (i.e. same thread as the incoming request). Simply using Dependency Injection from the constructor and the logger object is initialized just fine.
public class MyController : ControllerBase
{
private readonly ILogger<MyController> _logger;
public MyController(ILogger<MyController> logger)
{
_logger = logger;
}
[HttpPost]
public async Task<ActionResult> MyActionMethod([FromBody] RequestBody request)
{
_logger.LogInformation("This works fine");
var jobId = BackgroundJob.Enqueue<JobHandler>(x =>
handler.Main(param1, param2, param3);
return Ok($"Job dispatched successfully, id: {jobId}");
}
The problem lies when trying to log from within the code that is being run by the background job. Using DI doesn't resolve the logger object and always returns null.
I have a LogService
that I use in various parts of the project, and logger
always resolves to null.
public class LogService
{
private readonly ILogger<LogService> _logger;
public LogService(ILogger<LogService> logger)
{
_logger = logger;
}
public void LogSolverStatus(RoutingModel model)
{
string status = model.GetStatus().ToString();
//Console.WriteLine($"Done Solving, Solution Status: {status}");
// This doesn't work because _logger is null and throws an exception
_logger.LogInformation("Done Solving, Solution Status: {status}", status);
}
One solution is passing dependencies when firing the background job.
Is there a better/easier solution?
I understand from this SO thread that the logger is supposed to be registered as Transient
or Singleton
.
How can I do this?