【发布时间】:2019-05-04 14:29:52
【问题描述】:
控制台应用不会像 Web 应用那样将启动文件与配置服务一起使用,我正在努力理解依赖注入的关键概念。
(请注意以下示例无法编译)
这是我认为它应该如何工作的一个基本示例(请指出任何非常规或错误的地方):
static void Main(string[] args)
{
var builder = new ConfigurationBuilder()
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.AddUserSecrets<Settings>()
.Build();
var services = new ServiceCollection()
.AddLogging(b => b
.AddConsole())
.AddDbContext<UnderstandingDIContext>(options =>
options.UseSqlite(builder.GetConnectionString("DefaultConnection")))
.BuildServiceProvider();
var logger = services.GetService<ILoggerFactory>()
.CreateLogger<Program>();
logger.LogInformation("Starting Application");
var worker = new Worker();
logger.LogInformation("Closing Application");
}
但是如何在我的 'Worker' 类中使用这些服务呢?:
public Worker(ILogger logger, IConfiguration configuration)
{
logger.LogInformation("Inside Worker Class");
var settings = new Settings()
{
Secret1 = configuration["Settings:Secret1"],
Secret2 = configuration["Settings:Secret2"]
};
logger.LogInformation($"Secret 1 is '{settings.Secret1}'");
logger.LogInformation($"Secret 2 is '{settings.Secret2}'");
using (var context = new UnderstandingDIContext())
{
context.Add(new UnderstandingDIModel()
{
Message = "Adding a message to the database."
});
}
}
了解DIContext
public class UnderstandingDIContext : DbContext
{
public UnderstandingDIContext(DbContextOptions<UnderstandingDIContext> options)
: base(options)
{ }
public DbSet<UnderstandingDIModel> UnderstandingDITable { get; set; }
}
这段代码的问题如下:
Worker() 期望传递 ILogger 和 IConfiguration 参数,但我认为依赖注入应该涵盖这一点?
我无法运行'dotnet ef migrations add Initial',因为我没有正确传递连接字符串(错误:'无法创建'UnderstandingDIContext'类型的对象。')
'using (var context = new UnderstandingDIContext())' 无法编译,因为我误解了 DbContext 位。
我搜索了很多,有很多关于 Web 应用程序的示例,但对于控制台应用程序却很少。我是不是完全误解了依赖注入的整个概念?
【问题讨论】:
-
不要自己创建
new Worker()。而是将其注册到您的ServiceCollection并让 DI 为您实例化它。 -
这是否意味着您必须实现一个接口(例如 IWorker)或者这是推荐的做法?
-
不,你可以注册一个没有接口的依赖。只需将具体类型放在注册调用和构造函数参数中即可。
标签: c# asp.net-core dependency-injection