Потоковые строки из PostgreSQL (с размером выборки) - PullRequest
3 голосов
/ 02 мая 2019

Я бы хотел передавать результаты из PostgreSQL 11.2 и не читать все результаты сразу. Я использую новейшую стабильную версию SpringBoot 2.1.4.RELEASE.

Я прочитал статью, как это сделать в MySQL. http://knes1.github.io/blog/2015/2015-10-19-streaming-mysql-results-using-java8-streams-and-spring-data.html Я также прочитал статью, как это сделать в PostgreSQL: Поток репозитория Java 8 JPA построчно в Postgresql

У меня есть такой репозиторий:

public interface ProductRepository extends JpaRepository<Product, UUID> {
    @Query("SELECT p from Product p")
    @QueryHints(value = @QueryHint(name = HINT_FETCH_SIZE, value = "50"))
    Stream<Product> streamAll();
}

Чем я использую поток таким образом:

  productRepository.streamAll().forEach(product -> export(product));

Чтобы упростить пример, метод 'export' полностью пуст.

Когда я вызываю метод, я вижу запрос Hibernate

Hibernate: select product0_.id as id1_0_, product0_.created as created2_0_, product0_.description as descript3_0_, product0_.name as name4_0_, product0_.product_type_id as product_5_0_ from products product0_ order by product0_.id

и через некоторое время у меня возникает OutOfMemoryError. Подсказка запроса не помогла.

Как читать данные с помощью репозитория Spring Boot (или даже EntityManager) и оптимально загружать строки из БД. Я знаю, что могу сделать нумерацию страниц, но, как написано в статьях, это не самый оптимальный способ.

1 Ответ

1 голос
/ 02 мая 2019

В настоящее время с помощью пружины все данные извлекаются, и поток применяется только к данным, уже находящимся в памяти.

Если вы посмотрите на источник org.springframework.data.jpa.provider.PersistenceProvider, кажется, что он использует ScrollableResultsдля потоковой передачи данных.

Обычно ScrollableResults извлекает все данные из памяти.

Вы можете найти интересный полный анализ, используя базу данных MySql здесь , но, вероятно,то же самое работает для базы данных Postgres.

Так же, если вы думаете, что использовать решение, которому не нужно использовать много памяти, на самом деле это происходит, потому что базовая реализация не использует оптимальную реализацию.

...