我有一个实现两个接口的类,我想对类的方法应用拦截。
我遵循Unity Register two interfaces as one singleton中的建议,但我对结果感到惊讶。简而言之,似乎我的 CallHandler 被调用了两次。我有的最短的例子是这样的:
public interface I1
{
void Method1();
}
public interface I2
{
void Method2();
}
public class C : I1, I2
{
[Log]
public void Method1() {}
public void Method2() {}
}
public class LogAttribute : HandlerAttribute
{
public override ICallHandler CreateHandler(IUnityContainer container)
{
return new LogCallHandler();
}
}
public class LogCallHandler : ICallHandler
{
public IMethodReturn Invoke(
IMethodInvocation input, GetNextHandlerDelegate getNext)
{
Console.WriteLine("Entering " + input.MethodBase.Name);
var methodReturn = getNext().Invoke(input, getNext);
Console.WriteLine("Leaving " + input.MethodBase.Name);
return methodReturn;
}
public int Order { get; set; }
}
void Test()
{
IUnityContainer container = new UnityContainer();
container.AddNewExtension<Interception>();
container.RegisterType<C>(new ContainerControlledLifetimeManager());
container.RegisterType<I1, C>(
new Interceptor<TransparentProxyInterceptor>(),
new InterceptionBehavior<PolicyInjectionBehavior>());
container.RegisterType<I2, C>(
new Interceptor<TransparentProxyInterceptor>(),
new InterceptionBehavior<PolicyInjectionBehavior>());
container.Resolve<I1>().Method1();
}
这给出了这个输出:
Entering Method1
Entering Method1
Leaving Method1
Leaving Method1
删除“container.RegisterType I2, C”行会使日志只出现一次。添加第三个接口 I3,与 I2 类似,会导致日志出现 3 次。
我本来希望日志只被调用一次。我可以通过让 LogCallHandler 检测它是否从另一个 LogCallHandler 调用来实现这一点,但这似乎不优雅。
最初我想将拦截行为应用于 C 而不是分别应用于 I1 和 I2,但这需要 C 从 MarshalByRefObject 继承,这是我还不愿意强加的约束。
有替代方法吗?