Как установить количество элементов, которые будут извлекаться из серверной части DataProvider?
Я хочу лениво загружать некоторые данные из сетки в свой Vaadin View. Строки сетки иногда довольно большие, поэтому я хочу ограничить количество строк, которые загружаются одновременно, скажем, до 2.
Я пытался сделать это с помощью DataProvider.fromCallbacks()
. К сожалению, я не получаю желаемого результата, и меня немного смущают две функции, которые передаются в метод.
Насколько я понимаю, первая переданная функция описывает, как выбираются элементы, а вторая функция сообщает DataProvider максимально возможное количество элементов, которые могут быть извлечены.
fromCallbacks(CallbackDataProvider.FetchCallback fetchCallback, CallbackDataProvider.CountCallback countCallback) Создает нового поставщика данных, который использует обратные вызовы для выборки и подсчета элементов из любого резервного хранилища.
Я пробовал следующее, но это всегда приводит к получению большого количества предметов. (17 элементов в списке приводят к получению 17 элементов, 120 элементов в списке приводят к партиям по 50)
List<SomeObject> data = ... // filled with objects
DataProvider<CustromCell, Void> lazyLoadingProvider
= DataProvider.fromCallbacks(
query -> {
int offset = query.getOffset();
int limit = query.getLimit(); // Is this the amount of items that are fetched in one step?
if (offset + limit > data.size())
return data.stream();
List<CustromCell> cells = data.subList(offset,offset+limit);
//(offest,offset+2) crashes
return cells.stream()
},
query -> data.size() // Max possible items to fetch
);
grid.setDataProvider(lazyLoadingProvider);
Имеет следующее поведение:
Size Of Data: 219
Offset: 0
Limit: 50
Size Of Data: 219
Offset: 50
Limit: 50
Size Of Data: 219
Offset: 100
Limit: 50
Size Of Data: 219
Offset: 150
Limit: 50
Size Of Data: 219
Offset: 200
Limit: 19
Я должен позвонить getOffset()
а также getLimit()
объекта Query, в противном случае возникает исключение. Если я правильно понимаю, то лимит указывает, сколько элементов должно быть извлечено (в моем случае цель будет 2), но объект неизменен, поэтому я не могу изменить это значение (API запросов)?
tl;dr Как я могу сказать DataProvider, что он должен получать только 2 элемента из моей сетки одновременно?
Изменить: я обнаружил проблемы с github, связанные с моей проблемой (#6072, #3830)
Изменить 2: проблема с github была объединена, чтобы было более понятно, как работает метод getLimit(): https://github.com/vaadin/flow/issues/6996
2 ответа
Я смог найти решение для этого.
В query.getLimit()
зависит от размера страницы компонента (то есть сетки).
Цитата из Grid API:
Сетка ()
Создает новый экземпляр с размером страницы 50.
Моя сетка была инициализирована так: Grid a = new Grid();
что приводит к размеру страницы 50. query.getLimit()
вернет 50 в этом случае.
Сетка (int pageSize)
Создает новый экземпляр с указанным размером страницы.
Инициализируем сетку так: Grid a = new Grid(5);
. query.getLimit()
теперь вернет 5 в этом случае и DataProvider
получит только следующие 5 элементов.
Изменить: проблема github относительно этого вопроса SO была объединена: https://github.com/vaadin/flow/issues/6996
Если быть более точным, лимит запроса зависит от двух основных критериев:
- настройка размера страницы в вашей сетке (как вы уже нашли)
- и - в случае использования поставщика данных - размер поставщика данных.
И 2 других вторичных критерия / поведения:
Сколько элементов вы можете отображать в пользовательском интерфейсе одновременно. Если ваша сетка может отображать больше, чем установленный размер страницы за раз, то ограничение запроса будет автоматически адаптироваться в зависимости от размера поставщика данных и того, что я предполагаю, размер страницы по умолчанию (50)
Поскольку сетка может изменить ваш лимит запроса в зависимости от того, что я только что объяснил, если вы обновите свои данные (например, потому что вы применяете фильтрацию к поставщику данных), вашим лимитом больше не будет размер страницы сетки, если вы специально не установите его снова перед обновлением данных, например:
grid.setPageSize(GRID_PAGE_SIZE); grid.getDataProvider().refreshAll();
Таким образом, допустим, ваш поставщик данных возвращает 34 результата, вы установили размер страницы 5 и отображаете неограниченное количество результатов в пользовательском интерфейсе, у вас будет следующее поведение:
- Получить первые 5 элементов (настройка размера страницы)
- Обнаружено, что вы можете отображать больше элементов в пользовательском интерфейсе, поэтому запускайте вторую выборку в поставщике данных
- Получить от смещения 5 до предела 34
Я обнаружил, что эта комбинация вообще не задокументирована..