发文章
发文工具
撰写
网文摘手
文档
视频
思维导图
随笔
相册
原创同步助手
其他工具
图片转文字
文件清理
AI助手
留言交流
回到目录
Ioc组件有很多,之前也介绍过autofac,castle等,今天再来说一下在微软Nlayer DDD架构里使用的unity组件,今天主要说一下依靠注入,如果希望看拦截的用法,可以阅读这篇文章第十三回 实现AOP的拦截组件Unity.Interception
unity的用法主要说一下接口注入方法,它包括了程序中注入和配置文件注入,而接口注入还分为普通接口注入和泛型接口注入,下面分别来说一下:
public interface IUser { IQueryable<WebManageUsers> GetEntities(); } public class UserRepository : BackgroundRepository<WebManageUsers>, IUser { public IQueryable<WebManageUsers> GetEntities() { return this.GetModel(); } }
using (IUnityContainer container = new UnityContainer()) { ConfigurationManager.GetSection("unity"); UnityConfigurationSection.CurrentSection.Configure(container); container.RegisterType<IUser, DataTest.UserRepository>(); var repository = container.Resolve<IUser>(); }
<unity xmlns="http://schemas.microsoft.com/practices/2010/unity"> <container> <register type="EntityTest.IUser,EntityTest" mapTo="DataTest.UserRepository, DataTest" /> </container> </unity>
using (IUnityContainer container = new UnityContainer()) { ConfigurationManager.GetSection("unity"); UnityConfigurationSection.CurrentSection.Configure(container); var repository = container.Resolve<IUser>(); }
/// <summary> /// 基础的数据操作规范 /// </summary> /// <typeparam name="TEntity"></typeparam> public interface IRepository<TEntity> where TEntity : class { /// <summary> /// 添加实体并提交到数据服务器 /// </summary> /// <param name="item">Item to add to repository</param> void Insert(TEntity item); /// <summary> /// 移除实体并提交到数据服务器 /// 如果表存在约束,需要先删除子表信息 /// </summary> /// <param name="item">Item to delete</param> void Delete(TEntity item); /// <summary> /// 修改实体并提交到数据服务器 /// </summary> /// <param name="item"></param> void Update(TEntity item); /// <summary> /// 得到指定的实体集合(延时结果集) /// Get all elements of type {T} in repository /// </summary> /// <returns>List of selected elements</returns> IQueryable<TEntity> GetModel(); /// <summary> /// 根据主键得到实体 /// </summary> /// <param name="id"></param> /// <returns></returns> TEntity Find(params object[] id); } public class BackgroundRepository<T> : IRepository<T> where T : class { #region IRepository<TEntity> 成员 public virtual void Insert(TEntity item) { OnBeforeSaved(new SavedEventArgs(item, SaveAction.Insert)); Db.Entry<TEntity>(item); Db.Set<TEntity>().Add(item); this.SaveChanges(); OnAfterSaved(new SavedEventArgs(item, SaveAction.Insert)); } public virtual void Delete(TEntity item) { OnBeforeSaved(new SavedEventArgs(item, SaveAction.Delete)); Db.Set<TEntity>().Attach(item); Db.Set<TEntity>().Remove(item); this.SaveChanges(); OnAfterSaved(new SavedEventArgs(item, SaveAction.Delete)); } public virtual void Update(TEntity item) { OnBeforeSaved(new SavedEventArgs(item, SaveAction.Update)); Db.Set<TEntity>().Attach(item); Db.Entry(item).State = EntityState.Modified; this.SaveChanges(); OnAfterSaved(new SavedEventArgs(item, SaveAction.Update)); } /// <summary> /// 子类在实现时,可以重写,加一些状态过滤 /// </summary> /// <returns></returns> public virtual IQueryable<TEntity> GetModel() { // return Db.Set<TEntity>().AsNoTracking();//对象无法自动添加到上下文中,因为它是使用 NoTracking 合并选项检索的。请在定义此关系之前,将该实体显式附加到 ObjectContext。 return Db.Set<TEntity>();////ObjectStateManager 中已存在具有同一键的对象。ObjectStateManager 无法跟踪具有相同键的多个对象。 } /// <summary> /// 得到原生态结果集 /// </summary> /// <returns></returns> public IQueryable<TEntity> GetEntities() { return Db.Set<TEntity>(); } #endregion }
using (IUnityContainer container = new UnityContainer()) { ConfigurationManager.GetSection("unity"); UnityConfigurationSection.CurrentSection.Configure(container); container.RegisterType<IRepository<User>, BackgroundRepository<User>>(); var re = container.Resolve<IRepository<User>>(); }
<unity xmlns="http://schemas.microsoft.com/practices/2010/unity"> <container> <register type="IRepository.Core.IRepository`1,IRepository.Core" mapTo="DataTest.BackgroundRepository`1, DataTest" /> </container> </unity>
using (IUnityContainer container = new UnityContainer()) { ConfigurationManager.GetSection("unity"); UnityConfigurationSection.CurrentSection.Configure(container); var re = container.Resolve<IRepository<User>>(); }
下面我们封装一个服务定位器,让它把Unity容器封装一下,方便以后调用它,下面是ServiceLocator的原代码:
/// <summary> /// Represents the Service Locator. /// </summary> public sealed class ServiceLocator : IServiceProvider { #region Private Fields private readonly IUnityContainer _container; #endregion #region Private Static Fields private static readonly ServiceLocator instance = new ServiceLocator(); #endregion #region Ctor /// <summary> /// Initializes a new instance of ServiceLocator class. /// </summary> private ServiceLocator() { UnityConfigurationSection section = (UnityConfigurationSection)ConfigurationManager.GetSection("unity"); _container = new UnityContainer(); section.Configure(_container); } #endregion #region Public Static Properties /// <summary> /// Gets the singleton instance of the ServiceLocator class. /// </summary> public static ServiceLocator Instance { get { return instance; } } #endregion #region Private Methods private IEnumerable<ParameterOverride> GetParameterOverrides(object overridedArguments) { List<ParameterOverride> overrides = new List<ParameterOverride>(); Type argumentsType = overridedArguments.GetType(); argumentsType.GetProperties(BindingFlags.Public | BindingFlags.Instance) .ToList() .ForEach(property => { var propertyValue = property.GetValue(overridedArguments, null); var propertyName = property.Name; overrides.Add(new ParameterOverride(propertyName, propertyValue)); }); return overrides; } #endregion #region Public Methods /// <summary> /// Gets the service instance with the given type. /// </summary> /// <typeparam name="T">The type of the service.</typeparam> /// <returns>The service instance.</returns> public T GetService<T>() { return _container.Resolve<T>(); } /// <summary> /// Gets the service instance with the given type by using the overrided arguments. /// </summary> /// <typeparam name="T">The type of the service.</typeparam> /// <param name="overridedArguments">The overrided arguments.</param> /// <returns>The service instance.</returns> public T GetService<T>(object overridedArguments) { var overrides = GetParameterOverrides(overridedArguments); return _container.Resolve<T>(overrides.ToArray()); } /// <summary> /// Gets the service instance with the given type by using the overrided arguments. /// </summary> /// <param name="serviceType">The type of the service.</param> /// <param name="overridedArguments">The overrided arguments.</param> /// <returns>The service instance.</returns> public object GetService(Type serviceType, object overridedArguments) { var overrides = GetParameterOverrides(overridedArguments); return _container.Resolve(serviceType, overrides.ToArray()); } #endregion #region IServiceProvider Members /// <summary> /// Gets the service instance with the given type. /// </summary> /// <param name="serviceType">The type of the service.</param> /// <returns>The service instance.</returns> public object GetService(Type serviceType) { return _container.Resolve(serviceType); } #endregion }
下面再去使用unity时就方便多了,呵呵,看代码:
var model = ServiceLocator.Instance.GetService<IExtensionRepository<WebManageUsers>>().GetModel().ToList();
而使用ServiceLocator还有一个好处,就是不需要使用"实现的程序集",只要有"实现的程序集"复制到WEB项目的BIN目录即可,服务定位器会自己去定位的.
好了,讲到这里也就差不多了,需要注意的是,如果你在项目中进行注入时,需要先注入的实现类所在的程序集也引入进来,否则也是不可以resolve出来对象的,而对于业务层(领域)层来说,不需要关心底层
的实现技术,即不需要引用实现类的程序集,而在业务层引用接口程序集即可.
来自: 昵称10504424 > 《工作》
0条评论
发表
请遵守用户 评论公约
[IoC容器Unity]第一回:Unity预览
IUnityContainer RegisterType(Type from, Type to, string name, LifetimeManager lifetimeManager, params InjectionMember[] injectionMembers);><configuration> <configSections> ...
EF--封装三层架构IOC
Service{ public class StudentService : BaseService,IStudentService { public StudentService(DbContext context) : base(context) {...
C# WPF MVVM开发框架Caliburn.Micro自定义引导程序④
C# WPF MVVM开发框架Caliburn.Micro自定义引导程序④.本例中我们将使用内置容器,但是Caliburn.Micro可以很好地处理任何容器。虽然Caliburn.Micro确实通过引导程序的覆盖和IoC类提供ServiceLocator功能...
OpenStack架构(中文翻译)
OpenStack旗下包含了一组由社区维护的开源项目,他们分别是OpenStack Compute(Nova),OpenStack Object Storage(Swift),以及OpenSt...
Tomcat 系统架构与设计模式,第 1 部分: 工作原理
Tomcat 系统架构与设计模式,第 1 部分: 工作原理Tomcat 系统架构与设计模式,第 1 部分: 工作原理。Tomcat 中组件的生命周期是通过 Lif...
Ioc介绍之Kiss版
Ioc介绍之Kiss版。public class Girl { void kiss(Boy boy){ // kiss boy boy.kiss();IOC type 0:不用IOC public class Girl implements Servicable { private Kissable ...
Tomcat 系统架构与原理剖析
Servlet容器Http服务器2.2. Tomcat Servlet容器处理流程。Tomcat 连接器组件 Coyote3.1. Coyote简介。Tomcat 按照协议和I/O 提供了6个实...
tomcat 源码入门
tomcat代码看似很庞大,但从结构上看却很清晰和简单,它主要由一堆组件组成,如Server、Service、Connector等,并基于JMX管理这些组件,...
深入 Cloud Foundry(一)构架
熟悉CloudFoundry的朋友肯定知道,CloudFoundry给每一个app分配了一个url访问,如果直接使用VMware所托管的CloudFoundry.com的话,那你...
微信扫码,在手机上查看选中内容