无法转换类型为' System.Collections.Generic.List`1 []'的对象输入' System.Linq.IQueryable`1 []'

时间:2015-12-16 15:07:11

标签: c# linq list iqueryable

我的单元测试中有以下代码。但是,它会返回运行时提到的错误。

var leaveTypesList = new List<LeaveType>() { leaveType1, leaveType2, leaveType3 };
var leaveTypesQueryable = leaveTypesList.AsQueryable();
mockLeaveTypeRepository.Setup(r => r.GetLeaveTypes()).Returns(leaveTypesQueryable);
var leaveTypeDtos = service.GetLeaveTypes();

从服务返回结果时,从最后一行生成错误。

下面列出的GetLeaveTypes方法的服务代码,它是对存储库的简单访问。

    public IQueryable<LeaveTypeDto> GetLeaveTypes()
    {
        //return Mapper.Map<IQueryable<LeaveTypeDto>>(leaveTypeRepository.GetLeaveTypes());
        return leaveTypeRepository.GetLeaveTypes().ProjectTo<LeaveTypeDto>();
    }

存储库代码也是IQueryable休假类型的简单回复。

    public IQueryable<LeaveType> GetLeaveTypes()
    {
        return dbContext.LeaveType.Where(lt => lt.IsActive);
    }

只是无法弄清楚这里有什么问题。有什么想法吗?

1 个答案:

答案 0 :(得分:1)

您希望将leaveTypeRepository.GetLeaveTypes()映射到匹配的DTO对象的IQueryable。我认为您需要这样做,因为leaveTypeRepository.GetLeaveTypes()也是IQueryable,您希望与其查询提供商保持联系。

AutoMapper有一个different method

using AutoMapper.QueryableExtensions;

...

return leaveTypeRepository.GetLeaveTypes()
           .ProjectTo<LeaveTypeDto>();

这将返回一个IQueryable<LeaveTypeDto>,您可以应用后续的LINQ方法,这些方法仍将被转换为SQL。

现在异常的原因。这是因为IQueryable<T>没有默认实现。 AutoMapper会创建List<LeaveTypeDto>,但无法将其本地转换为IQueryable<LeaveTypeDto>。但是你可以做像......这样的事情。

Mapper.Map<IEnumerable<LeaveTypeDto>>(source)
Mapper.Map<IList<LeaveTypeDto>>(source)
Mapper.Map<LeaveTypeDto[]>(source)

...因为对于那些目标类型,AutoMapper知道它应该使用哪个默认实现(List<T>T[])。