2

我在一个程序集中有以下代码:

namespace MyLibrary
{
    class InternalClass
    {
        public event EventHandler<MyArgs> MyEvent;

        public void RaiseMyEvent()
        {
            MyEvent(this, new MyArgs());
        }
    }

    class MyArgs : EventArgs
    {
    }
}

以及另一个程序集中的以下代码:

namespace MyApp
{
    class Program
    {
        static void Main()
        {
            var assembly = Assembly.LoadFrom(@"C:\path\to\MyLibrary.dll");
            var types = assembly.GetTypes();
            var internalClassType = types.FirstOrDefault(t => t.FullName == "MyLibrary.InternalClass");
            var eventInfo = internalClassType.GetEvent("MyEvent");

            var internalClass = Activator.CreateInstance(internalClassType);
            eventInfo.AddEventHandler(internalClass,
                Delegate.CreateDelegate(eventInfo.EventHandlerType, typeof(Program), "MyHandler"));

            internalClassType.GetMethod("RaiseMyEvent").Invoke(internalClass, new object[0]);
        }

        public static void MyHandler(object sender, EventArgs e)
        {
        }
    }
}

但是,我在以下位置得到以下异常Delegate.CreateDelegate无法绑定到目标方法,因为它的签名或安全透明度与委托类型的签名或安全透明度不兼容。

第一个程序集中的类型是内部的,不能更改,也不能授予朋友程序集对第二个程序集的访问权限。

我尝试通过以下方式动态创建方法:

namespace MyApp
{
    class Program
    {
        static void Main()
        {
            var assembly = Assembly.LoadFrom(@"C:\path\to\MyLibrary.dll");
            var types = assembly.GetTypes();
            var internalClassType = types.FirstOrDefault(t => t.FullName == "MyLibrary.InternalClass");
            var myArgsType = types.FirstOrDefault(t => t.FullName == "MyLibrary.MyArgs");
            var eventInfo = internalClassType.GetEvent("MyEvent");

            var methodInfo = typeof(Program).GetMethod("MyHandler");
            var method = new DynamicMethod("MyHandlerImpl", null, new[] { typeof(object), myArgsType });
            var generator = method.GetILGenerator();
            generator.Emit(OpCodes.Ldarg_0);
            generator.Emit(OpCodes.Ldarg_1);
            generator.Emit(OpCodes.Call, methodInfo);
            generator.Emit(OpCodes.Ret);

            var internalClass = Activator.CreateInstance(internalClassType);
            eventInfo.AddEventHandler(internalClass, method.CreateDelegate(eventInfo.EventHandlerType));

            internalClassType.GetMethod("RaiseMyEvent").Invoke(internalClass, new object[0]);
        }

        public static void MyHandler(object sender, EventArgs e)
        {
        }
    }
}

但是,我在以下位置收到以下异常MethodBase.Invoke尝试通过方法“DynamicClass.MyHandlerImpl(System.Object, MyLibrary.MyArgs)”访问类型“MyLibrary.MyArgs”失败。

当我无权访问 EventArgs 类型时,有什么方法可以处理事件?

4

1 回答 1

1

其实,我想通了。

我变了

var method = new DynamicMethod("MyHandlerImpl", null, new[] { typeof(object), myArgsType });

var method = new DynamicMethod("MyHandlerImpl", null, new[] { typeof(object), typeof(EventArgs) });

并将Program课程公开,一切正常。

于 2014-02-03T18:52:43.480 回答