我有以下课程:
public interface IDbCommandHandler<in TCommand, out TOutput>
where TCommand : IDbCommand
{
TOutput Handle(TCommand command);
}
public class SubIdentifierItemCreateCommand<TItemType, TDefaultValues>
: BaseDbCommand
where TItemType: TDefaultValues
{
}
public class SubIdentifierItemCreateCommandHandler<TItemType, TDefaultValues>
: BaseDbCommandHandler<SubIdentifierItemCreateCommand<TItemType, TDefaultValues>, TItemType>,
IDbCommandHandler<SubIdentifierItemCreateCommand<TItemType, TDefaultValues>, TItemType>
where TItemType: class, TDefaultValues, IItemForGenericItemByIdentifierRetriever , new()
{
}
我需要将SubIdentifierItemCreateCommandHandler
注册为singleton-open-generic,以处理对类型服务的任何请求
IDbCommandHandler<SubIdentifierItemCreateCommand<,>,>
。
这可能吗?我已经尝试了各种各样的方式,但我总是遇到错误。
_container.RegisterSingleOpenGeneric(
typeof(IDbCommandHandler<,>),
typeof(SubIdentifierItemCreateCommandHandler<,>));
_container.RegisterOpenGeneric(
typeof(IDbCommandHandler<,>),
typeof(SubIdentifierItemCreateCommandHandler<,>));
// this one is throws a compile-time error, that you cannot
// use partial open types.
_container.RegisterManyForOpenGeneric(
typeof(IDbCommandHandler<SubIdentifierItemCreateCommand<,>,>),
typeof(SubIdentifierItemCreateCommandHandler<,>));
我希望能够打电话给下面的工作:
var item = _container.GetInstance<
IDbCommandHandler<
SubIdentifierItemCreateCommand<
SectionData,
ISectionDataDefaultValues>,
SectionData>>();
答案 0 :(得分:0)
不幸的是,你偶然发现了框架中的一个错误。 Simple Injector 1.6.1无法正确处理“where TItemType:TDefaultValues”约束。
解决方案很简单,迁移到Simple Injector 2.0(via NuGet)。
如果您因任何原因无法切换到Simple Injector 2.0,您可以注册ResolveUnregisteredType
事件以注册该类型以解决1.6.1版本中的错误:
container.ResolveUnregisteredType += (sender, e) =>
{
var serviceType = e.UnregisteredServiceType;
if (serviceType.IsGenericType &&
serviceType.GetGenericTypeDefinition() == typeof(IDbCommandHandler<,>))
{
var commandArg = serviceType.GetGenericArguments()[0];
var outputArg = serviceType.GetGenericArguments()[1];
if (commandArg.IsGenericType &&
commandArg.GetGenericTypeDefinition() ==
typeof(SubIdentifierItemCreateCommand<,>))
{
var itemTypeArgument = commandArg.GetGenericArguments()[0];
var defaultValuesArgument = commandArg.GetGenericArguments()[1];
if (itemTypeArgument != outputArg)
{
return;
}
Type typeToRegister;
try
{
typeToRegister =
typeof(SubIdentifierItemCreateCommandHandler<,>)
.MakeGenericType(itemTypeArgument.GetGenericArguments());
}
catch (ArgumentException)
{
// Thrown by MakeGenericType when the type constraints
// do not match. In this case, we don't have to register
// anything and can bail out.
return;
}
object singleInstance = container.GetInstance(typeToRegister);
// Register the instance as singleton.
e.Register(() => singleInstance);
}
}
};
我知道,这很难看,但至少有一个解决方法; - )