Pessimistic Locking in JPA


  • PESSIMISTIC_READ – allows us to obtain a shared lock and prevent the data from being updated or deleted, Whenever we want to just read data and don’t encounter dirty reads, we could use PESSIMISTIC_READ (shared lock). We won’t be able to make any updates or deletes though. It sometimes happens that the database we use doesn’t support the PESSIMISTIC_READ lock, so it’s possible that we obtain the PESSIMISTIC_WRITE lock instead.
  • PESSIMISTIC_WRITE – allows us to obtain an exclusive lock and prevent the data from being read, updated or deleted, Any transaction that needs to acquire a lock on data and make changes to it should obtain the PESSIMISTIC_WRITE lock. According to the JPA specification, holding PESSIMISTIC_WRITE lock will prevent other transactions from reading, updating or deleting the data. Please note that some database systems implement multi-version concurrency control which allows readers to fetch data that has been already blocked.


entityManager.find(Student.class, studentId, LockModeType.PESSIMISTIC_READ);


Query query = entityManager.createQuery("from Student where studentId = :studentId");
query.setParameter("studentId", studentId);



query.setLockMode(LockModeType.PESSIMISTIC_WRITE);


query.getResultList()


Student resultStudent = entityManager.find(Student.class, studentId);

entityManager.lock(resultStudent, LockModeType.PESSIMISTIC_WRITE);


Student resultStudent = entityManager.find(Student.class, studentId);

entityManager.refresh(resultStudent, LockModeType.PESSIMISTIC_FORCE_INCREMENT);


public interface ArticleRepository extends CrudRepository<Article, Long> {



  @Lock(LockModeType.PESSIMISTIC_WRITE)

  @Query("select a from Article a where a.id = :id")

  Article findArticleForWrite(@Param("id") Long id);



  @Lock(LockModeType.PESSIMISTIC_READ)

  @Query("select a from Article a where a.id = :id")

  Article findArticleForRead(@Param("id") Long id);

}



@NamedQuery(name="lockStudent",

  query="SELECT s FROM Student s WHERE s.id LIKE :studentId",

  lockMode = PESSIMISTIC_READ)


Set Lock timeout

Map<String, Object> properties = new HashMap<>(); 
map.put("javax.persistence.lock.timeout", 1000L); 


entityManager.find(
  Student.class, 1L, LockModeType.PESSIMISTIC_READ, properties);

Comments

Popular posts from this blog

Fixing the DeepSpeed Import Error While Fine-Tuning the Qwen Model

Amazon Linux 2023 - User data configuration for launch templates to connect to the EKS cluster

How to create ISM policy and rotate logs in opensearch