Exception using Vaadin CRUD with ListDataProvider

Hi Guys,

I’m getting an exception when setting up a simple Vaadin CRUD component with a ListDataProvider.
When I comment out the setDataProvider line, the page loads up just fine (albeit with no records).

Any Ideas? I’m pretty new to v12, but it seems to me that ListDataProvider implements all the serial predicate filters - so I’m not quite sure what’s going on here.

This app is based on bakery demo. So the repository .findAll() just returns a list of beans.

~Ben

Java Code:

Crud<Recipe> crud = new Crud<>(Recipe.class, createForm(layout));
        setSizeFull()
        add(crud)

        crud.getGrid().removeColumnByKey("id");
        crud.getGrid().removeColumnByKey("version");
        crud.setDataProvider(new ListDataProvider(service.getRepository().findAll()));

Exception Log (The important bit):

java.lang.ClassCastException: com.vaadin.flow.component.crud.CrudFilter cannot be cast to com.vaadin.flow.function.SerializablePredicate
	at java.util.Optional.map(Optional.java:215) ~[na:1.8.0_191]

	at com.vaadin.flow.data.provider.ListDataProvider.getFilteredStream(ListDataProvider.java:99) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.data.provider.ListDataProvider.size(ListDataProvider.java:86) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.data.provider.DataProviderWrapper.size(DataProviderWrapper.java:85) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.data.provider.DataCommunicator.getDataProviderSize(DataCommunicator.java:336) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.data.provider.DataCommunicator.flush(DataCommunicator.java:449) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.data.provider.DataCommunicator.lambda$requestFlush$2f364bb9$1(DataCommunicator.java:421) ~[flow-data-1.2.4.jar:1.2.4]

	at com.vaadin.flow.internal.StateTree.lambda$runExecutionsBeforeClientResponse$1(StateTree.java:350) ~[flow-server-1.2.4.jar:1.2.4]

	at java.util.ArrayList.forEach(ArrayList.java:1257) ~[na:1.8.0_191]

Hi Ben,
thanks for your report.

The problem is that CrudGrid makes it mandatory for dataprovider to use filter CrudFilter. There are 2 obvious ways I see:

  1. Use another instance of Grid:
Grid<Recipe> grid = new Grid<>(Recipe.class);
Crud<Recipe> crud = new Crud<>(Recipe.class, grid, createForm(layout));
grid.setDataProvider(new ListDataProvider(service.getRepository().findAll()));
  1. Use custom filterable data provider which has CrudFilter filter type instead of ListDataProvider:
List<Recipe> data = service.getRepository().findAll();
AbstractBackEndDataProvider<Recipe, CrudFilter> dp = new AbstractBackEndDataProvider<Recipe, CrudFilter>(){
	@Override
	protected Stream<Recipe> fetchFromBackEnd(
			Query<Recipe, CrudFilter> query) {
		return data.stream();
	}

	@Override
	protected int sizeInBackEnd(Query<Recipe, CrudFilter> query) {
		return data.size();
	}
};

Thanks Aliaksandr, I’ll try this for sure.

I had my suspicions about utilising CrudFilter, but I thought it should have been a standard element seeing as they were asking for a DataProvider.

I would have thought the Crud should work with any DataProvider.

I didn’t realise you can instantiate a Crud with your own Grid. I’ll give that a go also.