vaadin / flow

Vaadin Flow is a Java framework binding Vaadin web components to Java. This is part of Vaadin 10+.
Apache License 2.0
590 stars 164 forks source link

IndexOutOfBoundsException on UI#push() call #19503

Open VISTALL opened 1 month ago

VISTALL commented 1 month ago

Description of the bug

Rare exception throw this

java.lang.IndexOutOfBoundsException: toIndex = 350
    at java.base/java.util.AbstractList.subListRangeCheck(AbstractList.java:509)
    at java.base/java.util.AbstractList.subList(AbstractList.java:499)
    at com.vaadin.flow.data.provider.DataCommunicator.collectKeysToFlush(DataCommunicator.java:1460)
    at com.vaadin.flow.data.provider.DataCommunicator.flush(DataCommunicator.java:1230)
    at com.vaadin.flow.data.provider.DataCommunicator.lambda$requestFlush$7258256f$1(DataCommunicator.java:1138)
    at com.vaadin.flow.internal.StateTree.lambda$runExecutionsBeforeClientResponse$2(StateTree.java:397)
    at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:184)
    at java.base/java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:179)
    at java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1708)
    at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:509)
    at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:499)
    at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:151)
    at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:174)
    at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
    at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:596)
    at com.vaadin.flow.internal.StateTree.runExecutionsBeforeClientResponse(StateTree.java:392)
    at com.vaadin.flow.server.communication.UidlWriter.encodeChanges(UidlWriter.java:394)
    at com.vaadin.flow.server.communication.UidlWriter.createUidl(UidlWriter.java:170)
    at com.vaadin.flow.server.communication.UidlWriter.createUidl(UidlWriter.java:215)
    at com.vaadin.flow.server.communication.AtmospherePushConnection.push(AtmospherePushConnection.java:207)
    at com.vaadin.flow.server.communication.AtmospherePushConnection.push(AtmospherePushConnection.java:181)
    at com.vaadin.flow.component.UI.push(UI.java:743)
    at <internal code>
    at com.vaadin.flow.component.UI.accessSynchronously(UI.java:489)
    at com.vaadin.flow.component.UI$2.execute(UI.java:564)
    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572)
    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:317)
    at com.vaadin.flow.server.VaadinService.runPendingAccessTasks(VaadinService.java:2082)
    at com.vaadin.flow.server.VaadinSession.unlock(VaadinSession.java:708)
    at com.vaadin.flow.server.VaadinService.ensureAccessQueuePurged(VaadinService.java:2047)
    at com.vaadin.flow.server.VaadinSession.unlock(VaadinSession.java:737)
    at com.vaadin.flow.server.VaadinService.ensureAccessQueuePurged(VaadinService.java:2047)
    at com.vaadin.flow.server.VaadinSession.unlock(VaadinSession.java:737)
    at com.vaadin.flow.server.VaadinService.ensureAccessQueuePurged(VaadinService.java:2047)
    at com.vaadin.flow.server.VaadinService.accessSession(VaadinService.java:2014)
    at com.vaadin.flow.server.VaadinSession.access(VaadinSession.java:1012)
    at com.vaadin.flow.component.UI.access(UI.java:561)
    at com.vaadin.flow.component.UI.lambda$accessLater$18bf859d$1(UI.java:622)
    at <internal code>
    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144)
    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642)
    at java.base/java.lang.Thread.run(Thread.java:1583)

Expected behavior

Expected - no errors :)

Minimal reproducible example

code like this

            ui.accessLater(() -> {
                // internal logic 

                ui.push();
            }, () -> {
            }).run();

Can't find reproduce example - very rare exception

Versions

mcollovati commented 1 month ago

Do you have implemented a custom DataProvider or using callback methods for lazy data binding? If so, could you show the relevant code?

VISTALL commented 1 month ago

Hello. I have big application in Vaadin Flow, but I'm always use built-in methods, in one case it's ListDataProvider but - collection type is CopyOnWriteArrayList (and there no random access to this Grid, and there an additional lock protection).

Also there an override for key mapper

        grid.getDataCommunicator().getKeyMapper().setIdentifierGetter(RawConfigRow::getKeys); // its map<string, object>

Which is immutable map, and never change