단위 테스트에 IoC 사용


97

IoC 컨테이너를 단위 테스트에 어떻게 사용할 수 있습니까? IoC를 사용하여 대규모 솔루션 (50 개 이상의 프로젝트)에서 모의를 관리하는 것이 유용합니까? 어떤 경험? 단위 테스트에서 사용하기에 잘 작동하는 C # 라이브러리가 있습니까?


7
@ 마크 시만 그것을 지적하기에 너무 겸손한 것,하지만 당신은이 질문에 관심이 있다면, 당신은 적어도 알고 있어야 AutoFixture
루벤 Bartelink

1
Miguel Castro의 Vimeo에서 DI와 조롱 사이의 관계에 대한 좋은 이야기가 있습니다. vimeo.com/68390510
GregC

답변:


131

일반적으로 단위 테스트는 책임 분리에 관한 것이기 때문에 단위 테스트에는 DI 컨테이너가 필요하지 않습니다.

생성자 주입을 사용하는 클래스를 고려하십시오.

public MyClass(IMyDependency dep) { }

전체 애플리케이션에서 뒤에 숨겨진 거대한 종속성 그래프가있을 수 IMyDependency있지만 단위 테스트에서는 모든 것을 단일 Test Double 로 평면화합니다 .

Moq 또는 RhinoMocks와 같은 동적 모의를 사용하여 Test Double을 생성 할 수 있지만 필수는 아닙니다.

var dep = new Mock<IMyDependency>().Object;
var sut = new MyClass(dep);

어떤 경우에는 자동 모의 컨테이너 가 있으면 좋겠지 만 프로덕션 애플리케이션에서 사용하는 것과 동일한 DI 컨테이너를 사용할 필요는 없습니다.


13
동의했습니다 ... 테스트 대상이 IoC 컨테이너 종속성 으로 사용 하지 않는 한 테스트에는 필요하지 않습니다 ... 단위 테스트를 수행 할 때 대부분의 개체 그래프를 제거합니다.
Anderson Imes

4
@Mark Seemann 말이됩니다 ...하지만 통합 테스트는 어떻습니까? 즉, UI 테스트로 놀았고 컴포지션 루트를 공유해야하는 상황에 직면했습니다. 다른하실 말씀 있나요?
Arnis Lapsa

5
@Arnis L .: 통합 테스트의 경우 덜 중요합니다. DI 컨테이너를 사용하여 구성 요소를 연결하도록 선택할 수 있지만, 그렇다면 피하 테스트 또는 전체 시스템 테스트를 수행하지 않는 한 전체 애플리케이션과 다른 컨테이너 구성이 필요할 수 있습니다. 컨테이너의 애플리케이션 구성을 재사용 할 수 있습니다.
Mark Seemann

msdn magazine Test Double 참조 : download.microsoft.com/download/3/A/7/…
M.Hassan

18

단위 테스트에 Ioc 컨테이너를 어떻게 사용할 수 있습니까?

IoC는 인터페이스 사용, new () 없음, 싱글 톤 없음 등 격리 된 단위 테스트 (예 : 모의 사용)를 더 쉽게 만드는 프로그래밍 패러다임을 적용합니다.

그러나 테스트를 위해 IoC 컨테이너를 사용하는 것은 실제로 요구 사항이 아닙니다. 모의 주입과 같은 일부 기능 만 제공하지만 수동으로 수행 할 수 있습니다.

IoC를 사용하여 대규모 솔루션 (50 개 이상의 프로젝트)에서 모의를 관리하는 것이 유용합니까?

IoC를 사용하여 모의를 관리한다는 것이 무슨 뜻인지 잘 모르겠습니다. 어쨌든 IoC 컨테이너는 일반적으로 테스트와 관련하여 모의를 주입하는 것 이상을 수행 할 수 있습니다. 리팩토링을 가능하게하는 적절한 IDE 지원이 있다면 사용하지 않으시겠습니까?

경험이 있습니까?

예, 거대한 솔루션에서는 오류가 발생하지 않고 리팩토링에 반대하는 솔루션이 그 어느 때보 다 필요합니다 (즉, 유형 안전 IoC 컨테이너 또는 우수한 IDE 지원을 통해).


17

나는 종종 테스트에서 IoC 컨테이너를 사용합니다. 물론 그들은 순수한 의미에서 "단위 테스트"가 아닙니다. IMO 그들은 더 BDDish이며 리팩토링을 용이하게합니다. 리팩토링에 대한 확신을주기 위해 테스트가 있습니다. 잘못 작성된 테스트는 코드에 시멘트를 붓는 것과 같을 수 있습니다.

다음을 고려하세요:

[TestFixture]
public class ImageGalleryFixture : ContainerWiredFixture
{
    [Test]
    public void Should_save_image()
    {
        container.ConfigureMockFor<IFileRepository>()
            .Setup(r => r.Create(It.IsAny<IFile>()))
            .Verifiable();

        AddToGallery(new RequestWithRealFile());

        container.VerifyMockFor<IFileRepository>();
    }

    private void AddToGallery(AddBusinessImage request)
    {
        container.Resolve<BusinessPublisher>().Consume(request);
    }
}

갤러리에 이미지를 추가 할 때 발생하는 몇 가지 일이 있습니다. 이미지 크기가 조정되고 축소판이 생성되며 파일이 AmazonS3에 저장됩니다. 컨테이너를 사용하면 테스트하려는 동작 만 더 쉽게 분리 할 수 ​​있습니다.이 경우에는 지속되는 부분입니다.

자동 모의 컨테이너 확장은이 기술을 사용할 때 유용합니다. http://www.agileatwork.com/auto-mocking-unity-container-extension/


8
"코드에 시멘트를 붓는 것과 같은"문구에 +1. 나는 항상 그것을 사용하기 시작했습니다.
Andrew Shepherd

2

SimpleInjector , DryIoc 와 같은 미등록 / 알려지지 않은 서비스를 해결할 수있는 컨테이너 사용 아직 구현되지 않은 인터페이스에 대한 모의 객체를 반환 할 수 있습니다 (그 광산을).

즉, 첫 번째 간단한 구현과 모의 된 종속성으로 개발을 시작하고 진행함에 따라 실제 것으로 대체 할 수 있습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.