1

I'm trying to unit test this simple method although I'm not sure how to stub out the where clause using moq? I've tried the following although I'm struggling to get it working!?

I want to test that Get() method returns a list of Person.

Thanks,

My Test

[Test]
public void TempTest()
{
    // Arrange
    var list = new List<string> {"Key"};
    var mockRepository = new Mock<IBRepository>();
    var bService = new BService(mockRepository.Object);

    // ** I'm not sure about this line **
    mockRepository.Setup(x => x.Where...);

    // Act
    var result = bService.Get(list);

    // Assert
}

Method to test

private readonly IBRepository _repository;

public List<MyClass> Get(List<string> list)
{
    var collection = new List<MyClass>();

    foreach (var key in list)
    {
        var id = key;
        collection.AddRange(_repository.Where(x => x.SomeProperty.Equals(id)));
    }

    return list;
}

IBRepository

public interface IBRepository : IRepository<B, int>
{
}

BRepository

public class BRepository : Repository<B, int>, IBRepository, IUnitOfWorkRepository
{
    public BRepository(NHUnitOfWork<UserMapping> uow)
  : base(uow)
    {
    }
}

IRepository

public interface IRepository<T, TId> : INoIdRepository<T>, IReadOnlyRepository<T, TId> where T : IAggregateRoot
{
    TId Insert(T entity);

    bool TryInsert(T entity, out TId entityId);

    void DeleteById(TId id);

    void DeleteByIds(IList<TId> ids);
}

Where functionality

IEnumerable<T> Where(Expression<Func<T, bool>> predicate);
James Radford
  • 1,815
  • 4
  • 25
  • 40
  • 1
    What is the exact type of `_repository`. Is the method `Where` an extension method from Linq, or is it an instance method of the `_repository`? What does the declaration of `Where` look like? You might be able to do something like `mockRepository.Setup(x => x.Where(It.IsAny>())).Returns(yourTestPersons);` but it is a pure guess until I get more info. – Jeppe Stig Nielsen Jan 07 '14 at 11:40
  • So does `IPersonRepository` inherit from `IEnumerable` then? If not, couldn't you create a method on the repository that calls `Where` as required, rather than surfacing LINQ calls directly on your repository? That seems like a strange thing to do – levelnis Jan 08 '14 at 10:13
  • ok thanks, why is it strange? I've also updated the question with the implementation of IPersonRepository – James Radford Jan 08 '14 at 10:21
  • It looks like you're pulling back an enumeration based on `customerId`. Mocking would be trivial if you created a method on your repository that passed in the `customerId`, internally called `Where` on the collection in question and returned the result – levelnis Jan 08 '14 at 10:40
  • Can you add the code in the `IPersonRepository` interface itself to your question? – levelnis Jan 08 '14 at 10:41
  • see above, let me know if you need anything else.. – James Radford Jan 08 '14 at 11:02
  • What are you trying to test after all? Please show your test method. – Thomas Weller Jan 08 '14 at 11:12
  • The `IRepository<>` and `Repository<>` implementations as well please – levelnis Jan 08 '14 at 11:27
  • updates applied, sorry for the confusion. The Where clause is IEnumerable – James Radford Jan 08 '14 at 12:03
  • I found better explanation here https://stackoverflow.com/questions/60335620/how-to-create-xunit-test-for-microsoft-entityframeworkcore-3-1-method-firstordef – user1154390 May 12 '20 at 08:59

1 Answers1

0

I think you are leaking some implementation details from the repository interface. Your design would be more testable if you move quering to repository implementation. Here's how I would do it:

interface IBRepository
{
    List<MyClass> Get(List<string> idList);
}

With this interface you don't have to send predicates to the interface or try to mock LINQ methods (you can't mock them anyway because they are extension methods).

I guess you have a generic repository interface that you want to use. IMHO generic repository interfaces are not very useful, you can already use the common functionality by inheriting from the generic repository implementation. This makes mocking repositories really simple:

[Test]
public void TempTest()
{
    // Arrange
    var list = new List<string> {"Key"};
    var mockRepository = new Mock<IBRepository>();
    var bService = new BService(mockRepository.Object);

    mockRepository.Setup(x => x.Get(list)).Returns(new List<MyClass>());

    // Act
    var result = bService.Get(list);

    // Assert
}
Ufuk Hacıoğulları
  • 37,978
  • 12
  • 114
  • 156