2017-02-08 11 views
1

Ich habe einen REST-Service mit Jersey & Spring-Boot geschrieben. Ich habe benutzerdefinierte Validator-Klassen für POST-Parameter geschrieben. Ich möchte das gleiche tun. Ich konnte nicht herausfinden, wie es geht. Mein Validator sieht aus wie folgt:Jersey benutzerdefinierte Validatoren unittest

@Retention(RetentionPolicy.RUNTIME) 
@Constraint(validatedBy = ValidTaskForCreate.Validator.class) 
public @interface ValidTaskForCreate { 
    String message() default "Invalid Request to create a Task"; 
    Class<?>[] groups() default {}; 

Class<? extends Payload>[] payload() default {}; 
public class Validator implements ConstraintValidator<ValidTaskForCreate, Task> { 

    @Override 
    public void initialize(ValidTaskForCreate constraintAnnotation) { 
    } 

    @Override 
    public boolean isValid(final Task task, ConstraintValidatorContext context) { 
      context.disableDefaultConstraintViolation(); 
      if(task.getName() == null || task.getName().isEmpty()) { 
       context.buildConstraintViolationWithTemplate("Task name should be specified").addConstraintViolation(); 
       return false; 
      } 

      if(task.getTaskType() == null) {  
       context.buildConstraintViolationWithTemplate("Specify a valid TaskType in the range of [1..3]").addConstraintViolation(); 
       return false; 
      } 
      return true; 
     } 

    } 
} 

Jetzt möchte ich die isValid() Funktion testen, indem verschiedene Aufgaben Objekte übergeben. Ich bin mir nicht sicher, wie ich diese Methode jetzt nennen soll. ich Instanz Validator Klasse wie folgt erstellen,

ValidTaskForCreate.Validator taskValidator = null; 
    taskValidator = new ValidTaskForCreate.Validator(); 

nennen isValid(), kann ich taskValidator.isValid (verwenden). Aber ich kann nicht das ConstraintValidatorContext-Objekt als zweiten Parameter übergeben.

Oder gibt es einen Weg zu UnitTest benutzerdefinierten Validierungsklassen wie diesem?

Antwort

1

Ich weiß jedoch nicht, wie das ConstraintValidatorContext-Objekt erstellt wird, das als zweiter Parameter übergeben wird.

Verwenden Sie einfach Mockito und verspotten Sie es. Überprüfen Sie dann, ob die richtigen Methoden aufgerufen wurden. So testen Sie das Verhalten der Einheit, wenn Abhängigkeiten beteiligt sind.

private ConstraintValidatorContext context; 
private ConstraintValidatorContext.ConstraintViolationBuilder builder; 

@Before 
public void setup() { 
    // mock the context 
    context = Mockito.mock(ConstraintValidatorContext.class); 

    // context.buildConstraintViolationWithTemplate returns 
    // ConstraintValidatorContext.ConstraintViolationBuilder 
    // so we mock that too as you will be calling one of it's methods 
    builder = Mockito.mock(ConstraintValidatorContext.ConstraintViolationBuilder.class); 

    // when the context.buildConstraintViolationWithTemplate is called, 
    // the mock should return the builder. 
    Mockito.when(context.buildConstraintViolationWithTemplate(Mockito.anyString())) 
     .thenReturn(builder); 
} 

@Test 
public void test() { 
    // call the unit to be tested 
    boolean result = ..isValid(badTask, context); 

    // assert the result 
    assertThat(result).isFalse(); 

    // verify that the context is called with the correct argument 
    Mockito.verify(context) 
      .buildConstraintViolationWithTemplate("Task name should be specified"); 
} 

Beachten Sie die Verwendung von Mockito direkt. In den meisten Fällen werden Sie wahrscheinlich nur statische Importe verwenden, um es weniger ausführlich zu machen. Ich wollte es nur lesbarer machen