HIbernate commit () e flush ()

Ho cercato molto su org.hibernate.Transaction.commit() e ho letto molto su org.hibernate.Transaction.commit() e org.hibernate.Session.flush() , conosco lo scopo di ciascun metodo, ma ho ancora una domanda.

È buona pratica chiamare a mano il metodo org.hibernate.Session.flush() ? Come detto nei documenti org.hibernate.Session ,

Deve essere chiamato alla fine di un’unità di lavoro, prima di eseguire la transazione e chiudere la sessione (in base alla modalità flush, Transaction.commit () chiama questo metodo).

Potresti spiegarmi come chiamare org.hibernate.Session.flush() a mano se org.hibernate.Transaction.commit() lo chiamerà automaticamente?

Grazie!

Nel Manuale di Hibernate puoi vedere questo esempio

 Session session = sessionFactory.openSession(); Transaction tx = session.beginTransaction(); for ( int i=0; i<100000; i++ ) { Customer customer = new Customer(.....); session.save(customer); if ( i % 20 == 0 ) { //20, same as the JDBC batch size //flush a batch of inserts and release memory: session.flush(); session.clear(); } } tx.commit(); session.close(); 

Senza la chiamata al metodo flush, la cache di primo livello genererebbe una OutOfMemoryException

Inoltre puoi dare un'occhiata a questo post sul flushing

Un caso comune per lo svuotamento esplicito è quando si crea una nuova quadro persistente e si desidera che essa abbia una chiave primaria artificiale generata e assegnata ad essa, in modo che sia ansible utilizzarla in un secondo momento nella stessa transazione. In tal caso, la chiamata di flush comporterebbe l’assegnazione di un ID alla tua quadro.

Un altro caso è se ci sono molte cose nella cache di 1 ° livello e vorreste cancellarlo periodicamente (in modo da ridurre la quantità di memoria usata dalla cache) ma volete comunque impegnare il tutto insieme . Questo è il caso che la risposta di Aleksei copre (+1 da me).

flush() sincronizzerà il tuo database con lo stato corrente di oggetti / oggetti contenuti nella memoria ma non impegnerà la transazione. Quindi, se ottieni qualche eccezione dopo che è stato chiamato flush() , la transazione verrà ripristinata. Puoi sincronizzare il tuo database con piccoli blocchi di dati usando flush() invece di commettere grandi dati contemporaneamente usando commit() e affrontare il rischio di ottenere un’eccezione di memoria insufficiente .

commit() renderà permanenti i dati memorizzati nel database. Non è ansible eseguire il rollback della transazione una volta che il commit() avuto esito positivo.

flush (); Flushing è il processo di sincronizzazione dell’archivio persistente sottostante con lo stato persistibile contenuto in memory.it che verrà aggiornato o inserito nelle tabelle nella transazione in esecuzione, ma potrebbe non essere in grado di confermare tali modifiche.

È necessario eseguire il flushing dell’elaborazione batch altrimenti potrebbe fornire OutOfMemoryException.

Commettere(); Commit renderà il commit del database. Quando si ha un object persistente e si cambia un valore su di esso, esso diventa sporco e l’ibernazione ha bisogno di svuotare queste modifiche sul layer di persistenza. Quindi si deve eseguire il commit ma si finisce anche l’unità di lavoro. transaction.commit ()

Per impostazione predefinita, la modalità a livello è AUTO che significa che: “La Sessione viene talvolta svuotata prima dell’esecuzione della query per garantire che le query non restituiscano mai lo stato non aggiornato”, ma la maggior parte della sessione temporale viene svuotata quando si effettuano le modifiche. La chiamata manuale del metodo flush è utile quando si utilizza FlushMode = MANUAL o si desidera eseguire un qualche tipo di ottimizzazione. Ma non l’ho mai fatto, quindi non posso darti consigli pratici.

In genere non è consigliabile chiamare il flush in modo esplicito a meno che non sia necessario. L’ibernazione di solito chiama automaticamente Flush alla fine della transazione e dovremmo lasciargli fare il suo lavoro. Ora, ci sono alcuni casi in cui potrebbe essere necessario chiamare esplicitamente flush dove una seconda attività dipende dal risultato della prima attività di Persistenza, entrambi all’interno della stessa transazione.

Ad esempio, potrebbe essere necessario mantenere una nuova Entità e quindi utilizzare l’Id di quell’ quadro per svolgere qualche altra attività all’interno della stessa transazione, in tal caso è richiesto di svuotare esplicitamente l’entity framework per prima.

 @Transactional void someServiceMethod(Entity entity){ em.persist(entity); em.flush() //need to explicitly flush in order to use id in next statement doSomeThingElse(entity.getId()); } 

Nota inoltre che, lo svuotamento esplicito non causa un commit del database, un commit del database viene eseguito solo alla fine di una transazione, quindi se si verifica un errore di runtime dopo aver chiamato flush, le modifiche continueranno a essere ripristinate.

session.flush () è metodo synchronize significa inserire i dati nel database sequenzialmente. Se usiamo questo metodo, i dati non verranno archiviati nel database ma verrà archiviato nella cache, se qualsiasi eccezione aumenterà nel mezzo possiamo gestirla. Ma commit () memorizzerà i dati nel database, se stiamo memorizzando più quantità di dati, allora potrebbe esserci la possibilità di uscire da Of Memory Exception, come nel programma JDBC in argomento Save point