2013-03-01 2 views
0

나는이 내 저장소 인터페이스에서 다음과 같은 방법저장소 인터페이스 방법으로 Moq 사용?

IQueryable<T> GetQuery<T>(Expression<Func<T, bool>> predicate) where T : class; 

나는 클래스가 나는 다음과 같은 생성자를 단위 테스트에 행동하는거야 있습니다

public MyClass(IUnitOfWork unitOfWork) 

IUnitOfWork 인터페이스에있다

Repository Repository { get; } 

그래서 내가 장치에 노력하고있어 MyClass.DoSomething() 방법 사장님을 테스트 : 노출 된 저장소 속성입니다 전자 그래서 :

//Arrange 
var repositoryMock = new Mock<IUnitOfWork>(); 
repositoryMock.Setup(x => x.Repository.GetQuery<Account>(y => y.Id == 123)) 
          .Returns(accounts.AsQueryable()); //This setup always fails 
var myClass = new MyClass(repositoryMock.Object); //don't even get here 

내가 얻을 예외는 다음과 같습니다 :

System.NotSupportedException : 잘못된 설정 A의 나는 실패 단위 테스트 Arrange 섹션이

[TestInitialize] 
public void Setup() 
{ 

    accounts = new List<Account>() 
    { 
     new Account() 
      { 
       Id = 123 
      } 
    }; 
} 

다음 가상이 아닌 가상 (VB에서 재정의 가능) 멤버 : x => x.Repository.GetQuery (y => y.Id == 123)

나는 모의에 Setup의 다른 변화를 시도했다 :

repositoryMock.Setup(x => x.Repository.GetQuery<Account>()).Returns((Account a) => accounts.AsQueryable().Where(z => z.Id == 123)); 

repositoryMock.Setup(x => x.Repository.GetQuery<Account>(y => y.Id == 123)).Returns((Account a) => accounts.AsQueryable().Where(z => z == a)); 

하지만 성공

을; 매번 동일한 예외가 발생합니다. 그들은 단위 테스트를 실행할 때 항상 같은 예외를 throw합니다. 내가 Interface를 사용하여 조롱당하는 이유는 무엇입니까?이 예외가 발생하는 이유는 무엇입니까? 감사!

답변

1

표시된 Repository 속성은 인터페이스 유형이 아닙니다. 그것은 구체적인 수업입니다. 그리고 오류 메시지가 알려주므로 비 가상 메서드에 대한 기대치를 정의 할 수 없습니다. 당신이 그것을 조롱 할 수 있도록하려면 그래서 당신이 대신해야하는 것은 추상화 작업을하는 것입니다 :

IRepository Repository { get; } 
+0

이것은 기술적으로 * 내가 얻은 오류를 해결하기 위해 내 원래 게시물에 대한 답변입니다. 그러나 이것을 적용한 후에도 원래의 쿼리와 구문은 틀렸고 @HuseinRoncevic의 대답은 내가 가지고 있었던 다른 문제를 해결했습니다. 두 가지 모두에게 감사의 말로 대답을 표시하십시오. – atconway

1

현재 설정이 시도하는 대신 :

현실에서
//Arrange 
var repositoryMock = new Mock<IUnitOfWork>(); 
repositoryMock.Setup(x => x.Repository.GetQuery<Account>(
     It.IsAny<Expression<Func<T, bool>>>()); 
    .Returns(accounts.AsQueryable()); // This should not fail any more 
var myClass = new MyClass(repositoryMock.Object); 

, 그렇게하지를 당신이 당신의 명부를 어느 쪽이든 돌려 보내기 때문에 어떤 구체적인 람다든지 통과 할 필요가있다.

+0

이것은 정확하게 필요하지만, 주입 된 mockd '저장소를 사용하는'myClass.DoSomething'을 호출 할 때 내부적으로 호출 된 쿼리는 결과를 산출하지 않습니다. 오류가 없으며 아무 것도 반환되지 않습니다. 나는 코드 20 배 이상을 살펴 봤다. "Repository.GetQuery "이 호출 될 때'accounts'라는 목록을 반환 할 저장소의 인스턴스가 여기 있습니다. " 그렇다면 왜 간단한 쿼리로 결과가 나오지 않습니까? (좋은 점은 콘크리트 람다를 전달할 필요가 없다는 것입니다. 예, 항상 전체 목록이 반환되기를 바랍니다.) – atconway

+0

Nevermind - 알아 냈어. 나는 저장소에서'GetQuery'를 * 2 * 구현했습니다. 하나는 표현식을 취하고 다른 하나는 엔티티 만 취합니다. 내가 테스트 한 과부하는 실제로 엔티티를 가져간 것입니다. 나는 반환 된'IQuerable' 결과에 대한 쿼리를 작성한 다음 * 추가 ​​* 람다 식 필터링을 적용했습니다. 따라서 내 쿼리가'GetQuery'에 대한 원래 호출의 일부로 표현식을 제공했다면 코드가 작동합니다. 나는이 모든 것을 내 OP 때 이해하지 못했습니다. 당신의 도움을 주셔서 감사합니다. – atconway