Поддержка Dropwizard для проверки в нересурсных классах (JSR-303) - PullRequest
0 голосов
/ 11 мая 2018

В соответствии с этой ссылкой :

Если вам нужно проверить сущности за пределами конечных точек ресурса, к средству проверки можно обратиться в Среде при первом запуске приложения.

Это означает, что @Valid ниже не будет работать, и мне придется программно использовать валидатор на объекте profile и что-то делать с ошибками, которые возвращаются:

public class ProfilesManager {  
    ...
    public void createProfile(@Valid Profile profile) {
        Set<ConstraintViolation<Profile>> errors = validator.validate(profile);
        ...
    }
}

В Spring Boot все, что мне нужно сделать, - это пометить его @Validated, и автоматически будет выдан ConstraintViolationException:

@Validated
@Component
public class ProfilesManager { 
    public void createProfile(@Valid Profile profile) {
        // if invalid, exception thrown before getting here
    }
}

Существует ли эквивалентное решение для Dropwizard, официального или стороннего разработчика

1 Ответ

0 голосов
/ 13 мая 2018

Это легко реализовать самостоятельно, используя службу перехвата HK2 .Все, что вам нужно сделать, это предоставить MethodInteceptor, который проверяет параметры метода для аннотации @Valid и проверяет эти параметры с помощью Validator

public class ValidationMethodInterceptor implements MethodInterceptor {

    ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
    Validator validator = factory.getValidator();

    @Override
    public Object invoke(MethodInvocation invocation) throws Throwable {
        Object[] args = invocation.getArguments();
        for (int i = 0; i < args.length; i++) {
            Parameter parameter = invocation.getMethod().getParameters()[i];
            if (parameter.getAnnotation(Valid.class) != null) {
                handleValidation(args[i]);
            }
        }
        return invocation.proceed();
    }

    private void handleValidation(Object arg) {
        Set<ConstraintViolation<Object>> constraintViolations
                = validator.validate(arg);

        if (!constraintViolations.isEmpty()) {
            throw new IllegalArgumentException(
                    "constraint violations in bean argument");
        }
    }
}

В вашей реализации InterceptionService вы можете решить,какие службы должны быть проверены с помощью пользовательского Filter, который ищет пользовательскую аннотацию @Validated для класса обслуживания

public class ValidatedFilter implements Filter {

    @Override
    public boolean matches(Descriptor descriptor) {
        try {
            return Class.forName(descriptor.getImplementation())
                    .isAnnotationPresent(Validated.class);
        } catch (ClassNotFoundException e) {
            throw new RuntimeException(e);
        }
    }
}

public class ValidationInterceptionService implements InterceptionService {

    private final static MethodInterceptor METHOD_INTERCEPTOR = new ValidationMethodInterceptor();
    private final static List<MethodInterceptor> METHOD_LIST = Collections.singletonList(METHOD_INTERCEPTOR);

    @Override
    public Filter getDescriptorFilter() {
        return new ValidatedFilter();
    }

    @Override
    public List<MethodInterceptor> getMethodInterceptors(Method method) {
        for (Parameter parameter: method.getParameters()) {
            if (parameter.isAnnotationPresent(Valid.class)) {
                return METHOD_LIST;
            }
        }
        return null;
    }

    @Override
    public List<ConstructorInterceptor> getConstructorInterceptors(Constructor<?> c) {
        return null;
    }
}

См. полный пример с тестовым примером в этом репозитории GitHub .

...