Why won't DynamicProxy's interceptor get called for *each* virtual method call?

*爱你&永不变心* 提交于 2019-12-03 03:25:37

Looks like my guess was right.

I tried the same example, only this time creating the proxy directly from the class type:

Main(){

  //proxy-ing an explicit type
  A proxy = (A) new Castle.DynamicProxy.ProxyGenerator()
                 .CreateClassProxy<A>(new Interceptor());
  proxy.foo();

}

The result was what I expected in the first place:

Intercepted foo
foo
Intercepted bar
bar

This leads me to the following conclusion:

  • when creating a proxy from an interface, it uses composition to delegate calls to the implementation
  • when creating a proxy from a (class) type, it inherits from the type, so all virtual calls in the class type will call the overridden methods in the proxy.

When creating an interface proxy with an interface implementation, the generated proxy looks something like this:

class InterfaceProxy: IA { //implements interface
  IA m_impl;
  [...]

  Proxy(IA i_impl){
    m_impl = i_impl;
  }
  public void foo(){
    //overly-simplified, but you get the picture
    InvokeInterceptors("foo");

    //execution gets here when calling 'invocation.Proceed()' 
    //from the interceptor

    m_impl.foo();  //pass the execution to the implementation; 
                   //the proxy has no more control over what gets executed.

  }
  public void bar(){
    InvokeInterceptors("bar");
    m_impl.bar();
  }
}

When creating a class proxy, the code looks like this:

class ClassProxy: A { //inherits class type

  Proxy(): base() { ... }

  public override void foo(){
    InvokeInterceptors("foo");

    //execution gets here when calling 'invocation.Proceed()' 
    //from the interceptor

    base.foo();  //pass the execution to the base class 

  }
  public void bar(){
    InvokeInterceptors("bar");
    base.bar();
  }
}

You're using the method CreateInterfaceProxyWithTarget which instructs the proxy builder to create a proxy for the interface and forward the calls to the target object, so what you're seeing is what you've asked it to do.

If you want the proxy to derive from your class then you'd need to use the CreateClassProxy method instead.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!