c#在aspnet core外部库中注入设置
c# Inject settings in aspnet core external library
我有一个入口点为 ASP.NET Core API 的项目和一个作为 MongoDB 客户端的基础设施项目。我有一个问题,我会在带有 mongo 客户端的项目中注入我的接口 IDatabaseSettings(在一个公共项目中),所以我在我的主要项目中创建具体类型,如下所示:
public class MongoSettings : IDatabaseSettings
{
private const string Mongo = "Mongo";
private static IConfiguration _configuration;
public LogMongoSettings(IConfiguration configuration)
{
_configuration = configuration;
}
public string ConnectionString { get; } = _configuration.GetValue<string>($"{Mongo}:ConnectionString");
public string DatabaseName { get; } = _configuration.GetValue<string>($"{Mongo}:Database");
public string Username { get; } = _configuration.GetValue<string>($"{Mongo}:Username") ?? string.Empty;
public string Password { get; } = _configuration.GetValue<string>($"{Mongo}:Password") ?? string.Empty;
}
问题是 _configuration 始终为 null,此代码引发异常。
我使用 SimpleInjector 容器,我的启动项目是这样的:
public class Startup
{
private static readonly Container Container = new Container();
private static readonly Assembly LogReaderAssembly = Assembly.Load("LogReader.IdP");
private static readonly Assembly MongoLogReaderAssembly = Assembly.Load("LogReader.Mongo");
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
// For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.AddSimpleInjector(Container, options =>
{
options.AddAspNetCore()
.AddControllerActivation();
options.AddLogging();
});
services.AddSwaggerGen(options =>
{
options.SwaggerDoc("LogReader", new OpenApiInfo
{
Version = "V1"
});
});
InitializeContainer();
}
private static void InitializeContainer()
{
Container.RegisterSingleton<IDatabaseClient, DatabaseClient>();
Container.Register<IFileRepositoryReader, TraceFileRepositoryReader>();
Container.Register(typeof(IRepositoryReader<>), MongoLogReaderAssembly);
Container.RegisterSingleton(() => Container.GetInstance<MapperProvider>().GetMapper());
Container.Register(typeof(IQueryHandler<,>), LogReaderAssembly);
Container.Register<IDatabaseSettings, MongoSettings>();
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseSimpleInjector(Container);
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
app.UseSwagger();
Container.Verify(VerificationOption.VerifyAndDiagnose);
}
}
为什么会这样?问题是什么?
我不会在我的 Mongo 客户端中使用 IOptionMonitor,因为我不会认为这个 class 取决于具体的 TOptions。
有更好的解决方案吗?
谢谢。
最后,我用这段代码解决了问题:
public class MongoDatabaseSettings : IDatabaseSettings
{
private const string Mongo = "Mongo:";
public MongoDatabaseSettings(IConfiguration configuration)
{
Host = configuration.GetValue<string>($"{Mongo}{nameof(Host)}");
Port = configuration.GetValue<int>($"{Mongo}{nameof(Port)}");
DatabaseName = configuration.GetValue<string>($"{Mongo}{nameof(DatabaseName)}");
Username = configuration.GetValue<string>($"{Mongo}{nameof(Username)}");
Password = configuration.GetValue<string>($"{Mongo}{nameof(Password)}");
}
public string Host { get; }
public int Port { get; }
public string DatabaseName { get; }
public string Username { get; }
public string Password { get; }
}
我不明白为什么在这种情况下属性被正确初始化,而不是原来的问题代码不起作用。
你知道为什么会这样吗?谢谢
我有一个入口点为 ASP.NET Core API 的项目和一个作为 MongoDB 客户端的基础设施项目。我有一个问题,我会在带有 mongo 客户端的项目中注入我的接口 IDatabaseSettings(在一个公共项目中),所以我在我的主要项目中创建具体类型,如下所示:
public class MongoSettings : IDatabaseSettings
{
private const string Mongo = "Mongo";
private static IConfiguration _configuration;
public LogMongoSettings(IConfiguration configuration)
{
_configuration = configuration;
}
public string ConnectionString { get; } = _configuration.GetValue<string>($"{Mongo}:ConnectionString");
public string DatabaseName { get; } = _configuration.GetValue<string>($"{Mongo}:Database");
public string Username { get; } = _configuration.GetValue<string>($"{Mongo}:Username") ?? string.Empty;
public string Password { get; } = _configuration.GetValue<string>($"{Mongo}:Password") ?? string.Empty;
}
问题是 _configuration 始终为 null,此代码引发异常。 我使用 SimpleInjector 容器,我的启动项目是这样的:
public class Startup
{
private static readonly Container Container = new Container();
private static readonly Assembly LogReaderAssembly = Assembly.Load("LogReader.IdP");
private static readonly Assembly MongoLogReaderAssembly = Assembly.Load("LogReader.Mongo");
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
// For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.AddSimpleInjector(Container, options =>
{
options.AddAspNetCore()
.AddControllerActivation();
options.AddLogging();
});
services.AddSwaggerGen(options =>
{
options.SwaggerDoc("LogReader", new OpenApiInfo
{
Version = "V1"
});
});
InitializeContainer();
}
private static void InitializeContainer()
{
Container.RegisterSingleton<IDatabaseClient, DatabaseClient>();
Container.Register<IFileRepositoryReader, TraceFileRepositoryReader>();
Container.Register(typeof(IRepositoryReader<>), MongoLogReaderAssembly);
Container.RegisterSingleton(() => Container.GetInstance<MapperProvider>().GetMapper());
Container.Register(typeof(IQueryHandler<,>), LogReaderAssembly);
Container.Register<IDatabaseSettings, MongoSettings>();
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseSimpleInjector(Container);
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
app.UseSwagger();
Container.Verify(VerificationOption.VerifyAndDiagnose);
}
}
为什么会这样?问题是什么? 我不会在我的 Mongo 客户端中使用 IOptionMonitor,因为我不会认为这个 class 取决于具体的 TOptions。 有更好的解决方案吗? 谢谢。
最后,我用这段代码解决了问题:
public class MongoDatabaseSettings : IDatabaseSettings
{
private const string Mongo = "Mongo:";
public MongoDatabaseSettings(IConfiguration configuration)
{
Host = configuration.GetValue<string>($"{Mongo}{nameof(Host)}");
Port = configuration.GetValue<int>($"{Mongo}{nameof(Port)}");
DatabaseName = configuration.GetValue<string>($"{Mongo}{nameof(DatabaseName)}");
Username = configuration.GetValue<string>($"{Mongo}{nameof(Username)}");
Password = configuration.GetValue<string>($"{Mongo}{nameof(Password)}");
}
public string Host { get; }
public int Port { get; }
public string DatabaseName { get; }
public string Username { get; }
public string Password { get; }
}
我不明白为什么在这种情况下属性被正确初始化,而不是原来的问题代码不起作用。 你知道为什么会这样吗?谢谢