Как привести конкретный класс к логически правильному интерфейсу generi c - PullRequest
1 голос
/ 10 июля 2020

Моя модель класса выглядит следующим образом:

// Interfaces

public interface IRequest { }

public interface IResponse { }

public interface IHandler<in T_Request, out T_Response>
    where T_Request : IRequest
    where T_Response : IResponse
{
    T_Response Handle(T_Request request);
}

// Concrete Class

public class CreateOrderRequest : IRequest { }

public class CreateOrderResponse : IResponse { }

public class CreateOrderHandler : IHandler<CreateOrderRequest, CreateOrderResponse>
{
    public CreateOrderResponse Handle(CreateOrderRequest request)
    {
        throw new NotImplementedException();
    }
}

Это прекрасный дизайн класса. Но знайте, что мне нужно держать 'Handler' в переменной времени выполнения:

public class Test
{
    public void MyMethod()
    {
        IHandler<IRequest, IResponse> handlerA = new CreateOrderHandler(); // <-- Failed at compile time
        IHandler<CreateOrderRequest, IResponse> handlerB = new CreateOrderHandler(); // <-- Working
        IHandler<CreateOrderRequest, CreateOrderResponse> handlerC = new CreateOrderHandler(); // <-- Working
    }
}

Потому что общий c аргумент 'T_Request' имеет ключевое слово 'in'-Variant-Keyword преобразование в переменную' handlerA ' не работает. Но этот гипс мне нужен. В реальном проекте я хочу получить конкретный обработчик от фабрики и затем вызвать метод Handle.

Кто-нибудь знает, как изменить эту модель класса, чтобы ковариантная функция работала для меня?

...