配置文件加载
Startup文件加载:
/// <summary> /// 配置信息对象 /// </summary> private readonly IConfiguration _configuration; /// <summary> /// 服务配置对象 /// </summary> private readonly ServiceOption _serviceOption; /// <summary> /// 构造函数 /// </summary> /// <param name="env"></param> public Startup(IWebHostEnvironment env) { _configuration = env.LoadSettings(); _serviceOption = new ServiceOption { IsUseGlobalAuthFilter = false, //全局认证过滤开关 IsUseJwtAuthentication = false, //JWT认证开关 IgnoreJsonNullValue = false, //忽略JSON空值开关 IsUseCap = false //CAP开关 }; } /// <summary> /// 初始化服务配置 /// </summary> /// <param name="services">服务集合对象</param> public void ConfigureServices(IServiceCollection services) { //请在此向容器注册自定义的服务类 services.AddScoped<MobileSessionsService>(); services.InitServices(_configuration, _serviceOption); }
StartupExtension文件:
/// <summary> /// 加载配置文件 /// </summary> /// <param name="env">环境对象</param> /// <returns>配置对象</returns> public static IConfiguration LoadSettings(this IHostEnvironment env) { Const.MachineCode = EnvUtil.WelcomeWithMakeMachineCode(); var builder = new ConfigurationBuilder() .SetBasePath(AppDomain.CurrentDomain.BaseDirectory) .AddJsonFile("commons.json", optional: true, reloadOnChange: false) .AddJsonFile($"commons.{env.EnvironmentName}.json", optional: true, reloadOnChange: false) .AddJsonFile("appsettings.json", optional: true, reloadOnChange: false) .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true, reloadOnChange: false) .AddEnvironmentVariables(); var config = builder.Build(); string appName = config["ProjectName"]; Console.WriteLine("当前应用:" + appName); Const.GlobalConfiguration = config; return config; } /// <summary> /// 初始化Redis /// </summary> /// <param name="configuration"></param> private static void InitRedis(IConfiguration configuration) { //var redisPwd = configuration["RedisConfig:Password"]; //var projectGroup = configuration["ProjectGroup"]; ////集群模式 //var clusterNodes = configuration.GetSection("RedisConfig:ClusterNodes").Get<List<string>>(); //if (clusterNodes != null && clusterNodes.Count > 0) //{ // var newNodes = new List<string>(); // clusterNodes.ForEach(i => newNodes.Add($"{i},password={redisPwd},defaultDatabase=0,ssl=false,prefix={projectGroup}")); // string urls = string.Join(";", newNodes); // var redisClient = new CSRedisClient(urls); // RedisHelper.Initialization(redisClient); //} //哨兵模式 //string sentinelMaster = configuration["RedisConfig:SentinelMaster"]; //var sentinelNodes = configuration.GetSection("RedisConfig:SentinelNodes").Get<List<string>>(); //if (sentinelNodes != null && sentinelNodes.Count > 0) //{ // string connectionString = $"{sentinelMaster},password={redisPwd},defaultDatabase=0,poolsize=50,ssl=false,writeBuffer=10240,prefix={projectGroup}"; // var redisClient = new CSRedisClient(connectionString, sentinelNodes.ToArray()); // RedisHelper.Initialization(redisClient); // Console.WriteLine($">>>>>>>>>>>>>>>>>>>>Redis连接信息【{EnvUtil.EnvName}】<<<<<<<<<<<<<<<<<<<<"); // Console.WriteLine("连接字符串:" + connectionString); // Console.WriteLine("哨兵节点:" + string.Join(",", sentinelNodes)); //} } /// <summary> /// 初始化通用服务 /// </summary> /// <param name="services"></param> /// <param name="configuration"></param> public static void InitServices(this IServiceCollection services, IConfiguration configuration) { string mainConSting = configuration.GetConnectionString("Main"); if (!string.IsNullOrWhiteSpace(mainConSting)) services.AddDbContext<MainDbContext>(builder => builder.UseSqlServer(mainConSting)); string readConString = configuration.GetConnectionString("Read"); if (!string.IsNullOrWhiteSpace(readConString)) services.AddDbContext<ReadDbContext>(builder => builder.UseSqlServer(readConString)); services.AddHttpContextAccessor(); services.AddSingleton(configuration); InitRedis(configuration); services.AddCap(options => { options.FailedRetryCount = 5; options.UseInMemoryStorage(); options.UseInMemoryMessageQueue(); options.UseEntityFramework<MainDbContext>(); var rabbitMqOptions = configuration.GetSection("RabbitMQConfig").Get<RabbitMQOptions>(); options.UseRabbitMQ(mqOptions => { mqOptions.HostName = rabbitMqOptions.HostName; mqOptions.Port = rabbitMqOptions.Port; mqOptions.UserName = rabbitMqOptions.UserName; mqOptions.Password = rabbitMqOptions.Password; }); options.UseDashboard(dashboardOptions => { dashboardOptions.PathMatch = $"/api/{configuration["ProjectPrefix"]}/cap"; }); }); } /// <summary> /// 初始化通用服务 /// </summary> /// <param name="services">服务集合对象</param> /// <param name="configuration">配置对象</param> /// <param name="serviceOption">选项配置</param> public static void InitServices(this IServiceCollection services, IConfiguration configuration, ServiceOption serviceOption) { if (serviceOption.IsUseUnifiedReadDb) { string mainConSting = configuration.GetConnectionString("Main"); if (!string.IsNullOrWhiteSpace(mainConSting)) services.AddDbContext<MainDbContext>(builder => builder.UseSqlServer(mainConSting)); } if (serviceOption.IsUseUnifiedReadDb) { string readConString = configuration.GetConnectionString("Read"); if (!string.IsNullOrWhiteSpace(readConString)) services.AddDbContext<ReadDbContext>(builder => builder.UseSqlServer(readConString)); } services.AddMediatR(Assembly.GetEntryAssembly()); services.AddHttpClient(); services.AddOptions(); services.AddSingleton(configuration); services.AddCors(options => { options.AddDefaultPolicy(builder => builder.AllowAnyOrigin() .AllowAnyHeader().AllowAnyMethod()); }); services.AddControllers(); services.AddApiVersioning(options => { options.DefaultApiVersion = new ApiVersion(1, 0); options.AssumeDefaultVersionWhenUnspecified = true; options.ReportApiVersions = true; options.ApiVersionReader = new HeaderApiVersionReader("api-version"); }); services.Replace(ServiceDescriptor.Transient<IControllerActivator, ServiceBasedControllerActivator>()); services.AddMvc(options => { if (serviceOption.IsUseGlobalAuthFilter) options.Filters.Add(new AuthorizeFilter()); }) .AddNewtonsoftJson(options => { options.SerializerSettings.ContractResolver = new DefaultContractResolver(); options.SerializerSettings.DateFormatHandling = DateFormatHandling.MicrosoftDateFormat; options.SerializerSettings.DateTimeZoneHandling = DateTimeZoneHandling.Local; options.SerializerSettings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore; options.SerializerSettings.DateFormatString = "yyyy/MM/dd HH:mm:ss.fff"; if (serviceOption.IgnoreJsonNullValue) options.SerializerSettings.NullValueHandling = NullValueHandling.Ignore; }) .AddControllersAsServices() .AddRazorRuntimeCompilation(); services.AddHttpContextAccessor(); if (serviceOption.IsUseCap) { services.AddCap(options => { options.FailedRetryCount = 5; options.UseInMemoryStorage(); options.UseInMemoryMessageQueue(); options.UseEntityFramework<MainDbContext>(); var rabbitMqOptions = configuration.GetSection("RabbitMQConfig").Get<RabbitMQOptions>(); options.UseRabbitMQ(mqOptions => { mqOptions.HostName = rabbitMqOptions.HostName; mqOptions.Port = rabbitMqOptions.Port; mqOptions.UserName = rabbitMqOptions.UserName; mqOptions.Password = rabbitMqOptions.Password; }); options.UseDashboard(dashboardOptions => { dashboardOptions.PathMatch = $"/api/{configuration["ProjectPrefix"]}/cap"; }); }); } if (serviceOption.IsUseRedis) InitRedis(configuration); if (serviceOption.IsUseJwtAuthentication) { services.Configure<TokenDto>(configuration.GetSection("JwtConfig")); services.Configure<AdminTokenDto>(configuration.GetSection("AdminJwtConfig")); var jwtConfig = configuration.GetSection("JwtConfig").Get<TokenDto>(); var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(jwtConfig.Secret)); services.AddSingleton(securityKey); services.AddAuthorization(options => { options.AddPolicy("Admin", builder => builder.Requirements.Add(new AdminPolicyRequirement())); }); services.AddSingleton<IAuthorizationHandler, AdminAuthorizationHandler>(); services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme) .AddJwtBearer(options => { options.TokenValidationParameters = new TokenValidationParameters { ValidateIssuer = true, ValidIssuer = jwtConfig.Issuer, ValidateAudience = true, ValidAudience = jwtConfig.Audience, ClockSkew = TimeSpan.FromSeconds(0), ValidateLifetime = true, IssuerSigningKey = securityKey }; options.Events = new JwtBearerEvents { OnMessageReceived = ctx => { string tmpToken = ctx.HttpContext.Request.Headers["token"].ToString(); if (!string.IsNullOrWhiteSpace(tmpToken)) ctx.Token = tmpToken; return Task.CompletedTask; }, OnChallenge = ctx => { ctx.HandleResponse(); if (!ctx.Response.HasStarted) { ctx.Response.Headers.Add("Access-Control-Allow-Origin", "*"); ctx.Response.ContentType = "application/json"; ctx.Response.StatusCode = (int) HttpStatusCode.Unauthorized; string msg; ApiCode code = ApiCode.UnLogin; if (ctx.AuthenticateFailure is SecurityTokenInvalidSignatureException) { msg = "请先登录"; code = ApiCode.UnLogin; } else if (ctx.AuthenticateFailure is SecurityTokenExpiredException) { msg = "登录过期"; code = ApiCode.TokenExpire; } else msg = "无权访问"; var respObj = new ApiResult(code, msg); var json = JsonConvert.SerializeObject(respObj); ctx.Response.WriteAsync(json); } return Task.CompletedTask; } }; }); } if (serviceOption.IsUseConsulReg) { var consulConfig = configuration.GetSection("ConsulConfig").Get<ConsulConfigDto>(); services.AddSingleton(consulConfig); } if (!EnvUtil.IsProduction) { services.AddSwaggerGen(options => { options.SwaggerDoc(configuration["ProjectPrefix"], new OpenApiInfo { Version = "V1", Title = configuration["ProjectName"] + $"接口文档({EnvUtil.EnvChineseName})", Description = "本文档根据后端接口自动生成,出现在在此页面的接口代表后端已完成", Contact = new OpenApiContact { Name = "test网", Email = "hr@test.com", Url = new Uri("http://www.test.com") }, License = new OpenApiLicense { Name = "许可声明", Url = new Uri("http://www.tianping898.com") } }); options.AddSecurityDefinition("Bearer", new OpenApiSecurityScheme { Description = "在下框中输入请求头中需要添加Jwt授权Token,格式为(注意中间有个空格):Bearer Token", Name = "Authorization", In = ParameterLocation.Header, Type = SecuritySchemeType.ApiKey, BearerFormat = "JWT", Scheme = "Bearer" }); options.AddSecurityRequirement(new OpenApiSecurityRequirement { { new OpenApiSecurityScheme { Reference = new OpenApiReference { Type = ReferenceType.SecurityScheme, Id = "Bearer" } }, new string[] { } } }); options.OperationFilter<SwaggerOperationFilter>(); options.DocumentFilter<SwaggerHiddenApiFilter>(); options.DocumentFilter<SwaggerEnumFilter>(); var entryXmlFile = $"{Assembly.GetEntryAssembly()?.GetName().Name}.xml"; var entryXmlPath = Path.Combine(AppContext.BaseDirectory, entryXmlFile); if (File.Exists(entryXmlPath)) options.IncludeXmlComments(entryXmlPath, true); var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml"; var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile); if (File.Exists(xmlPath)) options.IncludeXmlComments(xmlPath, true); }); } }
/// <summary> /// 加载配置文件 /// </summary> /// <param name="env">环境对象</param> /// <returns>配置对象</returns> public static IConfiguration LoadSettings(this IHostEnvironment env) { //Const.MachineCode = EnvUtil.WelcomeWithMakeMachineCode();
//var builder = new ConfigurationBuilder() // .SetBasePath(AppDomain.CurrentDomain.BaseDirectory) // .AddJsonFile("commons.json", optional: true, reloadOnChange: false) // .AddJsonFile($"commons.{env.EnvironmentName}.json", optional: true, reloadOnChange: false) // .AddJsonFile("appsettings.json", optional: true, reloadOnChange: false) // .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true, reloadOnChange: false) // .AddEnvironmentVariables(); //var config = builder.Build();
//string appName = config["ProjectName"]; //Console.WriteLine("当前应用:" + appName);
//Const.GlobalConfiguration = config; //return config;
var settingInfo = env.InitSettings(); Const.MachineCode = settingInfo.MachineCode; Const.GlobalConfiguration = settingInfo.Configuration;
return Const.GlobalConfiguration; }
/// <summary> /// 初始化Redis /// </summary> /// <param name="configuration"></param> private static void InitRedis(IConfiguration configuration) { //var redisPwd = configuration["RedisConfig:Password"]; //var projectGroup = configuration["ProjectGroup"];
////集群模式 //var clusterNodes = configuration.GetSection("RedisConfig:ClusterNodes").Get<List<string>>(); //if (clusterNodes != null && clusterNodes.Count > 0) //{ // var newNodes = new List<string>(); // clusterNodes.ForEach(i => newNodes.Add($"{i},password={redisPwd},defaultDatabase=0,ssl=false,prefix={projectGroup}")); // string urls = string.Join(";", newNodes); // var redisClient = new CSRedisClient(urls); // RedisHelper.Initialization(redisClient); //}
//哨兵模式 //string sentinelMaster = configuration["RedisConfig:SentinelMaster"]; //var sentinelNodes = configuration.GetSection("RedisConfig:SentinelNodes").Get<List<string>>(); //if (sentinelNodes != null && sentinelNodes.Count > 0) //{ // string connectionString = $"{sentinelMaster},password={redisPwd},defaultDatabase=0,poolsize=50,ssl=false,writeBuffer=10240,prefix={projectGroup}"; // var redisClient = new CSRedisClient(connectionString, sentinelNodes.ToArray()); // RedisHelper.Initialization(redisClient); // Console.WriteLine($">>>>>>>>>>>>>>>>>>>>Redis连接信息【{EnvUtil.EnvName}】<<<<<<<<<<<<<<<<<<<<"); // Console.WriteLine("连接字符串:" + connectionString); // Console.WriteLine("哨兵节点:" + string.Join(",", sentinelNodes)); //} }
/// <summary> /// 初始化通用服务 /// </summary> /// <param name="services"></param> /// <param name="configuration"></param> public static void InitServices(this IServiceCollection services, IConfiguration configuration) { string mainConSting = configuration.GetConnectionString("Main"); if (!string.IsNullOrWhiteSpace(mainConSting)) services.AddDbContext<MainDbContext>(builder => builder.UseSqlServer(mainConSting));
string readConString = configuration.GetConnectionString("Read"); if (!string.IsNullOrWhiteSpace(readConString)) services.AddDbContext<ReadDbContext>(builder => builder.UseSqlServer(readConString));
services.AddHttpContextAccessor(); services.AddSingleton(configuration);
InitRedis(configuration);
services.AddCap(options => { options.FailedRetryCount = 5; options.UseInMemoryStorage(); options.UseInMemoryMessageQueue(); options.UseEntityFramework<MainDbContext>(); var rabbitMqOptions = configuration.GetSection("RabbitMQConfig").Get<RabbitMQOptions>(); options.UseRabbitMQ(mqOptions => { mqOptions.HostName = rabbitMqOptions.HostName; mqOptions.Port = rabbitMqOptions.Port; mqOptions.UserName = rabbitMqOptions.UserName; mqOptions.Password = rabbitMqOptions.Password; });
options.UseDashboard(dashboardOptions => { dashboardOptions.PathMatch = $"/api/{configuration["ProjectPrefix"]}/cap"; }); }); }
/// <summary> /// 初始化通用服务 /// </summary> /// <param name="services">服务集合对象</param> /// <param name="configuration">配置对象</param> /// <param name="serviceOption">选项配置</param> public static void InitServices(this IServiceCollection services, IConfiguration configuration, ServiceOption serviceOption) { if (serviceOption.IsUseUnifiedReadDb) { string mainConSting = configuration.GetConnectionString("Main"); if (!string.IsNullOrWhiteSpace(mainConSting)) services.AddDbContext<MainDbContext>(builder => builder.UseSqlServer(mainConSting)); }
if (serviceOption.IsUseUnifiedReadDb) { string readConString = configuration.GetConnectionString("Read"); if (!string.IsNullOrWhiteSpace(readConString)) services.AddDbContext<ReadDbContext>(builder => builder.UseSqlServer(readConString)); }
services.AddMediatR(Assembly.GetEntryAssembly()); services.AddHttpClient(); services.AddOptions(); services.AddSingleton(configuration); services.AddCors(options => { options.AddDefaultPolicy(builder => builder.AllowAnyOrigin() .AllowAnyHeader().AllowAnyMethod()); }); services.AddControllers(); services.AddApiVersioning(options => { options.DefaultApiVersion = new ApiVersion(1, 0); options.AssumeDefaultVersionWhenUnspecified = true; options.ReportApiVersions = true; options.ApiVersionReader = new HeaderApiVersionReader("api-version"); }); services.Replace(ServiceDescriptor.Transient<IControllerActivator, ServiceBasedControllerActivator>()); services.AddMvc(options => { if (serviceOption.IsUseGlobalAuthFilter) options.Filters.Add(new AuthorizeFilter()); }) .AddNewtonsoftJson(options => { options.SerializerSettings.ContractResolver = new DefaultContractResolver(); options.SerializerSettings.DateFormatHandling = DateFormatHandling.MicrosoftDateFormat; options.SerializerSettings.DateTimeZoneHandling = DateTimeZoneHandling.Local; options.SerializerSettings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore; options.SerializerSettings.DateFormatString = "yyyy/MM/dd HH:mm:ss.fff"; if (serviceOption.IgnoreJsonNullValue) options.SerializerSettings.NullValueHandling = NullValueHandling.Ignore; }) .AddControllersAsServices() .AddRazorRuntimeCompilation(); services.AddHttpContextAccessor(); if (serviceOption.IsUseCap) { services.AddCap(options => { options.FailedRetryCount = 5; options.UseInMemoryStorage(); options.UseInMemoryMessageQueue(); options.UseEntityFramework<MainDbContext>(); var rabbitMqOptions = configuration.GetSection("RabbitMQConfig").Get<RabbitMQOptions>(); options.UseRabbitMQ(mqOptions => { mqOptions.HostName = rabbitMqOptions.HostName; mqOptions.Port = rabbitMqOptions.Port; mqOptions.UserName = rabbitMqOptions.UserName; mqOptions.Password = rabbitMqOptions.Password; });
options.UseDashboard(dashboardOptions => { dashboardOptions.PathMatch = $"/api/{configuration["ProjectPrefix"]}/cap"; }); }); }
if (serviceOption.IsUseRedis) InitRedis(configuration);
if (serviceOption.IsUseJwtAuthentication) { services.Configure<TokenDto>(configuration.GetSection("JwtConfig")); services.Configure<AdminTokenDto>(configuration.GetSection("AdminJwtConfig")); var jwtConfig = configuration.GetSection("JwtConfig").Get<TokenDto>(); var securityKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(jwtConfig.Secret)); services.AddSingleton(securityKey);
services.AddAuthorization(options => { options.AddPolicy("Admin", builder => builder.Requirements.Add(new AdminPolicyRequirement())); }); services.AddSingleton<IAuthorizationHandler, AdminAuthorizationHandler>();
services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme) .AddJwtBearer(options => { options.TokenValidationParameters = new TokenValidationParameters { ValidateIssuer = true, ValidIssuer = jwtConfig.Issuer, ValidateAudience = true, ValidAudience = jwtConfig.Audience, ClockSkew = TimeSpan.FromSeconds(0), ValidateLifetime = true, IssuerSigningKey = securityKey };
options.Events = new JwtBearerEvents { OnMessageReceived = ctx => { string tmpToken = ctx.HttpContext.Request.Headers["token"].ToString(); if (!string.IsNullOrWhiteSpace(tmpToken)) ctx.Token = tmpToken; return Task.CompletedTask; }, OnChallenge = ctx => { ctx.HandleResponse(); if (!ctx.Response.HasStarted) { ctx.Response.Headers.Add("Access-Control-Allow-Origin", "*"); ctx.Response.ContentType = "application/json"; ctx.Response.StatusCode = (int) HttpStatusCode.Unauthorized; string msg; ApiCode code = ApiCode.UnLogin; if (ctx.AuthenticateFailure is SecurityTokenInvalidSignatureException) { msg = "请先登录"; code = ApiCode.UnLogin; } else if (ctx.AuthenticateFailure is SecurityTokenExpiredException) { msg = "登录过期"; code = ApiCode.TokenExpire; } else msg = "无权访问";
var respObj = new ApiResult(code, msg); var json = JsonConvert.SerializeObject(respObj); ctx.Response.WriteAsync(json); }
return Task.CompletedTask; } }; }); }
if (serviceOption.IsUseConsulReg) { var consulConfig = configuration.GetSection("ConsulConfig").Get<ConsulConfigDto>(); services.AddSingleton(consulConfig); }
if (!EnvUtil.IsProduction) { services.AddSwaggerGen(options => { options.SwaggerDoc(configuration["ProjectPrefix"], new OpenApiInfo { Version = "V1", Title = configuration["ProjectName"] + $"接口文档({EnvUtil.EnvChineseName})", Description = "本文档根据后端接口自动生成,出现在在此页面的接口代表后端已完成", Contact = new OpenApiContact { Name = "天平网", Email = "hr@TianPing.com", Url = new Uri("http://www.tianping898.com") }, License = new OpenApiLicense { Name = "许可声明", Url = new Uri("http://www.tianping898.com") } });
options.AddSecurityDefinition("Bearer", new OpenApiSecurityScheme { Description = "在下框中输入请求头中需要添加Jwt授权Token,格式为(注意中间有个空格):Bearer Token", Name = "Authorization", In = ParameterLocation.Header, Type = SecuritySchemeType.ApiKey, BearerFormat = "JWT", Scheme = "Bearer" });
options.AddSecurityRequirement(new OpenApiSecurityRequirement { { new OpenApiSecurityScheme { Reference = new OpenApiReference { Type = ReferenceType.SecurityScheme, Id = "Bearer" } }, new string[] { } } });
options.OperationFilter<SwaggerOperationFilter>(); options.DocumentFilter<SwaggerHiddenApiFilter>(); options.DocumentFilter<SwaggerEnumFilter>();
var entryXmlFile = $"{Assembly.GetEntryAssembly()?.GetName().Name}.xml"; var entryXmlPath = Path.Combine(AppContext.BaseDirectory, entryXmlFile); if (File.Exists(entryXmlPath)) options.IncludeXmlComments(entryXmlPath, true);
var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml"; var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile); if (File.Exists(xmlPath)) options.IncludeXmlComments(xmlPath, true); }); } }