twifosp
twifosp

Reputation: 287

Autofac Intercept Target Method

I'm using Autofac.Extras.DynamicProxy2 to perform some method interception on a service implementation.

The service has quite a few methods and I only want to target a few.

Is there a better practice besides than checking for invocation target name against an approved string dictionary of methods I want to intercept?

   public void Intercept(IInvocation invocation)
    {
        invocation.Proceed();
        if (ContinueIntercept(invocation))
        {
            // Do intercept work
        }
    }

    private bool ContinueIntercept(IInvocation invocation)
    {            
        // Logic to compare invocation.MethodInvocationTarget.Name 
    }

It really doesn't add all that much over head, but it still feels like a poor way to do it. Especially since adding this to a specific service implementation means it will intercept all of the method calls of the base class common implementation. It wouldn't be as bad if it only intercepted the derived class.

I see that Castle.DynamicProxy2 has ways to specify invocation target, but I don't see how to wire that up with autofac.

Upvotes: 3

Views: 3565

Answers (1)

Cyril Durand
Cyril Durand

Reputation: 16192

You can use a IProxyGenerationHook to specify on which method the ProxyBuilder should generate a proxy.

public class FooProxyGenerationHook : IProxyGenerationHook
{
    public void MethodsInspected()
    { }

    public void NonProxyableMemberNotification(Type type, MemberInfo memberInfo)
    { }

    public Boolean ShouldInterceptMethod(Type type, MethodInfo methodInfo)
    {
        if (type == typeof(Foo) && methodInfo.Name == "Do")
        {
            return true;
        }
        return false;
    }
}

Then, you can register it this way :

    ProxyGenerator generator = new ProxyGenerator();
    FooProxyGenerationHook hook = new FooProxyGenerationHook();
    IFoo foo = generator.CreateClassProxyWithTarget<Foo>(new Foo(), new ProxyGenerationOptions(hook), new FooInterceptor());

In order to avoid calling the IProxyGenerationHook for each proxy, you should have only one instance of hook.

With DynamicProxy2, you can use this code :

    FooProxyGenerationHook hook = new FooProxyGenerationHook();

    ContainerBuilder builder = new ContainerBuilder();
    builder.RegisterType<FooInterceptor>().AsSelf();
    builder.RegisterType<Foo>().As<IFoo>()
            .EnableClassInterceptors(new ProxyGenerationOptions(hook))
            .InterceptedBy(typeof(FooInterceptor));

Upvotes: 4

Related Questions