Understanding the first level JPA cache
I can bet that every Java developer at least heard about L1 (aka EntityManager or Session) cache. But is your level of understanding it good enough? If you're not sure, consider going through this post.
At first, we need to know what the persistence context is. Following EntityManager JavaDoc we know, that:
"A persistence context is a set of entity instances in which for any persistent entity identity there is a unique entity instance. Within the persistence context, the entity instances and their lifecycle are managed."
In fact, the first level cache is the same as the persistence context. That means operations such as persist(), merge(), remove() are changing only internal collections in the context and are not synchronized to the underlying database. What is the mosts important here is what happens when you invoke the clear() method. It clears the L1 cache. But we know L1 == persistence context. Does it mean clearing L1 removes all entities? In fact yes - all entities will be dropped and never synchronized to the database. That's not a secret, it states in the documentation - "Unflushed changes made to the entity (...) will not be synchronized to the database." But who cares about the docs? :)
So how does it look in practice? Take a look at the code below:
If you omit flush() the entity won't hit the database. It will live only in your code, and after leaving method which created this object will be lost. Let's take a look at the next sample:
What will be the value of the name property after finishing this code? Of course still "old name", because in the moment when setName() has been invoked the entity is no longer managed and it has to be merged with the persistent context (by invoking em.merge(myEntity) method) to be the subject of the dirty checking.
But I'm not calling flush() method in my code and everything works!? But do you call clear()? That's what I thought. What is the default flush behavior? JPA by default flushes changes on commit as well as every query execution (FlushModeType.AUTO). If you change it to COMMIT (with em.setFlushMode(FlushModeType.COMMIT) method) then flush will occur (as name suggests) only on commit.
Deep understanding of the L1 behavior is especially important when dealing with batch operations. Why? If you want such operation to be effective, we must manually flush changes from time to time (let's say every 100 operations). Do you know, that flush() doesn't clear the persistence context? So what? Flush is not cheap because it must process all entities in the context to see if there is anything to synchronize with the database. If you won't clear the context manually immediately after flush(), every next operation will take longer and longer. To be honest this time grows exponentially, which seems to be sufficient reason to remember about mentioned technique.
If you're interested in deeper dive into persistence context please feel free to clone and play with this repository, which contains all described cases and examples.
At first, we need to know what the persistence context is. Following EntityManager JavaDoc we know, that:
"A persistence context is a set of entity instances in which for any persistent entity identity there is a unique entity instance. Within the persistence context, the entity instances and their lifecycle are managed."
In fact, the first level cache is the same as the persistence context. That means operations such as persist(), merge(), remove() are changing only internal collections in the context and are not synchronized to the underlying database. What is the mosts important here is what happens when you invoke the clear() method. It clears the L1 cache. But we know L1 == persistence context. Does it mean clearing L1 removes all entities? In fact yes - all entities will be dropped and never synchronized to the database. That's not a secret, it states in the documentation - "Unflushed changes made to the entity (...) will not be synchronized to the database." But who cares about the docs? :)
So how does it look in practice? Take a look at the code below:
em.persist(myEntity); // saves entity to the context em.flush(); // triggers insert into database em.clear(); // removes entity from the context == entity is no longer managed
If you omit flush() the entity won't hit the database. It will live only in your code, and after leaving method which created this object will be lost. Let's take a look at the next sample:
myEntity.setName("old name"); em.persist(myEntity); em.flush(); em.clear(); myEntity.setName("new name"); em.flush();
What will be the value of the name property after finishing this code? Of course still "old name", because in the moment when setName() has been invoked the entity is no longer managed and it has to be merged with the persistent context (by invoking em.merge(myEntity) method) to be the subject of the dirty checking.
But I'm not calling flush() method in my code and everything works!? But do you call clear()? That's what I thought. What is the default flush behavior? JPA by default flushes changes on commit as well as every query execution (FlushModeType.AUTO). If you change it to COMMIT (with em.setFlushMode(FlushModeType.COMMIT) method) then flush will occur (as name suggests) only on commit.
Deep understanding of the L1 behavior is especially important when dealing with batch operations. Why? If you want such operation to be effective, we must manually flush changes from time to time (let's say every 100 operations). Do you know, that flush() doesn't clear the persistence context? So what? Flush is not cheap because it must process all entities in the context to see if there is anything to synchronize with the database. If you won't clear the context manually immediately after flush(), every next operation will take longer and longer. To be honest this time grows exponentially, which seems to be sufficient reason to remember about mentioned technique.
If you're interested in deeper dive into persistence context please feel free to clone and play with this repository, which contains all described cases and examples.
Comments
very useful. I don’t know what I would have done if I had not
encountered such a step like this.
Digital Marketing Course In Chennai
Digital Marketing Training In Chennai
Seo Training in Chennai
Digital Marketing Course in Chennai
Digital Marketing Training in Chennai
Online Digital Marketing Training
SEO Training in Chennai
Abinitio Online Training Instittue
Microsoft Azure Online Training Instittue
App V Online Training Instittue
Digital Marketing Training
linux training in hyderabad
Angularjs Training in Chennai
Angularjs course in Chennai
Big Data Training in Chennai
German Classes in Chennai
AngularJS Training in Porur
AngularJS Training in Velachery
AngularJS Training in Adyar
Oracle Training in Chennai
Oracle Training institute in chennai
Unix Training in Chennai
Unix Shell Scripting Training in Chennai
LINUX Training in Chennai
LINUX Course in Chennai
Oracle Training in Velachery
Oracle Training in Tambaram
PHP Training in Chennai
web designing course in chennai
JAVA Training in Chennai
Hadoop Training in Chennai
Selenium Training in Chennai
German Classes in chennai
web designing course in chennai
web designing course in Porur
Aviation Academy in Chennai
Air hostess training in Chennai
Airport management courses in Chennai
Ground staff training in Chennai
Aviation Courses in Chennai
air hostess course in Chennai
Airport Management Training in Chennai
airport ground staff training courses in Chennai
All those who are into e-commerce and wants to know more about it and re-commerce.
Mainframe Training in Hyderabad
Well said! Nice content and thanks for sharing the post. Great written and useful info, Please keep blogging.
Pega Training in Chennai
Pega Course
Primavera Training in Chennai
Excel Training in Chennai
Corporate Training in Chennai
Embedded System Course Chennai
Tableau Training in Chennai
Spark Training in Chennai
Thanks & Regards,
VRIT Professionals,
No.1 Leading Web Designing Training Institute In Chennai.
And also those who are looking for
Web Designing Training Institute in Chennai
SEO Training Institute in Chennai
Photoshop Training Institute in Chennai
PHP & Mysql Training Institute in Chennai
Android Training Institute in Chennai
web designing course with placement
php training with placement in chennai
magento developer training | magento course in chennai
Corporate TRaining Spring Framework
Project Centers in Chennai For CSE
Spring Training in Chennai
Web Designing Training Institute in Chennai | web design training center in chennai | web designing course in chennai with placement
Mobile Application Development Courses in chennai
Data Science Training in Chennai | Data Science courses in Chennai
Professional packers and movers in chennai | PDY Packers | Household Goods Shifting
Web Designing Training Institute in Chennai | Web Designing courses in Chennai
PPC Companies in Delhi
SEO Company in Delhi
SEO Company in Delhi NCR
SMO Company in Delhi
SMO Company in India