Как добавить валидаторы в Vaadin 8?

В Vaadin 7 была функция addValidator, но в Vaadin 8 ее нет.

Vaadin 7 Пример:

   TextField user = new TextField("User:");
   user.setRequired(true);
   user.setInputPrompt("Your username");
   user.addValidator(new NullValidator("Username can't be empty", false));
   user.setInvalidAllowed(false);

person Diego D    schedule 27.02.2017    source источник


Ответы (3)


Я нашел ответ здесь: Что нового

Пример:

new Binder<Person>().forField(tf)
    .withValidator(str -> str.length() == 4, "Must be 4 chars")
    .withConverter(new StringToIntegerConverter("Must be Integer"))
    .withValidator(integer -> integer.equals(2017), "Wrong date")
    .bind(Person::getBirthYear, Person::setBirthYear);

введите описание изображения здесь

person Diego D    schedule 27.02.2017
comment
Что делать, если у вас нет подшивки из-за создания динамической формы? - person Stephane Grenier; 19.07.2017

принятый ответ Диего Д. выглядит правильным. Этот код, похоже, взят из этого очень короткого (3 минуты), но очень полезного видео, опубликованного компанией Vaadin, Типобезопасная проверка до и после преобразователя. Показывает новый подход Vaadin 8 к валидации. Я добавлю несколько примечаний, покажу расширенный синтаксис и предоставлю полный пример кода для полноценного рабочего приложения.

Валидатор + Биндер

Одно большое отличие Vaadin 8 заключается в том, что валидаторам требуется использование скоросшивателя. Раньше вы прикрепляли валидатор к полю, но теперь в Vaadin 8 вы прикрепляете валидатор только к привязке. Команда Vaadin осознает, что для некоторых простых ситуаций это требование связующего может раздражать, но по большей части они разумно ожидают, что ситуации, требующие проверки, вполне вероятно, также выполняют привязку. Я считаю, что это очень логичное переосмысление. Обсуждается в другом видео компании Vaadin, веб-семинаре: что нового в Vaadin 8?.

Валидация и конвертеры

Мы определяем два разных валидатора: один будет вызываться до того, как конвертер преобразует введенные пользователем данные, а другой будет вызываться после преобразования. Таким образом, порядок вызовов методов withValidator и withConverter в свободном стиле является ключом к правильному поведению здесь. Конечно, beforeConversion и afterConversion - плохие названия для объектов валидатора, но они сделаны так, чтобы прояснить намерение запуска до или после конвертера в этой демонстрации.

Лямбда-синтаксис необязательный

Один валидатор использует традиционный стиль кода Java, переопределяя метод. Другой валидатор использует синтаксис Lambda. Посмотрите видео и ознакомьтесь с ответом Диего D, где приведен код, еще более упрощенный с помощью однострочных лямбда-аргументов.

package com.example.valapp;

import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.data.Binder;
import com.vaadin.data.ValidationResult;
import com.vaadin.data.Validator;
import com.vaadin.data.ValueContext;
import com.vaadin.data.converter.StringToIntegerConverter;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.*;

import javax.servlet.annotation.WebServlet;


/**
 * This UI is the application entry point. A UI may either represent a browser window
 * (or tab) or some part of a html page where a Vaadin application is embedded.
 * <p>
 * The UI is initialized using {@link #init(VaadinRequest)}. This method is intended to be
 * overridden to add component to the user interface and initialize non-component functionality.
 */
@Theme ( "mytheme" )
public class MyUI extends UI {

    @Override
    protected void init ( final VaadinRequest vaadinRequest ) {

        final TextField tf = new TextField ( "Enter year of birth:" );

        Validator<String> beforeConversion = new Validator < String > ( ) {
            @Override
            public ValidationResult apply ( String s, ValueContext valueContext ) {
               if(s.length ()!= 4) {
                   return  ValidationResult.error ( "Year must consist of 4 digits" );
               } else {
                   return  ValidationResult.ok () ;
               }
            }
        } ;

        Validator<Integer> afterConversion = Validator.from ( value -> value.equals ( 2017 ), "Wrong year." );

        new Binder < Person > ( )
                .forField ( tf )
                .withValidator ( beforeConversion )
                .withConverter ( new StringToIntegerConverter ( "Input must be Integer" ) )
                .withValidator ( afterConversion )
                .bind ( Person:: getYearOfBirth, Person:: setYearOfBirth );

        Button button = new Button ( "Tell me" );
        button.addClickListener ( event -> Notification.show("This is the caption", "This is the description", Notification.Type.HUMANIZED_MESSAGE) );

        setContent ( new VerticalLayout ( tf  , button ) );
    }

    @WebServlet ( urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true )
    @VaadinServletConfiguration ( ui = MyUI.class, productionMode = false )
    public static class MyUIServlet extends VaadinServlet {
    }
}
person Basil Bourque    schedule 24.03.2017

Что делать, если у вас нет подшивки из-за создания динамической формы?

Vaadin 8.1 поддерживает удаление привязки для поля, которое поддерживает динамические формы. Если вы сделаете поле невидимым, удалите привязку для этого поля. Когда вы сделаете поле видимым, снова добавьте подшивку.

person Brett Sutton    schedule 07.03.2018