What is the relationship between DTO and lazy-loading in Hibernate
I know what is DTO: An object that carries data between processes in order to reduce the number of method calls. and I know what is lazy-loading in hibernate.
I read this sentences in "Full Stack Development with JHipster" book : JHipster uses DTO (Data Transfer Object) and VM (View Model) on the server side. DTOs are for transferring data from the service layer to and from the resource layer. They break the Hibernate transactions and avoids further lazy loading from being triggered by the resource layer.
I don't understand the relationship between DTO and lazy loading.
Lazy loading is for entities, not DTOs.
A JPA entity can be represented as a POJO or a Proxy.
As I explained in this article, using
EntityManager.find gives you a POJO:
Post post = entityManager.find(Post.class, postId);
EtityManager.getReference method gives you a Proxy:
Post post = entityManager.getReference(Post.class, postId);
The POJO has its basic properties initialized because a SELECT statement was executed to fetch the entity. The Proxy does not hit the database upon creation. Only the id is set based on the provided entity identifier. Only you access the Proxy properties, a SELECT statement will be executed.
Proxies are also used for collections (e.g.
@ManyToMany) which are using the
FetchType.LAZY strategy by default. Once you access the LAZY collection, a SELECT statement will be executed to fetch the associated collection.
Now, a DTO is based on a projection, hence a SELECT statement is executed prior to populating the DTO. For this purpose, you can say that the DTO is eagerly loaded every time.
DTOs are much more efficient than entities for read-only projections because you load just the table columns that you explicitly requested. For more details about the best way to use DTOs with JPA and Hibernate, check out this article.
Eager/Lazy Loading In Hibernate, What is hibernate proxy and how it helps in lazy loading? Should I use OpenSessionInView Pattern or use DTO objects in my service layer, to counter the lazy loading exceptions. Is it a good practice to return Domain/Entity objects from Service layer? Or is it a good practice to return DTO objects, which are later serialized into xml/json in web service layer.
If you pass Hibernate managed persistent entities to the resource layer with LazyLoading enabled, the resource layer will invoke
get-methods in order to read their properties some of which are possibly not initialized at that time. Hibernate will then lazily load the data of that particular property from the persisntet store, sending an SQL statement (possibly each time starting and committing a new transaction) and waiting for response which is quite slow. If this happens hundred of times, each time having to initialize another property, each time triggering a lazy load, the user has to wait...
If you prepare a DTO in your service layer, containing all the data relevant to the resource layer, read access to that DTO is highly efficient without the risk of hitting the database for any
get-method invokation as everything relevant is in memory already. No subsequent lazy load will be triggered.
What is lazy loading in hibernate?, the "real" object from the database whenever one of its methods is called. Lazy Loading in Hibernate. Hibernate applies lazy loading approach on entities and associations by providing a proxy implementation of classes. Hibernate intercepts calls to an entity by substituting it with a proxy derived from an entity’s class.
In Simple terms: If you call getter of a lazy loading marked field, Hibernate will make a db query for that data.
This is one of the reasons you should not return Entities as backend response... any JSON conversion(Serialization)/getter call will trigger unwanted loading of the data.
whereas a DTO is made specifically to transfer data as per use and you create DTO from these Entities (Multiple DTO can be created from one Entity) and pick only required data fields
Eg. User entity: has user details and list of friends UserDetailsDTO: would only require the details and dont need 1000's of friends mapped to the user... and their friends... UserFriendsDTO: we can selectively get the friends names or ids for this DTO
What is proxy in the context of load() method of Hibernate?, Those objects add an extra layer on top of the domain objects, and are are using JPA, this is because the service layer is transactional, so lazy-loading will work). For a many-to-many relationship on the owner side: it will use DTOs from the into the Java compiler, that will generate the required mapping automatically. Say you have a parent and that parent has a collection of children. Hibernate now can "lazy-load" the children, which means that it does not actually load all the children when loading the parent. Instead, it loads them when requested to do so.
Hibernate Lazy Loading Tutorial, To enable lazy loading explicitly you must use “fetch = FetchType.LAZY” on a association which you want to lazy load when you are using hibernate annotations. Hibernate lazy loading refer to strategy when data is loaded lazily, on demand. 1. Hibernate lazy loading – why we need it? Consider one of common Internet web application: the online store. The store maintains a catalog of products. At the crudest level, this can be modeled as a catalog entity managing a series of product entities.
Using DTOs, 1 The Main Difference Between DTOs And Entities; 2 Projections For Write Operations; 3 Projections To make sure that Hibernate doesn't fetch any extra data, I set the FetchType for the @ManyToOne association on the Book entity to LAZY. The code that you don’t see is the transactional code (enabled by the @Transactional annotation in your DAOs) and this is something that you always need to keep in mind when using Lazy loading. Having said that, let’s take a look at an example of Lazy loading using our User object.
Entities or DTOs - When should you use which , The best way to lazy load entity attributes using JPA and Hibernate When it comes to reading data, subentities are very similar to DTO The fetching strategy is declared in the mapping relationship to define how Hibernate fetch its related collections and entities. Fetching Strategies. There are four fetching strategies. 1. fetch-“join” = Disable the lazy loading, always load all the collections and entities.
- Should i use DTOs or read-only Entities for read-only operations?
- It depends on how much data you need to be fetched. If you need the entire entity, use that. If you only need a subset of that entity, then use a DTO.
- Thanks Vlad. Is it legal to access an entity in presentation layer?
- Since the UI usually operated on JSON data from the server, it's just a matter whether it's fine to transform the entity to JSON. So, if the entity doesn't have proxies, it's not that much different than serializing a DTO to JSON. Proxies usually complicate this process if they are uninitialized and the mapper tries to access them.
- You're welcome. If you enjoyed this answer, check out my Hibernate tutorial collection with over 250 articles on best practices and tips.