简体   繁体   中英

Dynamically Changing dll at runtime based on user input

I have to create a C# library to use a third party application which is a COM object. Currently the application is in two versions Version 1 (old) and Version 2 (new) as mention below,

Version 1 (Sample1.dll)

namespace Sample
{
    public interface IApplication 
    {  
        string Version { get; } 
    }
}

Version 2 (Sample2.dll)

namespace Sample
{
   public interface IApplication 
    {  
        string Version { get; } 
    }
}

The ProgID for Sample1.dll is Sample.Application.1 and Sample2.dll is Sample.Application.2 respectively.

Now i want to refer any of the version of dll in my project and use the IApplication interface.

static void Main(string[] args)
{
    int version = 0;
    if (int.TryParse(Console.ReadLine(), out version))
    {
        Type comType = Type.GetTypeFromProgID(String.Format("Sample.Application.{0}", version));
        object item = Activator.CreateInstance(comType);

        IApplication application = item as IApplication;

         Console.WriteLine("Version: {0}", application.Version);
    }
}

The above code works if i refer

1. Sample1.dll and use Sample.Application.1 as ProgID
2. Sample2.dll and use Sample.Application.2 as ProgID

But i want to dynamically change the sample dll based on the ProgID and use the IApplication interface.

Basically i want to write code that support two versions of dll (Sample1.dll and Sample2.dll).

The best solution is make your own proxy class that your code can write against, in the constructor of the proxy you can specify which version you want.

In the below example I went with the easier route of using dynamic , you loose compile time type safety but because every member should be the same name as the proxy member it is easy to just copy and paste the function or property names. Neither Sample1.dll nor Sample2.dll are added as references.

class Program
{
    static void Main(string[] args)
    {
        int version = 0;
        if (int.TryParse(Console.ReadLine(), out version))
        {
            IApplication application = new ApplicationProxy(version);

            Console.WriteLine("Version: {0}", application.Version);
        }
    }
}

/// <summary>
/// A copy of IApplication that is local to your program that holds the shared members.
/// This is what the rest of your program will likely use.
/// </summary>
public interface IApplication
{
    string Version { get; }
}

public class ApplicationProxy : IApplication
{
    private readonly dynamic _application;
    public ApplicationProxy(int version)
    {
        Type comType = Type.GetTypeFromProgID(String.Format("Sample.Application.{0}", version));
        _application = Activator.CreateInstance(comType);
    }

    public string Version
    {
        get { return _application.Version; }
    }
}

You could get rid of dynamic and add both Sample1.dll and Sample2.dll as references using aliases but that will result in much more complex code.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM