调用接口方法,但 System.Reflection.MethodBase 设置为 System.Object

本文关键字:System MethodBase 设置 Object Reflection 调用 方法 接口 | 更新日期: 2023-09-27 18:13:03

>我正在尝试在运行时调用通用接口方法,但是在查找类型信息时,它似乎找到的是IDomainEventSubscriber而不是传递的正确类型。

引发运行时错误:Object does not match target type.

检查我看到的值 handler实例类型 是 typeof(TestEventHandler)methodInfo{System.Reflection.MethodBase}显示{Void HandleEvent(System.Object)}

因此,它被设置为System.Object的方法类型,而不是实际类型(例如,在我们称为Dispatch(new TestEvent());的情况下,TestEvent(

是否可以获得正确的实现,以便我可以在运行时调用接口成员?

public interface IDomainEventSubscriber<T>
{
    void HandleEvent(T domainEvent);
}
class TestEventHandler : IDomainEventSubscriber<TestEvent>
{
    public void HandleEvent(TestEvent domainEvent)
    {
    }
}
// some service that dispatches events
void Dispatch<T>(T eventToPublish) where T : class
{
    Type handlerType = map.GetHandlersForType(eventToPublish.GetType());
    // a valid object instance is returned from my IoC container
    object handlerInstance = this.ResolveHandler<T>(handlerType);
    // i can guarantee the instance implements IDomainEventSubscriber<T> where T
    // is the same type as eventToPublish
    Type typeInfo = typeof(IDomainEventSubscriber<T>);
    MethodInfo methodInfo = typeInfo.GetMethod("HandleEvent");
   // this line throws an error :(
    methodInfo.Invoke(handlerInstance, new object[] { eventToPublish });
}

调用接口方法,但 System.Reflection.MethodBase 设置为 System.Object

我认为你根本不需要反思。既然您知道该实例实现了IDomainEventSubscriber<T>,为什么不将其转换为该实例呢?

// You could make ResolveHandler just return IDomainEventSubscriber<T> of course
var handler = (IDomainEventSubscriber<T>) ResolveHandler<T>(handlerType);
handler.HandleEvent(eventToPublish);

但是您的代码实际上似乎对我来说工作正常,已将其提取到一个简短但完整的程序中(如下(。您的methodInfo具有类型 System.Object 的参数这一事实表明T System.Object,而它应该TestEvent。所以也许问题只是你的方法是如何被调用的?

using System;
using System.Reflection;
public class TestEvent{}
public interface IDomainEventSubscriber<T>
{
    void HandleEvent(T domainEvent);
}
class TestEventHandler : IDomainEventSubscriber<TestEvent>
{
    public void HandleEvent(TestEvent domainEvent)
    {
        Console.WriteLine("Done");
    }
}
class Test
{
    static void Main(string[] args)
    {
        Dispatch<TestEvent>(new TestEvent(), typeof(TestEventHandler));
    }
    static void Dispatch<T>(T eventToPublish, Type handlerType)
    {
        object handlerInstance = Activator.CreateInstance(handlerType);
        Type typeInfo = typeof(IDomainEventSubscriber<T>);
        MethodInfo methodInfo = typeInfo.GetMethod("HandleEvent");       
        methodInfo.Invoke(handlerInstance, new object[] { eventToPublish });
    }
}