package com.vaadin.tests.server.component.abstractlisting;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Stream;

import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;

import com.vaadin.data.Listing;
import com.vaadin.server.data.BackEndDataSource;
import com.vaadin.server.data.DataSource;
import com.vaadin.server.data.ListDataSource;
import com.vaadin.server.data.Query;
import com.vaadin.ui.AbstractListing;

public class AbstractListingTest {

    private static final String[] ITEM_ARRAY = new String[] { "Foo", "Bar",
            "Baz" };

    private Listing<String> listing;
    private List<String> items;

    @Before
    public void setUp() {
        items = new ArrayList<>(Arrays.asList(ITEM_ARRAY));
        listing = new AbstractListing<String>() {
        };
    }

    @Test
    public void testSetItemsWithCollection() {
        listing.setItems(items);
        listing.getDataSource().apply(new Query()).forEach(
                str -> Assert.assertTrue("Unexpected item in data source",
                        items.remove(str)));
        Assert.assertTrue("Not all items from list were in data source",
                items.isEmpty());
    }

    @Test
    public void testSetItemsWithVarargs() {
        listing.setItems(ITEM_ARRAY);
        listing.getDataSource().apply(new Query()).forEach(
                str -> Assert.assertTrue("Unexpected item in data source",
                        items.remove(str)));
        Assert.assertTrue("Not all items from list were in data source",
                items.isEmpty());
    }

    @Test
    public void testSetDataSource() {
        ListDataSource<String> dataSource = DataSource.create(items);
        listing.setDataSource(dataSource);
        Assert.assertEquals("setDataSource did not set data source", dataSource,
                listing.getDataSource());
        listing.setDataSource(new BackEndDataSource<>(q -> Stream.of(ITEM_ARRAY)
                .skip(q.getOffset()).limit(q.getLimit()),
                q -> ITEM_ARRAY.length));
        Assert.assertNotEquals("setDataSource did not replace data source",
                dataSource, listing.getDataSource());
    }
}

@@ -240,40 +240,8 @@
 t;%0A%0A
-import com.vaadin.data.Listing;%0A
 impo
@@ -277,32 +277,32 @@
 kEndDataSource;%0A
+
 import com.vaadi
@@ -410,16 +410,66 @@
 .Query;%0A
+import com.vaadin.server.data.TypedDataGenerator;%0A
 import c
@@ -499,16 +499,51 @@
 sting;%0A%0A
+import elemental.json.JsonObject;%0A%0A
 public c
@@ -570,16 +570,908 @@
 Test %7B%0A%0A
+    private final class TestListing extends AbstractListing%3CString%3E %7B%0A%0A        @Override%0A        public void addDataGenerator(TypedDataGenerator%3CString%3E generator) %7B%0A            super.addDataGenerator(generator);%0A        %7D%0A%0A        @Override%0A        public void removeDataGenerator(TypedDataGenerator%3CString%3E generator) %7B%0A            super.removeDataGenerator(generator);%0A        %7D%0A%0A        /**%0A         * Used to execute data generation%0A         */%0A        public void runDataGeneration() %7B%0A            super.getDataCommunicator().beforeClientResponse(true);%0A        %7D%0A    %7D%0A%0A    private final class CountGenerator implements TypedDataGenerator%3CString%3E %7B%0A%0A        int callCount = 0;%0A%0A        @Override%0A        public void generateData(String data, JsonObject jsonObject) %7B%0A            ++callCount;%0A        %7D%0A%0A        @Override%0A        public void destroyData(String data) %7B%0A        %7D%0A    %7D%0A%0A
     priv
@@ -1572,31 +1572,27 @@
 private 
+Test
 List
-ing%3CStr
 ing
-%3E
  listing
@@ -1750,45 +1750,21 @@
 new 
-AbstractListing%3CString%3E() %7B%0A        %7D
+TestListing()
 ;%0A  
@@ -3071,32 +3071,32 @@
 e data source%22,%0A
-
                 
@@ -3138,11 +3138,1115 @@
 );%0A    %7D
+%0A%0A    @Test%0A    public void testAddDataGeneartorBeforeDataSource() %7B%0A        CountGenerator generator = new CountGenerator();%0A        listing.addDataGenerator(generator);%0A        listing.setItems(%22Foo%22);%0A        listing.runDataGeneration();%0A        Assert.assertEquals(%22Generator should have been called once%22, 1,%0A                generator.callCount);%0A    %7D%0A%0A    @Test%0A    public void testAddDataGeneartorAfterDataSource() %7B%0A        CountGenerator generator = new CountGenerator();%0A        listing.setItems(%22Foo%22);%0A        listing.addDataGenerator(generator);%0A        listing.runDataGeneration();%0A        Assert.assertEquals(%22Generator should have been called once%22, 1,%0A                generator.callCount);%0A    %7D%0A%0A    @Test%0A    public void testRemoveDataGeneartor() %7B%0A        listing.setItems(%22Foo%22);%0A        CountGenerator generator = new CountGenerator();%0A        listing.addDataGenerator(generator);%0A        listing.removeDataGenerator(generator);%0A        listing.runDataGeneration();%0A        Assert.assertEquals(%22Generator should not have been called%22, 0,%0A                generator.callCount);%0A    %7D
 %0A%7D%0A

Add unit tests for adding and executing data generators