vaadin 10保存具有多对多关系的实体列表

时间:2019-03-08 09:02:02

标签: spring hibernate vaadin10

我有两个实体(项目和学生),具有很多对很多的关系,并且具有一个文本字段和两个元素列表的表单。

当我添加新学生时,出现两个元素列表。一个列表(左)具有所有可用的项目,另一个列表(右)具有将由学生选择的项目。

当我尝试绑定正确的列表时,问题就来了。我还有其他示例,但具有这样的简单元素:

getBinder().forField(tfDescription).withConverter(String::trim, String::trim).bind(Project::getDescription, Project::setDescription);

有人知道如何绑定或保存元素列表吗?

我要保存的一个示例是此示例,但在vaadin 10中:TwinCol

@Entity
public class Project {

     @Id
     @GeneratedValue(strategy = GenerationType.AUTO)
     private Long id;

     @ManyToMany(cascade = { CascadeType.ALL }, fetch = FetchType.EAGER)
     @JoinTable(name="student_project", joinColumns= 
               {@JoinColumn(referencedColumnName="ID")}
               , inverseJoinColumns= 
               {@JoinColumn(referencedColumnName="ID")})    
    private List<Student> students;

    private String description;

    public Project() {
    }

    public Project(String description) {
        super();
        this.description = description;
    }

    public Long getId() {
        return id;
    }

    public String getDescription() {
        return description;
    }

    public List<Student> getStudents() {
        return students;
    }

    public void setStudents(List<Student> students) {
        this.students = students;
    }
}

@Entity
public class Student {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    @ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL, mappedBy = "students")
    @Fetch(value = FetchMode.SUBSELECT)
    private List<Project> projects;

    private String name;

    public Student(String name) {
        this.name = name;
    }

    public Long getId() {
        return id;
    }

    public String getName() {
        return name;
    }


    public List<Project> getProjects() {
        return projects;
    }
}

----------------------------------------------

@SpringComponent
@Scope("request")
public class ProjectEditorDialog extends AbstractEditorDialog<Student> {
    private TextField tfName;

    @Autowired
    private ProjectRepository projectRepository;

    private ListBox<Project> lbLeft; // List of projects to select
    private Button bLeft;
    private Button bRight;
    private ListBox<Project> lbRight; // List of projects selected
    private Project tempProject;
    private List<Project> listLeftProjects = new ArrayList<Project>();
    private List<Project> listRightProjects = new ArrayList<Project>();

    @PostConstruct
    private void init() {
        createNameField();
        createLeftColumn();
        createCenterColumn();
        createRightColumn();
        checkButtons();
    }

    @Override
    protected void confirmDelete() {
        openConfirmationDialog("Delete Student",
                String.format("Delete student: [%s]?", getCurrentItem().getName()));
    }

    private void createNameField() {
        tfName = new TextField("Name");
        tfName.setRequired(true);
        getFormLayout().add(tfName);

        getBinder().forField(tfName).withConverter(String::trim, String::trim).bind(Student::getName,
                Student::setName);
    }

    private void createLeftColumn() {
        VerticalLayout leftColumn = new VerticalLayout();
        Label lTitle = new Label("Project availables");
        leftColumn.add(lTitle);

        lbLeft = new ListBox<Project>();
        listLeftProjects = projectRepository.findAll();
        lbLeft.setItems(listLeftProjects);

        lbLeft.setRenderer(new ComponentRenderer<>(item -> {
            Label label = new Label(item.getName());
            label.getStyle().set("propertyDescription", "value");
            return label;
        }));

        leftColumn.add(lbLeft);
        getHorizontalLayout().add(leftColumn);
    }

    private void createCenterColumn() {
        VerticalLayout centerColumn = new VerticalLayout();
        bRight = new Button(">>");
        bRight.addClickListener(new ComponentEventListener<ClickEvent<Button>>() {

            @Override
            public void onComponentEvent(ClickEvent<Button> event) {
                tempProject = lbLeft.getValue();
                if (tempProject != null) {
                    listLeftProjects.remove(tempProject);
                    listRightProjects.add(tempProject);

                    lbLeft.setItems(listLeftProjects);
                    lbRight.setItems(listRightProjects);

                    checkButtons();
                }
            }
        });

        bLeft = new Button("<<");
        bLeft.addClickListener(new ComponentEventListener<ClickEvent<Button>>() {

            @Override
            public void onComponentEvent(ClickEvent<Button> event) {
                tempProject = lbRight.getValue();

                if (tempProject != null) {
                    listRightProjects.remove(tempProject);
                    listLeftProjects.add(tempProject);

                    lbLeft.setItems(listLeftProjects);
                    lbRight.setItems(listRightProjects);
                    checkButtons();
                }
            }
        });

        centerColumn.add(bRight);
        centerColumn.add(bLeft);
        getHorizontalLayout().add(centerColumn);
    }

    private void createRightColumn() {
        VerticalLayout rightColumn = new VerticalLayout();
        Label lTitle = new Label("Projects selected");
        rightColumn.add(lTitle);
        lbRight = new ListBox<Project>();
        lbRight.setRenderer(new ComponentRenderer<>(item -> {
            Label label = new Label(item.getDescription());
            label.getStyle().set("propertyDescription", "value");
            return label;
        }));

        rightColumn.add(lbRight);
        getHorizontalLayout().add(rightColumn);
        /*This doesn't work -- getBinder().forField(lbRight).bind(Student::getProjects, Student::setProjects);*/
    }

    private void checkButtons() {
        if (listRightProjects.size() > 0)
            bLeft.setEnabled(true);
        else
            bLeft.setEnabled(false);

        if (listLeftProjects.size() > 0)
            bRight.setEnabled(true);
        else
            bRight.setEnabled(false);
    }
}

0 个答案:

没有答案