Unity.InterceptionExtension.ICallHandler实现一个操作日志记录功能
其它跟上一次一样
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection,Unity.Configuration" />
</configSections>
<unity>
<typeAliases>
<typeAlias alias="IPhone" type="ZEN.Interface.IPhone,ZEN.Interface"></typeAlias >
<typeAlias alias="IWork" type="ZEN.Interface.IWork,ZEN.Interface"></typeAlias >
<typeAlias alias="IPower" type="ZEN.Interface.IPower,ZEN.Interface"></typeAlias >
<typeAlias alias="ICar" type="ZEN.Interface.ICar,ZEN.Interface"></typeAlias >
<typeAlias alias="Phone" type="ZEN.Service.Phone,ZEN.Service"></typeAlias >
<typeAlias alias="Work" type="ZEN.Service.Work,ZEN.Service"></typeAlias >
<typeAlias alias="Power" type="ZEN.Service.Power,ZEN.Service"></typeAlias >
<typeAlias alias="Car" type="ZEN.Service.TeslaCar,ZEN.Service"></typeAlias >
</typeAliases>
<sectionExtension type="Microsoft.Practices.Unity.InterceptionExtension.Configuration.InterceptionConfigurationExtension, Unity.Interception.Configuration" />
<containers>
<container name="testContainer">
<extension type="Interception"/>
<register type="IPhone" mapTo="Phone" />
<register type="IPower" mapTo="Power" />
<register type="ICar" mapTo="Car" name="tesla" >
<property name="work" dependencyType="IWork" />
<property name="phone" dependencyType="IPhone" />
<method name="InitIphone">
<param name="_power" type="IPower" />
<param name="val" type="int" value="33"/>
</method>
<policyInjection></policyInjection>
<interceptor type="InterfaceInterceptor"/>
<!--<interceptionBehavior type="IOC.Common.IOC_AOP.AOP, IOC.Common"/>-->
</register>
<register type="IWork" mapTo="Work" />
</container>
</containers>
</unity>
</configuration>
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Unity.Interception.PolicyInjection.Pipeline;
namespace IOC.Common.IOC_AOP
{
class SimpleCallHandler : ICallHandler
{
public int Order {
get;
set;
}
public IMethodReturn Invoke(IMethodInvocation input, GetNextHandlerDelegate getNext)
{
Console.WriteLine(input.Target.GetType().Name);
return getNext()(input, getNext);
}
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Unity;
using Unity.Interception.PolicyInjection.Pipeline;
using Unity.Interception.PolicyInjection.Policies;
namespace IOC.Common.IOC_AOP
{
public class SimpleCallHandlerAttribute : HandlerAttribute
{
public override ICallHandler CreateHandler(IUnityContainer container)
{
return new SimpleCallHandler() { Order=this.Order};
}
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using IOC.Common.IOC_AOP;
namespace ZEN.Interface
{
public interface ICar
{
[SimpleCallHandler]
void GetName();
void GetPrice();
void GetMaxSpeed();
}
}
对IUnityContainer 进行封装
走指定构造函数
就不需要加特性啦
这样既可完成对象注册的同时对构造函数参数进行注入,此时还有另外一个需求,就是虽然在注册的时候已经对构造函数参数进行了初始化
在Unity中,已经帮我们解决了这个问题,我们可以通过ParameterOverride和ParameterOverrides来实现,其中ParameterOverride是针对一个参数,而ParameterOverrides是针对参数列表,有关注册参数初始化及参数重载的全部代码如下:
》》如果初始化是三个参数的构造函数, Resolve解析,是2个参数,只会替换对应的两个参数。
》》配置文件
using System;
using System.Collections.Generic;
using System.Linq;
using Unity;
using System.Configuration;
using System.IO;
using Microsoft.Practices.Unity.Configuration;
using Unity.Resolution;
namespace IOC.Common.IOC_AOP
{
public class ZenUnityContainerHelper
{
private IUnityContainer container;
public IUnityContainer Container {
private set {
container = value;
}
get {
return Container;
}
}
public ZenUnityContainerHelper()
{
this.container = new UnityContainer() ;
ExeConfigurationFileMap fileMap = new ExeConfigurationFileMap();
fileMap.ExeConfigFilename = Path.Combine(AppDomain.CurrentDomain.BaseDirectory + "CfgFiles\\Unity.Config");//找配置文件的路径
Configuration configuration = ConfigurationManager.OpenMappedExeConfiguration(fileMap, ConfigurationUserLevel.None);
UnityConfigurationSection section = (UnityConfigurationSection)configuration.GetSection(UnityConfigurationSection.SectionName);
section.Configure(container, "testContainer");
}
public T GetServer<T>()
{
return container.Resolve<T>();
}
/// <summary>
///
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="configName">配置文件中指定的name,对于同一个接口,多个实现情况</param>
/// <returns></returns>
public T GetServer<T>(string configName)
{
return container.Resolve<T>(configName);
}
/// <summary>
/// 返回构结函数带参数
/// </summary>
/// <typeparam name="T">依赖对象</typeparam>
/// <param name="parameterList">参数集合(参数名,参数值)</param>
/// <returns></returns>
public T GetServer<T,M>(Dictionary<string, object> parameterList)
{
var list = new ParameterOverrides();
foreach (KeyValuePair<string, object> item in parameterList)
{
list.Add(item.Key, item.Value);
}
return container.Resolve<T>(list.OnType<M>());
}
/// <summary>
/// 返回构结函数带参数
/// </summary>
/// <typeparam name="T">依赖对象</typeparam>
/// <param name="ConfigName">配置文件中指定的文字(没写会报异常)</param>
/// <param name="parameterList">参数集合(参数名,参数值)</param>
/// <returns></returns>
public T GetServer<T,M>(string configName, Dictionary<string, object> parameterList)
{
var list = new ParameterOverrides();
foreach (KeyValuePair<string, object> item in parameterList)
{
list.Add(item.Key, item.Value);
}
return container.Resolve<T>(configName,
list.OnType<M>());
}
}
}
》》》 使用封装
ZenUnityContainerHelper zenContainer= new ZenUnityContainerHelper();
var tesla_car = zenContainer.GetServer<ICar>("tesla");
tesla_car.GetName();
var xiaomi_car = zenContainer.GetServer<ICar>("xiaomi" );
xiaomi_car.GetName();
Dictionary<string, object> parm = new Dictionary<string, object>();
parm.Add("age", "一百");
parm.Add("policy", "遥遥领先");
var xiaomi_car1 = zenContainer.GetServer<ICar,XiaoMICar>("xiaomi2", parm);
xiaomi_car1.GetName();
Console.WriteLine("-----------------------------------");
配置文件
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection,Unity.Configuration" />
</configSections>
<unity>
<typeAliases>
<typeAlias alias="IPhone" type="ZEN.Interface.IPhone,ZEN.Interface"></typeAlias >
<typeAlias alias="IWork" type="ZEN.Interface.IWork,ZEN.Interface"></typeAlias >
<typeAlias alias="IPower" type="ZEN.Interface.IPower,ZEN.Interface"></typeAlias >
<typeAlias alias="ICar" type="ZEN.Interface.ICar,ZEN.Interface"></typeAlias >
<typeAlias alias="Phone" type="ZEN.Service.Phone,ZEN.Service"></typeAlias >
<typeAlias alias="Work" type="ZEN.Service.Work,ZEN.Service"></typeAlias >
<typeAlias alias="Power" type="ZEN.Service.Power,ZEN.Service"></typeAlias >
<typeAlias alias="Car" type="ZEN.Service.TeslaCar,ZEN.Service"></typeAlias >
<typeAlias alias="xiaomi" type="ZEN.Service.XiaoMICar,ZEN.Service"></typeAlias >
</typeAliases>
<sectionExtension type="Microsoft.Practices.Unity.InterceptionExtension.Configuration.InterceptionConfigurationExtension, Unity.Interception.Configuration" />
<containers>
<container name="testContainer">
<extension type="Interception"/>
<register type="IPhone" mapTo="Phone" />
<register type="IPower" mapTo="Power" />
<register type="ICar" mapTo="Car" name="tesla" >
<property name="work" dependencyType="IWork" />
<property name="phone" dependencyType="IPhone" />
<method name="InitIphone">
<param name="_power" type="IPower" />
<param name="val" type="int" value="33"/>
</method>
<policyInjection></policyInjection>
<interceptor type="InterfaceInterceptor"/>
<!--<interceptionBehavior type="IOC.Common.IOC_AOP.AOP, IOC.Common"/>-->
</register>
<register type="ICar" mapTo="xiaomi" name="xiaomi" >
<property name="work" dependencyType="IWork" />
<property name="phone" dependencyType="IPhone" />
<method name="InitIphone">
<param name="_power" type="IPower" />
</method>
<policyInjection></policyInjection>
<interceptor type="InterfaceInterceptor"/>
<!--<interceptionBehavior type="IOC.Common.IOC_AOP.AOP, IOC.Common"/>-->
</register>
<register type="ICar" mapTo="xiaomi" name="xiaomi2" >
<property name="work" dependencyType="IWork" />
<property name="phone" dependencyType="IPhone" />
<method name="InitIphone">
<param name="_power" type="IPower" />
</method>
<constructor>
<param name="age" type="System.String" />
<param name="policy" type="System.String" ></param>
</constructor>
<policyInjection></policyInjection>
<interceptor type="InterfaceInterceptor"/>
<!--<interceptionBehavior type="IOC.Common.IOC_AOP.AOP, IOC.Common"/>-->
</register>
<register type="IWork" mapTo="Work" />
</container>
</containers>
</unity>
</configuration>```