2015-10-23 17 views
7

Tôi đã đọc rất nhiều bài viết về cách chế biến đậu mùa xuân và các lĩnh vực autowired của họ. Nhưng không có gì tôi có thể tìm thấy về danh sách đậu tự động.Làm thế nào để thử một danh sách autowired của đậu mùa xuân?

bê tông vấn đề

Tôi đã một lớp được gọi là FormValidatorManager. Vòng lặp lớp này thông qua một số trình xác nhận hợp lệ thực hiện IFormValidator.

@Component 
public class FormValidatorManager implements IValidatorManager { 

    @Autowired 
    private List<IFormValidator> validators; 

    /* 
    * (non-Javadoc) 
    * 
    * @see 
    * com.sagemcom.esm.vision.business.validator.IFormValidator#validate(com 
    * .sagemcom.esm.vision.model.tablesdefinition.ColumnDTO, java.lang.String) 
    */ 
    @Override 
    public final IFieldError validate(ColumnDTO columnToValidate, String sentValue) { 
     String loweredColName = columnToValidate.getName().toLowerCase(); 
     IFieldError errorField = new FieldError(loweredColName); 

     for (IEsmFormValidator validator : validators) { 
      List<String> errrorsFound = validator.validate(columnToValidate, sentValue); 

      //les erreurs ne doivent pas être cumulées. 
      if(CollectionUtils.isNotEmpty(errrorsFound)){ 
       errorField.addErrors(errrorsFound); 
       break; 
      } 
     } 

     return errorField; 
    } 
} 

Tôi muốn kiểm tra lớp học này. Nhưng tôi không thể tìm ra cách để chế giễu tài sản validators.

Những gì tôi đã cố gắng

Kể từ IFormValidators là singleton, tôi đã cố gắng để thử một vài trường hợp trong số này đậu hy vọng họ được phản ánh trong FormValidatorManager.validators nhưng không thành công.

Sau đó, tôi đã cố tạo danh sách IFormValidators được chú thích là @Mock. Bằng cách bắt đầu List theo cách thủ công, tôi đã hy vọng initMocks() để chèn danh sách được tạo. Điều đó vẫn không thành công.

Đây là thử cuối cùng của tôi:

@RunWith(SpringJUnit4ClassRunner.class) 
@ContextConfiguration(locations={"classpath:spring/test-validator-context.xml"}) 
public class FormValidatorManagerTest { 

    @Mock 
    private RegexValidator regexValidator; 

    @Mock 
    private FormNotNullValidator notNullValidator; 

    @Mock 
    private FormDataTypeValidator dataValidator; 

    @InjectMocks 
    private FormValidatorManager validatorManager; 

    @Mock 
    private List<IEsmFormValidator> validators = new ArrayList<IEsmFormValidator>(); 

    @Mock 
    private ColumnDTO columnDTO; 

    @Before 
    public void init() { 

     validators.add(notNullValidator); 
     validators.add(regexValidator); 
     validators.add(dataValidator); 

     MockitoAnnotations.initMocks(this); 

     Mockito.when(columnDTO.getTitle()).thenReturn("Mock title"); 
     Mockito.when(columnDTO.getName()).thenReturn("Mock name"); 
    } 



    @Test 
    public void testNoErrorFound(){ 
     mockValidator(notNullValidator, new ArrayList<String>()); 
     mockValidator(regexValidator, new ArrayList<String>()); 
     mockValidator(dataValidator, new ArrayList<String>()); 

     IFieldError fieldErrors = validatorManager.validate(columnDTO, "Not null value"); 

     Assert.assertEquals(0, fieldErrors.getErrors().size()); 

     verifyNumberOfValidateCalls(regexValidator, Mockito.atMost(1)); 
     verifyNumberOfValidateCalls(dataValidator, Mockito.atMost(1)); 
     verifyNumberOfValidateCalls(notNullValidator, Mockito.atMost(1)); 
    } 



    private void mockValidator(IFormValidator validator, List<String> listToReturn){ 
     Mockito.when(validator.validate(Mockito.any(ColumnDTO.class), Mockito.anyString())).thenReturn(listToReturn); 
    } 

    private void verifyNumberOfValidateCalls(IFormValidator validator, VerificationMode verifMode){ 
     Mockito.verify(validator, verifMode).validate(Mockito.any(ColumnDTO.class), Mockito.anyString()); 
    } 
} 

Một NPE được ném trong IFormValidator.validate() mà tôi thougth sẽ chế giễu. Việc thực hiện cụ thể không nên được gọi.

Điều này dẫn đến hành vi thực sự xấu vì một số thử nghiệm của tôi trên lớp đó là dương tính giả trong khi những người khác hoàn toàn thất bại.

Tôi đang cố gắng tìm ra cách chế bản danh sách đậu tự động trong khi vẫn có khả năng giả lập các triển khai cụ thể.

Bạn có bắt đầu giải pháp ý tưởng không?

Trân

+0

Làm thế nào bạn mong chờ '@ Mock' và' @ Autowired' trên sân duy nhất để làm việc? Bạn có muốn nó chế nhạo, hoặc tự động có dây? Cũng tạo ra một danh sách trong thử nghiệm của bạn và hy vọng mùa xuân để phát hiện nó sẽ không bao giờ xảy ra. Tạo các mocks trong cấu hình mùa xuân của bạn thay vì các lớp của bạn, sử dụng phương thức 'mock' của nhà máy' Mockito' cho điều đó. –

+0

Tôi thực sự muốn nó chế nhạo, nhưng vì nó là một loại đậu mùa xuân, nên không được autowired là tốt?Tôi thực sự đã cố gắng để loại bỏ các autowired, nhưng nó đã không làm việc là tốt. Nó thậm chí còn tồi tệ hơn kể từ khi các validator là null và không bị chế nhạo. –

+0

bạn có thể sử dụng hàm tạo @Autowired ở trên. Vì vậy, trong bài kiểm tra, bạn có thể vượt qua trình xác nhận hợp lệ như các tham số hàm dựng cho lớp được kiểm tra. – freakman

Trả lời

9

Cuối cùng tôi figured it out ...

Đôi khi, hỏi một câu hỏi có thể cung cấp cho bạn một cách tiếp cận tốt hơn đến các vấn đề của bạn: p

Vấn đề là tôi đã liên kết các xác nhận để danh sách trước khi chúng bị chế nhạo. Các trình duyệt tính hợp lệ sau đó không có giá trị và không có tham chiếu nào có thể được cập nhật khi MockitAnnotations.initMocks(this).

Ngoài ra, để tránh các sự cố lặp trên List, tôi đã phải sử dụng @Spy thay vì @Mock.

Dưới đây là giải pháp finaly:

@Mock 
private EsmRegexValidator regexValidator; 

@Mock 
private EsmFormNotNullValidator notNullValidator; 

@Mock 
private EsmFormDataTypeValidator dataValidator; 

@InjectMocks 
private EsmFormValidatorManager validatorManager; 

@Spy 
private List<IEsmFormValidator> validators = new ArrayList<IEsmFormValidator>(); 

@Mock 
private ColumnDTO columnDTO; 

@Before 
public void init() { 

    MockitoAnnotations.initMocks(this); 

    validators.add(notNullValidator); 
    validators.add(regexValidator); 
    validators.add(dataValidator); 

    Mockito.when(columnDTO.getTitle()).thenReturn("Mock title"); 
    Mockito.when(columnDTO.getName()).thenReturn("Mock name"); 
} 
Các vấn đề liên quan