Search code examples
c#.netproxyruntimecil

Create a class to implement interface (like a proxy class) at runtime


First I'm using Visual Studio 2005 with .NET Framework 2.0. Unfortunately, I can't use a recent version of VS/.NET.

I need to be able to create a class at runtime that inherits another class and also implements a certain interface. The thing is that the class that needs to be inherited has the sames method signatures of the interface.

For example:

public interface ITestInterface
{
    void Test1();
    string Test2(int a, string b);
}

public class TestClass
{
    public void Test1() { ... }
    public string Test2(int a, string b) { ... }
    public void AnotherMethod() { ... }
}

If I create another class, for example:

public class AnotherClass : TestClass, ITestInterface
{
}

In Visual Studio 2005, it gets compiled with no problems as TestClass already implements all the interface's methods/functions.

If I inspect the generated MSIL code for this class, I can see that it creates a type called AnotherClass that inherits from TestClass and implements ITestInterface as I would expect (no methods/functions implemented as they are already implemented in the base class).

Trying to do this by code at runtime like this:

object GetProxy(Type iface, Type obj)
{
    string name = obj.Name + "Proxy";
    AssemblyBuilder assyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(new AssemblyName(name), AssemblyBuilderAccess.Run);
    ModuleBuilder modBuilder = assyBuilder.DefineDynamicModule(name);
    TypeBuilder typeBuilder = modBuilder.DefineType(name, TypeAttributes.Public | TypeAttributes.AutoClass | TypeAttributes.AnsiClass | TypeAttributes.BeforeFieldInit, obj, new Type[] { iface });

    Type proxyType = typeBuilder.CreateType(); // Exception here

    return Activator.CreateInstance(proxyType);
}

Throws the following exception:

An unhandled exception of type 'System.TypeLoadException' occurred in mscorlib.dll

Additional information: Method 'Test1' in type 'TestClassProxy' from assembly 'TestClassProxy, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null' does not have an implementation.

I can't figure out why the runtime is forcing me to implement the methods of the interface if they are already implemented in the base class.

Do you have some ideas? Maybe an option I'm missing?


Solution

  • Based on the information found in this link and this one suggested by Brian, marking the base class methods/functions as virtual solves this particular problem.

    I know this imposes a requirement for base classes but that's acceptable in my case.