Búsqueda de sitios web

¿Cómo ejecutar la actualización de inserción por lotes en Hibernate?


En este artículo, veremos cómo podemos ejecutar la inserción/actualización por lotes en hibernación.

Siempre que ejecutamos una declaración SQL, lo hacemos realizando una llamada de red a la base de datos. Ahora, si tenemos que insertar 10 entradas en nuestra tabla de base de datos, entonces tenemos que realizar 10 llamadas de red. En su lugar, podemos optimizar las llamadas de nuestra red mediante el uso de procesamiento por lotes. El procesamiento por lotes nos permite ejecutar un grupo de declaraciones SQL en una sola llamada de red.

Para comprender e implementar esto, definamos nuestras entidades:

@Entity public class Parent { @Id @GeneratedValue(strategy = GenerationType.AUTO) private long id; private String name; // Getters //Setters }

Para habilitar el procesamiento por lotes en hibernación, necesitamos agregar una propiedad a nuestra aplicación archivo de propiedades:

spring.jpa.properties.hibernate.jdbc.batch_size=3

Ahora, necesitamos ejecutar la función de persistencia del EntityManager para insertar los datos en la base de datos.

Ejemplo

@Autowired private EntityManager entityManager; @Test Public void InsertInBatch(){ for (int i = 0; i < 6; i++) { Parent parent = Parent[i]; entityManager.persist(parent); } }

Producción

"batch":true, "querySize":1, "batchSize":3, "query":["insert into parent (name, id) values (?, ?)"], "params":[["P1","1"],["P2","2"],["P3","3"]]
"batch":true, "querySize":1, "batchSize":3, "query":["insert into parent (name, id) values (?, ?)"], "params":[["P4","4"],["P5","5"],["P6","6"]]

Podemos ver desde la consola que la inserción en la tabla principal se realiza en un lote de tamaño 3.

Mientras persisten las entidades, puede ocurrir OutOfMemoryException porque Hibernate almacena las entidades en el contexto de persistencia. Entonces, para fines de optimización, podemos usar fluir() y borrar() del administrador de entidades después de cada lote.

Actualización por lotes significa actualizar una gran cantidad de datos en una sola llamada de red.

Para la actualización por lotes, el proceso es el mismo. Necesitamos agregar las siguientes dos declaraciones en el archivo de propiedades de nuestra aplicación y luego ejecutar el proceso de actualización.

spring.jpa.properties.hibernate.order_updates=true
spring.jpa.properties.hibernate.batch_versioned_data=true

Ejemplo

Código para actualizar los datos:

@Autowired private EntityManager entityManager; @Test public void UpdateInBatch() { TypedQuery<Parent> query = entityManager.createQuery("SELECT p from Parent p", Parent.class); List<Parent> Parents = query.getResultList(); int i=1; for (Parent parent : Parents) { String s="Parent"+Integer.toString(i); i++; parent.setName(s); } }

Hibernate ahora unirá estas declaraciones en un solo lote y las ejecutará.

Producción

"batch":true, "querySize":1, "batchSize":3, "query":["update parent set name=? where id=?"], "params":[["Parent1","1"],[" Parent2","2"],[" Parent3","3"]]
"batch":true, "querySize":1, "batchSize":3, "query":["update parent set name=? where id=?"], "params":[["Parent4","4"],["Parent5","5"],["Parent6","6"]]

Podemos ver desde la consola que la actualización de datos en la tabla principal se realiza en un lote de tamaño 3.