首页 新闻 会员 周边

依赖注入中如何动态的注入泛型实例类型的问题

0
悬赏园豆:50 [已解决问题] 解决于 2019-02-21 10:46

最近在重构代码时遇到的一个问题,先上代码,再分析

 using (var scope = HttpContext.RequestServices.CreateScope())
            {
                switch (voteRecordDto.ContentType)
                {
                    case ContentType.Ask:
                        voteRecordType = "Asking";
                        break;
                    case ContentType.Answer:
                        voteRecordType = "Answer";
                        break;
                    case ContentType.Comment:
                        voteRecordType = "Comment";
                        break;
                    default:
                        result = OperationResponse.Error("There is no accept Type!");
                        break;
                }
                using (var repository = scope.ServiceProvider.GetService<IVoteRecordRepository<QuestionVoteRecord>>())
                {
                    result = await _voteRecordService.VoteManageAsync(voteRecordDto, repository);
                }

我的目的是想要根据 switch 中的类型产生不同的类型注入到

using (var repository = scope.ServiceProvider.GetService<IVoteRecordRepository<XXX>>())

这个里面的XXX 中,请问如何获取到这个类型? Switch 中每个Case 对应着一个实体的类型,当然有种办法就是我直接在每个case 后面写上这样

using (var scope = HttpContext.RequestServices.CreateScope())
            {
                switch (voteRecordDto.ContentType)
                {
                    case ContentType.Asking:
                        using (var repository = scope.ServiceProvider.GetService<IVoteRecordRepository<QuestionVoteRecord>>())
                        {
                            result = await _voteRecordService.VoteManageAsync(voteRecordDto, repository);
                        }
                        break;
                    case ContentType.Answer:
                        voteRecordType = "Answer";
                        break;
                    case ContentType.Comment:
                        voteRecordType = "Comment";
                        break;
                    default:
                        result = OperationResponse.Error("There is no accept Type!");
                        break;
                }
                using (var repository = scope.ServiceProvider.GetService<IVoteRecordRepository<QuestionVoteRecord>>())
                {
                    result = await _voteRecordService.VoteManageAsync(voteRecordDto, repository);
                }

请问是否有更简便的方法?

c#
问题补充:

PS:或者说是否可以通过 string 类型的实体名获得该实体名同名的 实体类型。

BUTTERAPPLE的主页 BUTTERAPPLE | 老鸟四级 | 园豆:3190
提问于:2017-12-14 16:20
< >
分享
最佳答案
0

我感觉 GetService 有重载,可以传入Type类型参数

收获园豆:30
长蘑菇星人 | 小虾三级 |园豆:1832 | 2017-12-14 16:26

我需要的是GetService里面的这个类型的IVoteRecordRepository<T> 里面的这个T

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:28

@BUTTERAPPLE: IVoteRecordRepository<T> 用起来 和 T 有多大区别。

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:30

@长蘑菇星人: 大概上天和地的区别吧,T只是一个实体类型。IVoteRecordRepository<T> 是一个仓储的泛型接口。

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:32

@BUTTERAPPLE: 对于GetService呢。你是要获取 IVoteRecordRepository<T> 还是 T 呢

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:33

@BUTTERAPPLE:

                Type type;
                switch (voteRecordDto.ContentType)
                {
                    case ContentType.Ask:
                        voteRecordType = "Asking";
                         type = typeof( IVoteRecordRepository<XXX1>);
                        break;
                    case ContentType.Answer:
                        voteRecordType = "Answer";
                         type = typeof( IVoteRecordRepository<XXX2>);
                        break;
                    case ContentType.Comment:
                        voteRecordType = "Comment";
                        break;
                    default:
                        result = OperationResponse.Error("There is no accept Type!");
                        break;
                }
长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:35

@长蘑菇星人: 我想通过 string 类型的name 获取到这个同名实体对应的 实体类型,比如我IVoteRecordRepository<A>, IVoteRecordRepository<B>,IVoteRecordRepository<C>。 当case 1 时 取得A类型,依此类推

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:38

@长蘑菇星人: Error:type is a variable,but is used like a type

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:41

@BUTTERAPPLE:

typeof(IVoteRecordRepository<>).MakeGenericType(typeof(A))
长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:41

@长蘑菇星人: 你的这些我之前在Stack Overflow上找过,都已经试过啦。

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:43

@BUTTERAPPLE: 你是怎么写的。

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:48

@长蘑菇星人:

  Type type;
            using (var scope = HttpContext.RequestServices.CreateScope())
            {
                switch (voteRecordDto.ContentType)
                {
                    case ContentType.Ask:
                        type = typeof(IVoteRecordRepository<>).MakeGenericType(typeof(QuestionVoteRecord));
                        break;
                        break;
                    case ContentType.Answer:
                        voteRecordType = "Answer";
                        break;
                    case ContentType.Comment:
                        voteRecordType = "Comment";
                        break;
                    default:
                        result = OperationResponse.Error("There is no accept Type!");
                        break;
                }
                using (var repository = scope.ServiceProvider.GetService<type>())
                {
                    result = await _voteRecordService.VoteManageAsync(voteRecordDto, repository);
                }
BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:50

@BUTTERAPPLE: GetService 有重载么

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:51

@长蘑菇星人: 没。[尴尬]

BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 16:53

@BUTTERAPPLE: [滑稽]你没有骗我?

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:57

@BUTTERAPPLE: 把type 放括号里,把<type>删了

长蘑菇星人 | 园豆:1832 (小虾三级) | 2017-12-14 16:58
其他回答(1)
0

我记得.net core的依赖注入是泛型的,如果不行,建议使用工厂方法,像ILoggerFactory那样

收获园豆:20
dudu | 园豆:31003 (高人七级) | 2017-12-14 19:22

我去研究一下 ILoggerFactory怎么实现的。

支持(0) 反对(0) BUTTERAPPLE | 园豆:3190 (老鸟四级) | 2017-12-14 22:04
清除回答草稿
   您需要登录以后才能回答,未注册用户请先注册