Search code examples
.net-coreunity-containerinterception

Unity InterfacesInterceptor in .NET Core


I'll start out with the questions first and follow up with context:

  1. Is there a version of Unity.Interception available that is compatible with .NET Core?
  2. Is there a .NET Core compatible alternative to Unity.Interception?

I am looking at using the Microsoft.Practices.Unity.InterceptionExtension.InterfaceInterceptor to short-circuit calls to certain interfaces (example code below), but it seems that the suggested NuGet package, Unity.Interception 4.0.1, is not compatible with .NET Core.

I have made an attempt to shoe-horn in the usage of Unity.Interception 4.0.1, as the code snippets used works fine in classic .NET; but as mentioned I am running into problems with .NET Core:

Install-Package : Package Unity.Interception 4.0.1 is not compatible with netcoreapp1.1 (.NETCoreApp,Version=v1.1). Package Unity.Interception 4.0.1 supports: net45 (.NETFramework,Version=v4.5 )

I tried to circumvent this by adding net451 to the PackageTargetFallback list:

<PackageTargetFallback>$(PackageTargetFallback);net451;dnxcore50;portable-net451+win8</PackageTargetFallback>

This allowed me to install the package, but it then complains something fierce about needing a reference to mscorlib:

Error CS0012
The type 'Type' is defined in an assembly that is not referenced. You must add a reference to assembly 'mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.

I'm not going to attempt to reference in the Classic .NET framework into a .NET Core application, so I'm pretty much at a dead end here.

Example code:

public class Interceptions
{
    public static object CreateCustomInterceptedProxy(Type type)
    {
        var interceptor = new InterfaceInterceptor();

        var proxy = interceptor.CreateProxy(type, null);

        var interceptionBehavior = new CustomInterceptionBehavior();

        proxy.AddInterceptionBehavior(interceptionBehavior);

        return proxy;
    }
}

public class CustomInterceptionBehavior : IInterceptionBehavior
{
    public IMethodReturn Invoke(IMethodInvocation input, GetNextInterceptionBehaviorDelegate getNext)
    {
        object response = null; // replace with stuff that builds an actual object

        return input.CreateMethodReturn(response, new object[] { });
    }

    public IEnumerable<Type> GetRequiredInterfaces()
    {
        return Type.EmptyTypes;
    }

    public bool WillExecute => true;
}

Solution

  • It seems Castle.Core's DynamicProxy is what I needed:

    using Castle.DynamicProxy;
    
    public class CustomInterceptor : IInterceptor
    {
        public static object CreateCustomInterceptedProxy(Type type)
        {
            var proxyGenerator = new ProxyGenerator();
    
            var interceptor = new Interceptor();
    
            var proxy = proxyGenerator.CreateInterfaceProxyWithoutTarget(type, interceptor);
    
            return proxy;
        }
    }
    
    public class CustomInterceptor : IInterceptor
    {
        public void Intercept(IInvocation invocation)
        {
            object returnValue; // Do stuff to populate return value
    
            invocation.ReturnValue = returnValue;
        }
    }