• .NET: 如何通过AppDomain动态加载插件程序


    这是今天课堂上的一个小例子程序

    1. 接口

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace Interfaces
    {
        public interface IPlugin
        {
            void Run();
        }
    }
    

    2. 插件

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace PluginLib
    {
        [Serializable]
        public class Plugin:Interfaces.IPlugin
        {
            public void Run() {
                Console.WriteLine("插件在运行");
            }
    
    
        }
    }
    

    3. 主程序

                AppDomain plugindomain = AppDomain.CreateDomain("PluginDomain");
    
                #region 使用接口的方式来动态执行方法
                Interfaces.IPlugin plugin = (Interfaces.IPlugin)plugindomain.CreateInstanceFromAndUnwrap("PluginLib.dll", "PluginLib.Plugin");
    
                plugin.Run();
    
    
                Console.WriteLine("在插件程序域中加载的程序集");
                foreach (var item in plugindomain.GetAssemblies())
                {
                    Console.WriteLine(item.FullName);
                }
                #endregion

    结果如下

    image

    注意:这种方式加载的插件,里面的类型必须声明可序列化([Serializable] ),否则就会出现下面的错误

    image

    但是,如果插件真的没有声明可序列化,是不是就没有办法呢?也不是这么说

    4. 在主程序中添加一个TypeLoader

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    using System.Reflection;
    using System.IO;
    
    namespace _08_AppDomain_ServiceSample
    {
        [Serializable]
        public class TypeLoader
        {
            public Assembly LoadAssembly(string path) {
                return Assembly.LoadFile(Path.Combine(Environment.CurrentDirectory, path));
            }
        }
    }
    

    5. 修改代码,利用TypeLoader作为中间人,去动态加载那些插件程序集

                #region 使用加载代理的方式
                TypeLoader loader = (TypeLoader)plugindomain.CreateInstanceFromAndUnwrap("08_AppDomain_ServiceSample.exe", typeof(TypeLoader).FullName);
                Interfaces.IPlugin plugin = (Interfaces.IPlugin)loader.LoadAssembly("PluginLib.dll").CreateInstance("PluginLib.Plugin");
                plugin.Run();
                Console.WriteLine("在插件程序域中加载的程序集");
                foreach (var item in plugindomain.GetAssemblies())
                {
                    Console.WriteLine(item.FullName);
                }
    
                AppDomain.Unload(plugindomain);
    
                #endregion

    image

  • 相关阅读:
    ASP 禁止页面被缓存
    关于学习编程的一点想法
    今天下午做的一个关于web前端性能/性能测试的Talk
    错误植入法与老祖宗的智慧
    关闭sitwithwhom.51.net
    让Pywinauto支持中文菜单
    勤学与好问
    LoadRunner 的 web_set_user 函数
    有奖调查——《软件性能测试过程详解与案例剖析》第二版内容调查
    论“响应时间”
  • 原文地址:https://www.cnblogs.com/chenxizhang/p/1625953.html
Copyright © 2020-2023  润新知