0

我是 Mocking 的新手,但这一定是我所缺少的非常基本的东西:

下面的测试代码产生一个异常:

预期在模拟上至少调用一次,但从未执行过:x => x.DeleteProducts(._products)\r\n\r\n配置设置:\r\nx => x.DeleteProducts(._products), Times。从不\r\n\r\n执行的调用:\r\nIProductRepository.DeleteProducts(System.Collections.Generic.List`1[WebApiDemo.DataAccessLayer.Product])

我逐步执行了控制器方法,它似乎确实调用了 DeleteProducts 方法......

  // Arrange
  IEnumerable<Product> _products = Helpers.ProductHelpers.CreateProducts(_numberProducts);

  Mock<IProductRepository> _productRepository = new Mock<IProductRepository>();

  _productRepository.Setup(x => x.DeleteProducts(_products));

  ProductsController controller = new ProductsController(_productRepository.Object);

  // Act
  controller.Destroy(_productViewModels);  // Destroy calls DeleteProducts

  // Assert
  _productRepository.Verify(x => x.DeleteProducts(_products));
4

2 回答 2

0

DeleteProducts(_products);退货无效吗?我认为它确实如此,所以你需要把它放在它.Verifiable()的末尾.Setup()

有了这个,它应该可以正常运行,虽然我不确定你为什么有Times.Never()而不是Times.Once()??

我还主张在 Setup 调用中使用It.IsAny<T>而不是特定的集合,例如:

MyMock.Setup(x => x.MyMethod(It.IsAny<IEnumerable<Widget>>)).Verifiable()
于 2012-10-02T16:07:57.187 回答
0

除非您将模拟行为设置为严格,否则不需要设置。您不会从 Delete 中返回任何内容。调用验证就足够了。

有些事情从代码中并不完全明显。

存储库删除产品,但控制器销毁productviewmodels

在最小起订量 4 中,测试应该有效,如果

  • _products 中的每个产品都有一个产品视图模型
  • Controller.Destroy 方法以与 _products 相同的顺序从视图模型中获取产品

我会检查 _productViewModels 是否与 _products 1:1 匹配,并在调用 Delete() 之前检查 Destroy() 如何从视图模型中提取产品

我不会使用 IsAny>() 因为您想检查这些特定产品是否被删除而不是任何其他产品。

[TestClass]
public class Verifying {

    public interface IProductRepository {
        void Delete(IEnumerable<Product> products);
    }

    public class ProductController {
        private IProductRepository _repository;
        public ProductController(IProductRepository repository) {
            _repository = repository;
        }
        public void Destroy(IEnumerable<Product> products) {
            _repository.Delete(products);
        }
        public void Destroy(IEnumerable<ProductViewModel> productViewModels) {
            _repository.Delete(productViewModels.Select(vm => vm.Product));
        }
    }

    public class Product {
    }

    public class ProductViewModel {
        public Product Product { get; set;}
    }


    static Verifying() {
        sProducts = new List<Product> { new Product(), new Product(), new Product() };
        sProductViewModels = new List<ProductViewModel>(sProducts.Select(p => new ProductViewModel { Product = p }));
    }

    private static List<Product> sProducts;
    private static List<ProductViewModel> sProductViewModels;

    private Mock<IProductRepository> _mockRepository;
    private ProductController CreateController() {
        _mockRepository = new Mock<IProductRepository>();
        return new ProductController(_mockRepository.Object);
    }

    [TestMethod]
    public void DestroyingProducts() {
        var controller = CreateController();
        controller.Destroy(sProducts);
        _mockRepository.Verify(mk => mk.Delete(sProducts));
    }

    [TestMethod]
    public void DestroyingProductViewModels() {
        var controller = CreateController();
        controller.Destroy(sProductViewModels);
        _mockRepository.Verify(mk => mk.Delete(sProducts));
    }

}
于 2012-10-03T10:00:24.620 回答