[英]Autofac register generic instance with concrete type
I want to register a interface to a specific implementation.我想注册一个特定实现的接口。 The interface and the class both are generic instances, here it goes:
接口和类都是通用实例,这里是:
This is the container registration:这是容器注册:
builder.RegisterType<ParsedStatement>()
.As<IParsedStatement>()
.InstancePerDependency();
builder.RegisterType<NpoiParser<ParsedStatement>>()
.As<IParser<IParsedStatement>>()
.InstancePerDependency();
The interface for IParser: IParser 的接口:
public interface IParser<T> where T : class
The implementation of NpoiParser NpoiParser 的实现
public class NpoiParser<T> : BaseParser<T>, IParser<T> where T : class
ParsedStatement class already implements the interface IParsedStatement. ParsedStatement 类已经实现了接口 IParsedStatement。 Although when i start the application I get this error from the the build of the autofac container
虽然当我启动应用程序时,我从 autofac 容器的构建中得到了这个错误
System.ArgumentException: 'The type
RF.Infrastructure.Parser.NpoiParser`1[RF.Domain.ValueObjects.ParsedStatement]
is not assignable to serviceRF.Domain.Interfaces.Parser.IParser`1[[RF.Domain.Interfaces.ValueObjects.IParsedStatement, RF.Domain.Interfaces, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]]
.'System.ArgumentException: '
RF.Infrastructure.Parser.NpoiParser`1[RF.Domain.ValueObjects.ParsedStatement]
类型不可分配给服务RF.Domain.Interfaces.Parser.IParser`1[[RF.Domain.Interfaces.ValueObjects.IParsedStatement, RF.Domain.Interfaces, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]]
.'
I could use a generic approach like this:我可以使用这样的通用方法:
builder.RegisterGeneric(typeof(NpoiParser<>))
.As(typeof(IParser<>))
.InstancePerLifetimeScope();
It works but doesn't allow me to use IParser<ParsedStatement>
on the services since the NpoiParser class needs a concrete class since it uses a library and in that library only classes are permitted otherwise returns me the error "Cannot create an instance of an interface.".它可以工作,但不允许我在服务上使用
IParser<ParsedStatement>
,因为 NpoiParser 类需要一个具体的类,因为它使用一个库,并且在该库中只允许类,否则返回错误“无法创建一个实例界面。”。
The stack trace for the error when using generic is the following one:使用泛型时错误的堆栈跟踪如下:
at System.RuntimeTypeHandle.CreateInstance(RuntimeType type, Boolean publicOnly, Boolean wrapExceptions, Boolean& canBeCached, RuntimeMethodHandleInternal& ctor, Boolean& hasNoDefaultCtor)
at System.RuntimeType.CreateInstanceDefaultCtorSlow(Boolean publicOnly, Boolean wrapExceptions, Boolean fillCache)
at System.RuntimeType.CreateInstanceDefaultCtor(Boolean publicOnly, Boolean skipCheckThis, Boolean fillCache, Boolean wrapExceptions)
at System.Activator.CreateInstance(Type type, Boolean nonPublic, Boolean wrapExceptions)
at Npoi.Mapper.Mapper.<Take>d__66`1.MoveNext()
at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
at RF.Infrastructure.Parser.NpoiParser`1.ParseFile(Stream fileToParse, ITemplateDefinition info) in D:\Trabalho\RoyaltyFlush\royaltyflush.backend\RF.Infrastructure.Parser\NpoiParser.cs:line 52
at RF.Infrastructure.Parser.NpoiParser`1.ConvertStreamFileToObjectList(Stream fileToParse, ITemplateDefinition info) in D:\Trabalho\RoyaltyFlush\royaltyflush.backend\RF.Infrastructure.Parser\NpoiParser.cs:line 35
Any ideas on how i can register it on AutoFac with a specific class type?关于如何使用特定类类型在 AutoFac 上注册它的任何想法?
Registering NpoiParser<ParsedStatement>
as IParser<IParsedStatement>
is like registering apple as orange .将
NpoiParser<ParsedStatement>
注册为IParser<IParsedStatement>
就像将apple注册为orange 。
NpoiParser<ParsedStatement>
does not implement IParser<IParsedStatement>
, it only implements IParser<ParsedStatement>
. NpoiParser<ParsedStatement>
没有实现IParser<IParsedStatement>
,它只实现了IParser<ParsedStatement>
。
// Compile error
IParser<IParsedStatement> obj = new NpoiParser<ParsedStatement>();
There are two ways you could fix this:有两种方法可以解决这个问题:
IParser<ParsedStatement>
instead of IParser<IParsedStatement>
.IParser<ParsedStatement>
而不是IParser<IParsedStatement>
。IParser<T>
to covariant generic interface by using out
keyword.out
关键字将IParser<T>
更改为协变通用接口。 So change IParser<T>
to IParser<out T>
.IParser<T>
更改为IParser<out T>
。 But that requires the interface is indeed an covariant interface.
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.