日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

关于 项目中Ioc基础模块 的搭建 (已适用于.net core / .net Framework / Nancy)

發布時間:2025/3/15 编程问答 16 豆豆
生活随笔 收集整理的這篇文章主要介紹了 关于 项目中Ioc基础模块 的搭建 (已适用于.net core / .net Framework / Nancy) 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

Ioc?(Inversion of Control, 控制反轉)把創建對象的操作交給框架,亦被稱為?DI(Dependency Injection, 依賴注入)。

為什么叫做 “控制反轉” 呢?之前,我們想要一個對象都是?new?出來的,天天需要?new?對象是不是感覺有點麻煩。有人就想到了,把這些簡單重復的工作也交給框架做。本來需要我們向框架 “射入” 對象,現在框架自己能產生對象了,這不正是?控制反轉?嗎?于是,就有了這個響亮的名字。

本文不做具體概念講解 ,項目采用Autofac作為基礎框架

  關于Autofac的基礎用法可以參照官方的文檔教程 很詳細? 很具體 針對各種版本都有說明? (不要去看各種入門教程 或者翻譯文檔 全是瞎扯淡) https://autofaccn.readthedocs.io/zh/latest/

?

熟悉Ioc的都應該很清楚? 我們常用的操作主要就是兩個ResolverRegistrar

Registrar:

  隨著項目的逐漸增大,我們基本都采用模塊化的方式即?Module? Autofac已經提供了一個基礎的Module 我們可以在其內部里面重寫Load方法即可,但是考慮以后可能還需要做其他擴展所以我們還是提供一個IRegistrar?接口備用?

參照Load方法 我們只提供一個?ContainerBuilder

protected override void Load(ContainerBuilder builder)

Resolver:

  Autofac已經幫我們實現很多場景下的自動Resolver,但是具體的業務情況卻是我們可能需要在自己任意想要的地方去Resolver? ?所以我們需要自己來實現個IResolver

1 public interface IResolver 2 { 3 /// <summary> 4 /// Resolves this instance. 5 /// </summary> 6 /// <typeparam name="T"></typeparam> 7 /// <returns></returns> 8 T Resolve<T>(ILifetimeScope scope = null); 9 10 /// <summary> 11 /// Determines whether this instance is registered. 12 /// </summary> 13 /// <typeparam name="T"></typeparam> 14 /// <returns> 15 /// <c>true</c> if this instance is registered; otherwise, <c>false</c>. 16 /// </returns> 17 bool IsRegistered<T>() where T : class; 18 19 /// <summary> 20 /// Determines whether the specified type is registered. 21 /// </summary> 22 /// <param name="type">The type.</param> 23 /// <param name="scope">The ILifetimeScope</param> 24 /// <returns> 25 /// <c>true</c> if the specified type is registered; otherwise, <c>false</c>. 26 /// </returns> 27 bool IsRegistered(Type type, ILifetimeScope scope = null); 28 29 /// <summary> 30 /// Releases a pre-resolved object. See Resolve methods. 31 /// </summary> 32 /// <param name="obj">Object to be released</param> 33 void Release(object obj); 34 35 /// <summary> 36 /// Resolve 37 /// </summary> 38 /// <typeparam name="T"></typeparam> 39 /// <param name="parameters"></param> 40 /// <param name="scope"></param> 41 /// <returns></returns> 42 T Resolve<T>(IEnumerable<Parameter> parameters, ILifetimeScope scope = null); 43 44 /// <summary> 45 /// Resolve 46 /// </summary> 47 /// <typeparam name="T"></typeparam> 48 /// <param name="parameters"></param> 49 /// <returns></returns> 50 T ResolveParameter<T>(params Parameter[] parameters); 51 52 /// <summary> 53 /// Resolve 54 /// </summary> 55 /// <typeparam name="T"></typeparam> 56 /// <returns></returns> 57 T ResolveName<T>(string name); 58 59 /// <summary> 60 /// Resolve 61 /// </summary> 62 /// <returns></returns> 63 object Resolve(Type type); 64 } View Code

?-------------------------------------------------------------------------------------------------------------------------------------

然后 在.net core 中已經內置了Ioc? 基本代碼如下

1 /// <summary> 2 /// ConfigureServices 3 /// </summary> 4 /// <param name="services"></param> 5 /// <returns></returns> 6 public IServiceProvider ConfigureServices(IServiceCollection services) 7 { 8 } View Code

我們可以知道? .net core 內置的Ioc? 是以?IServiceCollection 為核心,所以 如果我們需要支持.net core版本則需要??IServiceCollection? ?所以我們提供一個?IServiceCollectionResolve

?IServiceCollectionResolve

1 public interface IServiceCollectionResolve 2 { 3 IServiceCollection ServiceCollection { get; set; } 4 5 T ResolveServiceValue<T>() where T : class, new(); 6 } View Code

Autofac 的核心在于?IContainer?所以我們提供一個?IIocManager?

IIocManager?

1 public interface IIocManager : IResolver, IRegistrar, IServiceCollectionResolve 2 { 3 /// <summary> 4 /// Reference to the Autofac Container. 5 /// </summary> 6 IContainer IocContainer { get; set; } 7 8 /// <summary> 9 /// ServiceLocatorCurrent 10 /// </summary> 11 IServiceLocator ServiceLocatorCurrent { get; set; } 12 13 /// <summary> 14 /// SetContainer 15 /// </summary> 16 /// <param name="containerBuilder"></param> 17 void SetContainer(ContainerBuilder containerBuilder); 18 19 /// <summary> 20 /// SetServiceCollection 21 /// </summary> 22 /// <param name="serviceCollection"></param> 23 void SetServiceCollection(IServiceCollection serviceCollection); 24 25 /// <summary> 26 /// UpdateContainer 27 /// </summary> 28 /// <param name="containerBuilder"></param> 29 [Obsolete("Containers should generally be considered immutable. Register all of your dependencies before building/resolving. If you need to change the contents of a container, you technically should rebuild the container. This method may be removed in a future major release.")] 30 void UpdateContainer(ContainerBuilder containerBuilder); 31 } View Code

說明:
IServiceLocator 來源于?CommonServiceLocator? 可以在?nuget?找到? 可以理解為IResolver??

UpdateContainer 官方已經不推薦使用? 可以使用但是盡量避免使用? 主要適用場景是 :已經初始化完成后? 再需要進行二次注冊等操作

?

至此我們所需要的接口基本定義完成。

我們需要一個實現 即?IocManager

1 /// <summary> 2 /// IocManager 3 /// </summary> 4 public class IocManager : IIocManager 5 { 6 /// <summary> 7 /// The Singleton instance. 8 /// </summary> 9 public static IocManager Instance { get; } 10 11 #region ContainerBuilder 12 13 /// <summary> 14 /// ContainerBuilder 15 /// </summary> 16 ContainerBuilder IRegistrar.ContainerBuilder 17 { 18 get => ContainerBuilder; 19 set => ContainerBuilder = value; 20 } 21 22 /// <summary> 23 /// ContainerBuilder 24 /// </summary> 25 public static ContainerBuilder ContainerBuilder { get; set; } 26 27 #endregion 28 29 #region IContainer 30 31 /// <summary> 32 /// IocContainer 33 /// </summary> 34 IContainer IIocManager.IocContainer 35 { 36 get => IocContainer; 37 set => IocContainer = value; 38 } 39 40 /// <summary> 41 /// IocContainer 42 /// </summary> 43 public static IContainer IocContainer { get; set; } 44 45 #endregion 46 47 #region IServiceLocator 48 49 IServiceLocator IIocManager.ServiceLocatorCurrent 50 { 51 get => ServiceLocatorCurrent; 52 set => ServiceLocatorCurrent = value; 53 } 54 55 /// <summary> 56 /// ServiceLocator 57 /// </summary> 58 public static IServiceLocator ServiceLocatorCurrent { get; set; } 59 60 #endregion 61 62 #region IServiceCollection 63 64 IServiceCollection IServiceCollectionResolve.ServiceCollection 65 { 66 get => ServiceCollection; 67 set => ServiceCollection = value; 68 } 69 70 /// <summary> 71 /// ServiceCollection 72 /// </summary> 73 public static IServiceCollection ServiceCollection { get; set; } 74 75 #endregion 76 77 /// <summary> 78 /// IocManager 79 /// </summary> 80 static IocManager() 81 { 82 Instance = new IocManager(); 83 } 84 85 /// <summary> 86 /// SetContainer 87 /// </summary> 88 /// <param name="containerBuilder"></param> 89 public void SetContainer(ContainerBuilder containerBuilder) 90 { 91 ContainerBuilder = containerBuilder; 92 var container = containerBuilder.Build(); 93 IocContainer = container; 94 95 //設置定位器 96 ServiceLocatorCurrent = new AutofacServiceLocator(IocContainer); 97 } 98 99 /// <summary> 100 /// SetServiceCollection 101 /// </summary> 102 /// <param name="serviceCollection"></param> 103 public void SetServiceCollection(IServiceCollection serviceCollection) 104 { 105 ServiceCollection = serviceCollection; 106 } 107 108 /// <summary> 109 /// UpdateContainer 110 /// </summary> 111 /// <param name="containerBuilder"></param> 112 [Obsolete("Containers should generally be considered immutable. Register all of your dependencies before building/resolving. If you need to change the contents of a container, you technically should rebuild the container. This method may be removed in a future major release.")] 113 public void UpdateContainer(ContainerBuilder containerBuilder) 114 { 115 ContainerBuilder = containerBuilder; 116 containerBuilder?.Update(IocContainer); 117 } 118 119 /// <summary> 120 /// resolve T by lifetime scope 121 /// </summary> 122 /// <typeparam name="T"></typeparam> 123 /// <param name="scope"></param> 124 /// <returns></returns> 125 public T Resolve<T>(ILifetimeScope scope = null) 126 { 127 if (scope == null) 128 { 129 scope = Scope(); 130 } 131 return scope.Resolve<T>(); 132 } 133 134 /// <summary> 135 /// Resolve 136 /// </summary> 137 /// <typeparam name="T"></typeparam> 138 /// <param name="parameters"></param> 139 /// <param name="scope"></param> 140 /// <returns></returns> 141 public T Resolve<T>(IEnumerable<Parameter> parameters, ILifetimeScope scope = null) 142 { 143 if (scope == null) 144 { 145 scope = Scope(); 146 } 147 return scope.Resolve<T>(parameters); 148 } 149 150 /// <summary> 151 /// Resolve 152 /// </summary> 153 /// <typeparam name="T"></typeparam> 154 /// <param name="parameters"></param> 155 /// <returns></returns> 156 public T ResolveParameter<T>(Parameter[] parameters) 157 { 158 var scope = Scope(); 159 return scope.Resolve<T>(parameters); 160 } 161 162 /// <summary> 163 /// ResolveName 164 /// </summary> 165 /// <typeparam name="T"></typeparam> 166 /// <returns></returns> 167 public T ResolveName<T>(string name) 168 { 169 var scope = Scope(); 170 var item = scope.ResolveNamed<T>(name); 171 return item; 172 } 173 174 /// <summary> 175 /// 176 /// </summary> 177 /// <param name="type"></param> 178 /// <returns></returns> 179 public object Resolve(Type type) 180 { 181 var scope = Scope(); 182 var item = scope.Resolve(type); 183 return item; 184 } 185 186 /// <summary> 187 /// IsRegistered 188 /// </summary> 189 /// <typeparam name="T"></typeparam> 190 /// <returns></returns> 191 public bool IsRegistered<T>() where T : class 192 { 193 return IsRegistered(typeof(T)); 194 } 195 196 /// <summary> 197 /// IsRegistered 198 /// </summary> 199 /// <param name="type"></param> 200 /// <param name="scope"></param> 201 /// <returns></returns> 202 public bool IsRegistered(Type type, ILifetimeScope scope = null) 203 { 204 if (scope == null) 205 { 206 scope = Scope(); 207 } 208 209 return scope.IsRegistered(type); 210 } 211 212 /// <summary> 213 /// release object lifetimescope 214 /// </summary> 215 /// <param name="obj"></param> 216 public void Release(object obj) 217 { 218 } 219 220 /// <summary> 221 /// create ILifetimeScope from container 222 /// </summary> 223 /// <returns></returns> 224 private static ILifetimeScope Scope() 225 { 226 return IocContainer.BeginLifetimeScope(); 227 } 228 229 /// <summary> 230 /// ResolveServiceValue 231 /// </summary> 232 /// <typeparam name="T"></typeparam> 233 /// <returns></returns> 234 public T ResolveServiceValue<T>() where T : class, new() 235 { 236 return ServiceCollection.ResolveServiceValue<T>(); 237 } 238 } View Code

說明:

主要依賴于:

?

這些全部完成后 我們需要一個最終的裝載程序??Bootstrap

1 /// <summary> 2 /// 初始化裝載程序 3 /// </summary> 4 public class Bootstrap 5 { 6 /// <summary> 7 /// _isInit 8 /// </summary> 9 private static bool _isInit; 10 11 /// <summary> 12 /// _iocManager 13 /// </summary> 14 public IIocManager IocManager { get; set; } 15 16 /// <summary> 17 /// StartupModule 18 /// </summary> 19 public Type StartupModule { get; set; } 20 21 /// <summary> 22 /// Instance 23 /// </summary> 24 /// <returns></returns> 25 public static Bootstrap Instance<TStartupModule>() where TStartupModule : WorkDataBaseModule 26 { 27 return new Bootstrap(typeof(TStartupModule)); 28 } 29 30 /// <summary> 31 /// instance bootstrap 32 /// </summary> 33 /// <returns></returns> 34 public static Bootstrap Instance() 35 { 36 return new Bootstrap(); 37 } 38 39 /// <summary> 40 /// Bootstrap 41 /// </summary> 42 public Bootstrap() : this(Dependency.IocManager.Instance) 43 { 44 } 45 46 /// <summary> 47 /// Bootstrap 48 /// </summary> 49 public Bootstrap(Type startupModule) : this(startupModule, Dependency.IocManager.Instance) 50 { 51 } 52 53 /// <summary> 54 /// Bootstrap 55 /// </summary> 56 /// <param name="iocManager"></param> 57 public Bootstrap(IIocManager iocManager) 58 { 59 IocManager = iocManager; 60 } 61 62 /// <summary> 63 /// Bootstrap 64 /// </summary> 65 /// <param name="startupModule"></param> 66 /// <param name="iocManager"></param> 67 public Bootstrap(Type startupModule, IIocManager iocManager) 68 { 69 StartupModule = startupModule; 70 IocManager = iocManager; 71 } 72 73 /// <summary> 74 /// 初始化集成框架(配置方式) 75 /// </summary> 76 [STAThread] 77 public void InitiateConfig(IServiceCollection services, List<string> paths) 78 { 79 if (_isInit) return; 80 var builder = new ContainerBuilder(); 81 82 #region RegisterConfig 83 var config = new ConfigurationBuilder(); 84 config.SetBasePath(AppDomain.CurrentDomain.BaseDirectory); 85 if (paths != null) 86 { 87 foreach (var item in paths) 88 { 89 config.AddJsonFile(item); 90 } 91 } 92 93 var module = new ConfigurationModule(config.Build()); 94 builder.RegisterModule(module); 95 96 #endregion 97 98 //注入初始module 99 builder.RegisterModule(new WorkDataModule()); 100 101 IocManager.SetServiceCollection(services); 102 103 builder.Populate(services); 104 105 IocManager.SetContainer(builder); 106 _isInit = true; 107 } 108 109 /// <summary> 110 /// InitiateConfig 111 /// </summary> 112 /// <param name="paths"></param> 113 public void InitiateConfig(List<string> paths) 114 { 115 if (_isInit) return; 116 var builder = new ContainerBuilder(); 117 118 #region RegisterConfig 119 var config = new ConfigurationBuilder(); 120 config.SetBasePath(AppDomain.CurrentDomain.BaseDirectory); 121 if (paths != null) 122 { 123 foreach (var item in paths) 124 { 125 config.AddJsonFile(item); 126 } 127 } 128 129 var module = new ConfigurationModule(config.Build()); 130 builder.RegisterModule(module); 131 132 #endregion 133 134 //注入初始module 135 builder.RegisterModule(new WorkDataModule()); 136 137 IocManager.SetContainer(builder); 138 _isInit = true; 139 } 140 141 /// <summary> 142 /// UpdateContainer 143 /// </summary> 144 /// <param name="services"></param> 145 [Obsolete("Containers should generally be considered immutable. Register all of your dependencies before building/resolving. If you need to change the contents of a container, you technically should rebuild the container. This method may be removed in a future major release.")] 146 public void CoreUpdateContainer(IServiceCollection services) 147 { 148 var builder = new ContainerBuilder(); 149 builder.Populate(services); 150 IocManager.UpdateContainer(builder); 151 } 152 153 154 } View Code

?

這樣我們整體的架子就算初步完成了??

擴展

1.隨著項目逐漸增大 我們會有很多很多的接口? 去進行注入? 我們? 希望通過反射的方式進行注入? 所以我們提供一個?ITypeFinder 方便進行操作

注:??ITypeFinder? 來源于?nopcommerce

代碼位置 :

https://github.com/wulaiwei/WorkData.Core/tree/master/WorkData/WorkData/Extensions/TypeFinders

2. 在?.net Framework? autofac 針對常量的配置 我們可以采用屬性注入的方式完成? ,但是針對.net core版本 不推薦采用 屬性注入? ,推薦使用core 自帶的文件注入方式

1 public Startup(IHostingEnvironment env) 2 { 3 var builder = new ConfigurationBuilder() 4 .SetBasePath(env.ContentRootPath) 5 .AddJsonFile("Config/appsettings.json", optional: true, reloadOnChange: true) 6 .AddJsonFile($"Config/appsettings.{env.EnvironmentName}.json", optional: true) 7 .AddEnvironmentVariables(); 8 this.Configuration = builder.Build(); 9 } View Code

有個參數選項? 為?reloadOnChange: true? 即修改后會自動重新加載 ,然后注入至?IServiceCollection既可以

我們可以采用IocManager 進行?Resolve 但是你就立馬會遇到很尷尬的問題? 加入我還沒注入完成 我就需要這個對象呢? ?

例如? 加入我需要使用JWT

1 services.AddAuthentication(options => 2 { 3 //認證middleware配置 4 options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme; 5 options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme; 6 }) 7 .AddJwtBearer(o => 8 { 9 //主要是jwt token參數設置 10 o.TokenValidationParameters = new TokenValidationParameters 11 { 12 //Token頒發機構 13 ValidIssuer = workDataBaseJwt.Issuer, 14 //頒發給誰 15 ValidAudience = workDataBaseJwt.Audience, 16 //這里的key要進行加密,需要引用Microsoft.IdentityModel.Tokens 17 IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(workDataBaseJwt.SecretKey)), 18 //ValidateIssuerSigningKey=true, 19 ////是否驗證Token有效期,使用當前時間與Token的Claims中的NotBefore和Expires對比 20 ValidateLifetime = true, 21 ////允許的服務器時間偏移量 22 ClockSkew = TimeSpan.Zero 23 }; 24 }); View Code

然后就需要這個對象?workDataBaseJwt? 所以? 我們這邊需要對?IServiceCollection? 做個擴展

1 public static class WorkDataServiceCollection 2 { 3 public static T ResolveServiceValue<T>(this IServiceCollection services) where T : class, new() 4 { 5 try 6 { 7 var provider = services.BuildServiceProvider(); 8 var entity = provider.GetRequiredService<IOptions<T>>().Value; 9 return entity; 10 } 11 catch (Exception) 12 { 13 return default(T); 14 } 15 } 16 } View Code

這樣我就可以在注入之前進行Resolve? ? 即:

1 services.Configure<WorkDataBaseJwt>(Configuration.GetSection("WorkDataBaseJwt")); 2 services.Configure<WorkDataDbConfig>(Configuration.GetSection("WorkDataDbContextConfig")); 3 services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>(); 4 services.AddTransient<IPrincipal>(provider => 5 provider.GetService<IHttpContextAccessor>().HttpContext.User); 6 7 var workDataBaseJwt = services.ResolveServiceValue<WorkDataBaseJwt>(); View Code

最后推薦使用? ?json? 進行模塊注冊

1 { 2 "modules": [ 3 { 4 "type": "WorkData.Web.WorkDataWebModule,WorkData.Web" 5 }, 6 { 7 "type": "WorkData.Domain.EntityFramework.DomainEntityFrameworkModule,WorkData.Domain.EntityFramework" 8 }, 9 { 10 "type": "WorkData.EntityFramework.EntityFrameworkModule,WorkData.EntityFramework" 11 }, 12 { 13 "type": "WorkData.Code.WorkDataCodeModule,WorkData.Code" 14 } 15 ] 16 } View Code

關于在.net core 版本下的完整使用? 可以參考? :

https://github.com/wulaiwei/WorkData.Core/tree/master/WorkData/WorkData.Web

?最后針對Nancy? ?WorkData的使用?

主要依賴于

using Autofac;
using Nancy;
using Nancy.Bootstrapper;
using Nancy.Bootstrappers.Autofac;

1 public class WorkDataAutofacNancyBootstrapper : AutofacNancyBootstrapper 2 { 3 /// <summary> 4 /// Gets a reference to the <see cref="Bootstrap" /> instance. 5 /// </summary> 6 public static Bootstrap BootstrapWarpper { get; } = Bootstrap.Instance(); 7 8 private readonly ILogService _logService; 9 10 static WorkDataAutofacNancyBootstrapper() 11 { 12 BootstrapWarpper.InitiateConfig(); 13 } 14 15 public WorkDataAutofacNancyBootstrapper() 16 { 17 _logService = BootstrapWarpper.IocManager.Resolve<ILogService>(); 18 } 19 20 protected override ILifetimeScope GetApplicationContainer() 21 { 22 return BootstrapWarpper.IocManager.IocContainer; 23 } 24 25 protected override void ConfigureApplicationContainer(ILifetimeScope container) 26 { 27 var builder = new ContainerBuilder(); 28 builder.RegisterType<CustomJsonNetSerializer>().As<ISerializer>(); 29 builder.RegisterType<UserMapper>().As<IUserMapper>(); 30 31 BootstrapWarpper.IocManager.UpdateContainer(builder); 32 } 33 34 protected override void RequestStartup(ILifetimeScope container, IPipelines pipelines, NancyContext context) 35 { 36 base.RequestStartup(container, pipelines, context); 37 38 #region 攔截器 39 40 pipelines.BeforeRequest += ctx => 41 { 42 var logRequest = new LogRequest 43 { 44 Url = context.Request.Url, 45 Form = JsonConvert.SerializeObject(context.Request.Form), 46 Query = JsonConvert.SerializeObject(context.Request.Query), 47 Method = context.Request.Method, 48 Body = context.Request.Body.AsString(), 49 Key = Guid.NewGuid().ToString(), 50 CreateTime = DateTime.Now, 51 CreateUserId = ctx.GetUserIdentity()?.UserId 52 }; 53 _logService.AddRequestIndex(logRequest); 54 return null; 55 }; 56 pipelines.AfterRequest += ctx => { }; 57 pipelines.OnError += (ctx, ex) => 58 { 59 var logRequestError = new LogRequestError 60 { 61 Url = context.Request.Url, 62 ErrorMessage = ex.Message, 63 Key = Guid.NewGuid().ToString(), 64 CreateTime=DateTime.Now, 65 CreateUserId= ctx.GetUserIdentity()?.UserId 66 }; 67 _logService.AddRequestErrorIndex(logRequestError); 68 69 return null; 70 }; 71 72 #endregion 73 } 74 75 protected override void ApplicationStartup(ILifetimeScope container, IPipelines pipelines) 76 { 77 base.ApplicationStartup(container, pipelines); 78 DiagnosticsHook.Disable(pipelines); 79 80 pipelines.AfterRequest += ctx => 81 { 82 ctx.Response.Headers.Add("Access-Control-Allow-Origin", "*"); 83 ctx.Response.Headers.Add("Access-Control-Allow-Credentials", "true"); 84 ctx.Response.Headers.Add("Access-Control-Allow-Methods", "POST,GET"); 85 ctx.Response.Headers.Add("Access-Control-Allow-Headers", "Content-Type,Access-Token"); 86 ctx.Response.Headers.Add("Access-Control-Expose-Headers", "*"); 87 }; 88 89 #region Authentication 90 var configuration = new StatelessAuthenticationConfiguration( 91 nancyContext => 92 { 93 //返回null代碼token無效或用戶未認證 94 var token = nancyContext.Request.Headers.Authorization; 95 if (string.IsNullOrEmpty(token)) 96 return null; 97 var userValidator = BootstrapWarpper.IocManager.Resolve<IUserMapper>(); 98 99 var userIdentity = userValidator.GetUserFromAccessToken(token); 100 101 return userIdentity; 102 } 103 ); 104 StatelessAuthentication.Enable(pipelines, configuration); 105 #endregion 106 107 //啟用Session 108 //CookieBasedSessions.Enable(pipelines); 109 110 base.ApplicationStartup(container, pipelines); 111 } 112 113 /// <summary> 114 /// RootPathProvider 115 /// </summary> 116 protected override IRootPathProvider RootPathProvider => 117 new WorkDataRootPathProvider(); 118 119 /// <summary> 120 /// 配置靜態文件訪問權限 121 /// </summary> 122 /// <param name="conventions"></param> 123 protected override void ConfigureConventions(NancyConventions conventions) 124 { 125 base.ConfigureConventions(conventions); 126 127 //靜態文件夾訪問 設置 css,js,image 128 conventions.StaticContentsConventions.AddDirectory("Contents"); 129 } 130 } View Code

推薦 下Nancy? ? 雖然 有.net? core 但是? 如果你用Nancy? 后會發現 兩者會有很多相似之處

最主要還是相當 輕量級? 可以高度的自定義? ?

?

轉載于:https://www.cnblogs.com/wulaiwei/p/9389736.html

總結

以上是生活随笔為你收集整理的关于 项目中Ioc基础模块 的搭建 (已适用于.net core / .net Framework / Nancy)的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 美女隐私免费 | 最新黄色网址在线观看 | 久久久精选 | 国产又粗又猛又色又 | 亚洲最大在线 | 丁香五香天堂 | xxx麻豆| 婷婷六月综合网 | 日日日夜夜操 | 黄色一级一片 | 亚洲激情视频网站 | 国产欧美精品一区二区三区 | 精品国产乱码久久久久久久软件 | 五月激情丁香 | 污污内射久久一区二区欧美日韩 | 欧美精品一区二区免费看 | 一区二区三区高清不卡 | 青青草久久伊人 | 欧美67194| 日本黄色xxxx | 91视频看| 传媒一区二区 | 久久久久久久久久久久久久国产 | 美女视频久久 | 97精品一区二区三区 | 又黄又爽视频在线观看 | 亚洲乱码一区 | 中文字幕在线观看亚洲 | 夜色一区二区 | 欧美国产二区 | 中文字幕亚洲区 | 久久不射网站 | 影音先锋国产在线 | 手机看片日韩久久 | av直播在线观看 | 女人十八毛片嫩草av | 色欲亚洲Av无码精品天堂 | 少妇按摩一区二区三区 | 澳门一级黄色片 | 狠狠插av | 开元在线观看视频国语 | 精品亚洲一区二区三区 | 麻豆最新 | 9久久9毛片又大又硬又粗 | 魔性诱惑 | aise爱色av| 亚洲天堂精品一区 | 男女免费视频 | 污版视频在线观看 | 国产福利免费 | 午夜精品久久久久久久 | 三级黄网| 中文字幕亚洲成人 | 色网av| 国产精品伊人久久 | 精品小视频在线观看 | 天天色综合天天 | 亚洲国产精品99 | www99re| 做a爰小视频| 高清成人免费视频 | 伊人青青 | 欧美美女在线 | 欧美日韩加勒比 | 91精品久久久久久久99蜜桃 | 69视频国产 | wwwxx欧美 | 午夜日韩视频 | 国产传媒av | 亚洲成人网在线 | 美女xx00| 美女网站在线免费观看 | 182av| 九九热这里只有精品6 | 中文字幕中文在线 | 第一次破处视频 | 国产大学生自拍视频 | 亚洲综合伊人久久 | 欧美国产视频一区 | 91玉足脚交白嫩脚丫 | 99久久99久久 | 日韩视频网址 | 九九视频这里只有精品 | 精品国产av 无码一区二区三区 | 伊人午夜 | 天堂影视av| 五月天久久| 合欢视频在线观看 | 在线免费观看www | 久久久久国产综合av天堂 | 激情视频在线观看免费 | 一区小视频| 久久免费国产精品 | 欧美日韩在线视频免费观看 | 国产精品久久久无码一区 | 日本熟妇一区二区 | 国产在线观看免费高清 | 亚洲精品第五页 | 久草影视在线观看 |