Bind an arraylist of Strings

Migrating from Vaadin 7-> 8 I’ve decided to start using the binder interface and I have the following question.

Suppose we have an object

public class Person {
 private String name = "";
 private ArrayList<String> companies = new ArrayList<String>();


by using the binder I can bind the normal fields such as boolean/text etc using:
binder.forField(nameTextField).bind(Person::getName, Person::setName);

but the question is HOW to bind the

ArrayList<String> to a Grid<String>


Is there a way or the binder just doesn’t support nested objects?


Hi, do you already have a solution for this issue??

I have exactly the same problem :smiley:

thank you Paul

Nope no solution so far…
I just have to use the binder for all the other fields and before saving I have to ‘manually’ check the entire list and put it at the object…
If anyone has any idea please be my guest!! :slight_smile:

I made a quick hack which seems to work for the simple use case of one way (read only) binding a List<String> property of a Bean to a custom Composite (which in turn is really just a Grid); here’s the full runnable source code:

package org.vaadin;

import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.shared.Registration;
import com.vaadin.ui.*;

import javax.servlet.annotation.WebServlet;
import java.time.LocalDate;
import java.util.Arrays;
import java.util.List;

public class MyUI extends UI {

    public static class StringList extends Composite implements HasValue<List<String>> {

        private List<String> strings = null;
        Grid.Column<String, String> column;
        Grid<String> grid;

        public StringList() {
            grid = new Grid<>();
            column = grid.addColumn(s -> s);

        public void setValue(List<String> strings) {
            this.strings = strings;

        public void setCaption(String caption) {

        public List<String> getValue() {
            return strings;

        public Registration addValueChangeListener(ValueChangeListener<List<String>> valueChangeListener) {
            return null;

        public void setRequiredIndicatorVisible(boolean b) {

        public boolean isRequiredIndicatorVisible() {
            return super.isRequiredIndicatorVisible();

        public void setReadOnly(boolean readOnly) {

        public boolean isReadOnly() {
            return super.isReadOnly();

    protected void init(VaadinRequest vaadinRequest) {
        final VerticalLayout layout = new VerticalLayout();

        Person person = new Person();
        person.setFruits(Arrays.asList("banana", "apple", "potato"));

        TextField nameTextField = new TextField("Name");
        DateField dateField = new DateField("Day of birth");
        StringList stringList = new StringList();

        layout.addComponents(nameTextField, dateField, stringList);

        Binder<Person> personBinder = new Binder<>();
        personBinder.forField(nameTextField).bind(Person::getName, Person::setName);
        personBinder.forField(dateField).bind(Person::getDayOfBirth, Person::setDayOfBirth);
        personBinder.forField(stringList).bind(Person::getFruits, Person::setFruits);



    public static class Person {
        private String name;

        private LocalDate dayOfBirth;

        private List<String> fruits;

        public String getName() {
            return name;

        public void setName(String name) {
   = name;

        public List<String> getFruits() {
            return fruits;

        public void setFruits(List<String> fruits) {
            this.fruits = fruits;

        public LocalDate getDayOfBirth() {
            return dayOfBirth;

        public void setDayOfBirth(LocalDate dayOfBirth) {
            this.dayOfBirth = dayOfBirth;

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

I’m gonna add a little explanation, supporting Ollis code example:

For any kind of list or set, even if it’s “just” a list of Strings, you will have to use Grids. By utilizing the grid’s editor, the user is able to see and edit any item in that list. The items shown in the grid are NOT copies of the bound bean’s list so any change in the grid will directly change the items of the bound bean.

You could even define your own grid editor save listener if you wanted to save these items in a DB independently of the bound bean, but I recommend only doing this if proper [cascading]
( is not possible.

Edit: With ollis example of the StringList class, the grid editor is not used, therefore the user will not be able to edit any of the shown Strings. But what he did is implementing HasValue which will enable it to set up the binding in the same way any other binding is done - with binder.forField(field).bind(getter, setter); If you enable the grid editor in Ollis example (only if you need to edit the strings there of course), it will be the perfect solution in my opinion.