2017-09-14 4 views
1

단위 테스트를 처음 사용합니다. 내가 아주 간단한 것을 테스트하기 위해 노력하고 있습니다 :File.Delete가 Moq을 사용하여 호출되었습니다.

if (!String.Equals(user.ProfilePictureUrl, _defaultPic)) 

내가 System.IO.File.Delete인지 확인하고 싶습니다 : 코드의이 섹션에서는

[HttpPost] 
public ActionResult EditProfile(ProfileViewModel model) 
{ 
    if (ModelState.IsValid) 
    { 
     // Retrieve current user 
     var userId = User.Identity.GetUserId(); 
     var user = _dataRepository.GetUserById(userId); 

     //If it isn't the single-instance default picture, delete the current profile 
     // picture from the Profile_Pictures folder 
     if (!String.Equals(user.ProfilePictureUrl, _defaultPic)) 
      System.IO.File.Delete(Server.MapPath(user.ProfilePictureUrl)); 

를,이 라인이 참으로 평가하는 조건을 만드는 오전 라는.

가장 좋은 방법은 무엇입니까?

System.IO.File.Delete 호출을 랩핑하여 인터페이스를 구현하는 클래스를 랩핑하여 호출해야한다는 사실을 모의 할 수 있어야합니까?

저는 Moq를 사용하고 있습니다.

+0

귀하의 마지막 문으로 확인 될 수 있도록 할 절대적으로 올바른 것입니다. 입출력 호출을 모방 할 수있는 추상화로 캡슐화합니다. – Nkosi

+0

감사합니다 @ Nkosi! –

+0

당신은 또한'Service.MapPath'에 대해서도 똑같이해야합니다. 이것들은 추상화 될 수있는 구현 문제입니다. 실제로 전체 문장을 하나의 추상화로 캡슐화 할 수 있습니다. – Nkosi

답변

1

인터페이스를 구현하는 내 자신의 클래스에서 System.IO.File.Delete 호출을 랩핑하여 리팩토링해야 인터페이스를 구현하여 호출 할 수 있는지 확인할 수 있습니까?

캡슐화 구현 명시 생성자 주입 통해 부양 주입 및 사용되는

public interface IFileSystem { 
    void Delete(string path); 

    //...code removed for brevity 
} 

public class ServerFileSystemWrapper : IFileSystem { 
    public void Delete(string path) { 
     System.IO.File.Delete(Server.MapPath(path)); 
    } 

    //...code removed for brevity 
} 

관한 것이다.

if (!String.Equals(user.ProfilePictureUrl, _defaultPic)) 
    _fileSystem.Delete(user.ProfilePictureUrl); //IFileSystem.Delete(string path) 

이 지금 망신 시켰를 설치하고 필요에

//Arrange 
var mockFile = new Mock<IFileSystem>(); 

var profilePictureUrl = "..."; 

//...code removed for brevity 

var sut = new AccountController(mockFile.Object, ....); 

//Act 
var result = sut.EditProfile(model); 

//Assert 
result.Should().NotBeNull(); 
mockFile.Verify(_ => _.Delete(profilePictureUrl), Times.AtLeastOnce());