如何使用 Moq 模拟带有 lambda 表达式的服务调用

How to mock a service call with a lambda expression using Moq

我正在使用 Moq 尝试模拟一个将 lambda 表达式作为其可选参数并调用数据库的方法。

这是我试图模拟的真实方法

public IQueryable<T> AllSearchBy<T>(params Expression<Func<T, bool>>[] search) where T : class
    {
        IQueryable<T> result = _context.Set<T>();

        foreach (var item in search)
        {
            result = result.Where(item);
        }

        return result;
    }

这是我的最小起订量存储库设置

var mockRepository = new Mock<IRepository>();

var rateEndHsbSlcTable = new List<Rate_End_HSB_SLC>
        {
            new Rate_End_HSB_SLC
            {
                Limit = 10000,
                DwellingAgeMin = 0,
                DwelilngAgeMax = 25,
                Premium = 22M
            },
            new Rate_End_HSB_SLC
            {
                Limit = 10000,
                DwellingAgeMin = 26,
                DwelilngAgeMax = 50,
                Premium = 45M
            }
        };

mockRepository.Setup(m => m.AllSearchBy(It.IsAny<Expression<Func<Rate_End_HSB_SLC, bool>>>()))
                      .Returns((Expression<Func<Rate_End_HSB_SLC, bool>> predicate) => rateEndHsbSlcTable.Where(predicate.Compile()).AsQueryable());



IRateServices rateService = new RateServices(mockRepository.Object, new HelperServices(mockRepository.Object));

这是我正在测试的代码中的调用,它给我一个错误(为简单起见,我用硬值替换了变量)

var test = _repository.AllSearchBy<Rate_End_HSB_SLC>(x => x.Limit == 10000 && x.DwellingAgeMin <= 19 && x.DwelilngAgeMax >= 19);

编译成功,但运行时出现以下异常

System.ArgumentException: Object of type 'System.Linq.Expressions.Expression1[System.Func2[Twico.DataAccess.Rate_End_HSB_SLC,System.Boolean]][]' cannot be converted to type 'System.Linq.Expressions.Expression1[System.Func2[Twico.DataAccess.Rate_End_HSB_SLC,System.Boolean]]'.

我怀疑问题出在我的设置上,return 类型不正确。

对我做错了什么有什么想法吗?

编辑:使用 ibebbs 答案,我让它可以使用这种语法!

mockRepository.Setup(m => m.AllSearchBy(It.IsAny<Expression<Func<Rate_End_HSB_SLC, bool>>[]>()))
                      .Returns((Expression<Func<Rate_End_HSB_SLC, bool>>[] predicates) => predicates.Aggregate(rateEndHsbSlcTable, (source, predicate) => source.Where(predicate.Compile()).ToList()).AsQueryable());

快速查看代码显示 AllSearchBy 需要一个 数组 Expression<Func<T, bool>> 但您的设置指定了一个表达式。

也许试试这样的方法?

mockRepository
  .Setup(m => m.AllSearchBy(It.IsAny<Expression<Func<Rate_End_HSB_SLC, bool>>[]>()))
  .Returns(predicates => predicates
    .Aggregate(
      rateEndHsbSlcTable, 
      (source, predicate) => source.Where(predicate.Compile())).AsQueryable());