Hibernate - how to load into POJO which is not an entity - java

I have an entity named father and son1 and son2 who are mapped as collections inside father
Lets say father has a,b,c properties son1 has a,d and son 2 has b,e
and I have a bean which contains a,b,d,e called MyBean in one query.
Can I use it in a simple query using addEntity(MyBean.class) where my MyBean is not an hibernate entity (POJO)?
the POJO is as simple as it gets without annotations
class POJO {
Object a,b,d,e;
//get and set's and empty c'tor etc
}

use the new keyword and create the object in your search query
this only works for jpql

Can I use it in a simple query using addEntity(MyBean.class) where my MyBean is not an hibernate entity (POJO)?
I don't believe so. I believe that hibernate must know about all classes it persists via mappings.

Related

Use #Query annotation not in the JpaRepository

I have the User entity in the database and it's JPA entity. I also have the UserDescription class which hasn't table in the database. I want to instantiate UserDescription class using different tables and entities. But I don't want to use EntityManager for it. So I found SELECT new ... pattern which can be used in #Query annotation, it's the perfect solution.
But I have simple issue - I need to annotate some method declaration which should be in interface. Usually it's done in JpaRepository, but UserDescription - isn't entity, so I can't do this!
Also, I tried to create POJO interface(UserDescriptionService) with method declaration which annotated using #Query annotation, tried to create field with this interface in the controller(), and annotated it with Autowired and of course got:
Field userDescriptionService in UserController required a bean of type
'UserDescriptionService' that could not be found.
So, how can I use #Query annotation not in the JpaRepository or how can I get JpaRepository for the non-entity class?
As M. Deinum already mentioned. You are not forced to return only Entities in JpaRepositories.
You can use the Constructor Expression (aka select new) or also projections.
Find more about projections here:
https://docs.spring.io/spring-data/jpa/docs/2.0.9.RELEASE/reference/html/#projections

Fetching parent data using Child Data in OneToMany JPA Relationship in spring

I have a classic problem where i need to find the parent data by using child data in One To Many JPA relationship
Scenario
I need to find all the student who lives in one city(ex- Delhi) and locality ( ex- west delhi)
I have one class as Studen and Another class as Address , In address class we are having these attributes in Class
I also have StudentRepository , now what Query Method should i write in Repository where i can get all the Students on address Filters basis
I am using Spring boot and Spring data
Please help me
If you need i can share the code!!!
You can use the below method in StudentRepository for the desired result
findByAddressCityAndAddressLocality(String city, String locality);

How to instantiate a class from string FQN in database in hibernate?

I'm trying to convert a legacy application to hibernate.
I have an entity that has a field, which should be instantiated to object instance based on a fully qualified name string in a database.
Consider the example below - if I have somePackageName.FirstClass in a database the someObject field should be an instance of FirstClass.
I guess I could use property access and persist / retrieve a string but that doesn't look very elegant to me.
I cannot use #PostLoad etc. - I'm using pure hibernate with spring (not JPA) - these annotations get ignored.
I know for example in MyBatis one can register a custom handler for field. Would anything similar be available in Hibernate?
I'm new to hibernate so I'm not really sure what the options are.
#Entity
class SomePersistentClass{
private SomeInterface someObject;
}
class FirstClass implements SomeInterface{
}
class SecondClass implements SomeInterface{
}
You can use JPA features such as #PostLoad, etc callbacks simply by enabling the proper Hibernate event listeners. Check the Hibernate EntityManager guide for details.
But this one is even easier. This is the role of a Type in Hibernate. First, you'll have to write an implementation of org.hibernate.type.Type or org.hibernate.usertype.UserType and specify that in #Type( type=... ) that handles the conversions (lots of web resources about writing custom Hibernate types). Then annotate your 'someObject' attribute with #Type( type="your.custom.TypeImpl" )

Load Entity from View in JPA/Hibernate

I have an application which uses Spring and Hibernate. In my database there are some views that I need to load in some entities. So I'm trying to execute a native query and load the class withthe data retrieved from the view:
//In my DAO class (#Repository)
public List<MyClass> findMyEntities(){
Query query = em.createNativeQuery("SELECT * FROM V_myView", MyClass.class);
return query.getResultList();
}
and MyClass has the same fields as the column names of the view.
The problem is that Hibernate can't recognize MyClass because it's not an entity (it's not annotated with #Entity)
org.hibernate.MappingException: Unknown entity
If I put MyClass as an entity the system will put try to create/update a table for that entity, because I have configured it :
<property name="hibernate.hbm2ddl.auto" value="update"/>
So I come into these questions:
Can I disable "hibernate.hbm2ddl.auto" just for a single entity?
Is there any way to load the data from a view into a non-entity class?
If not, what would be the best way in my case for loading the data from a view into a class in hibernate?
Thanks
Placed on your class
#Entity
#Immutable
#Subselect(QUERY)
public MyClass {....... }
Hibernate execute the query to retrieve data, but not create the table or view. The downside of this is that it only serves to make readings.
You may use axtavt solution. You may also just execute your query, and transform the List<Object[]> it will return into a List<MyClass> explicitely. Or you may map your view as a read-only entity, which is probably the best solution, because it would allow for associations with other tables, querying through JPQL, Criteria, etc.
In my opinion, hibernate.hbm2ddl.auto should only be used for quick n' dirty prototypes. Use the hibernate tools to generate the SQL file allowing to create the schema, and modify it to remove the creation of the view. Anyway, if it's set to update, shouldn't it skip the table creation since it already exists (as a view)?
You can use AliasToBeanResultTransformer. Since it's a Hibernate-specific feature, you need to access the underlying Hibernate Session:
return em.unwrap(Session.class)
.createSQLQuery("...")
.setResultTransformer(new AliasToBeanResultTransformer(MyClass.class))
.list();

Efficiently determining the IDs of entities referenced via OneToMany relationship

Let's say I have a Hibernate entity that declares a OneToMany relationship to a different entity:
#Entity
public class SomeEntity {
#OneToMany(fetch = FetchType.LAZY)
private List<OtherEntity> otherEntities = new LinkedList<OtherEntity>();
[...]
}
When mapping SomeEntity to the corresponding DTO, all I need are the IDs that identify OtherEntity as primary key (i.e., I am not actually interested in OtherEntity instances).
Does Hibernate support this pattern, i.e., only retrieving the IDs of entities referenced via a OneToMany relationship?
I cannot influence how SomeEntity is retrieved (i.e., I have an existing SomeEntity instance retrieved within te scope of the current Hibernate session), but let's assume that lazy loading has not yet taken place, so just retrieving the child objects' IDs (rather than the complete objects) would actually yield a performance benefit.
Well, if you only need the entities' ids and you want to be economical about it, when you get those entities from the database you should state in your query that you only want to get the ids of each entry, using projections, something like :
SELECT Entity.id as entity FROM Entity WHERE ...
This will return an array of objects of the same type as Entity's id field type.
You can try obtaining the primary key without accessing the entity itself (without otherEntities.get(0).getId()). To do this you can use the PersistenceUnitUtil class:
PersistenceUnitUtil#getIdentifier(yourEntity)
The PersistenceUnitUtil can be obtained from the EntityManagerFactory. So it could be something like:
EntityManager em = ...
PersistenceUnitUtil = em.getEntityManagerFactory().getPersistenceUnitUtil();
Unfortunately, I'm not aware if this will prevent the entity loading from occuring. However, just accessing the otherEntities collection or even obtaining references to each entity will not make the instance to be loaded; you need to invoke a method on the fetched entity in order to be sure it will be loaded.
You also might consider creating a #NamedQuery and return only the OtherEntity ID's.
HTH!
From hibernate reference, section 2.2.2.1.
http://docs.jboss.org/hibernate/annotations/3.5/reference/en/html/entity.html#entity-mapping-property
Declare your columns as lazy initialized:
#Basic(fetch = FetchType.LAZY)
private String getYourProperty() {
}
You also need to disable proxies for your entity class and byte instrument it. There is an example here:
Making a OneToOne-relation lazy
You can use the below HQL as told in the documentation to establish this.
session.createQuery(select new OtherEntity(oe.id) OtherEntity oe
where oe.parentSomeEntity.someId = :someId).list();//also set someId.
Add a constructor in OtherEntity to set the id also there should be a mapping to SomeEntity in OtherEntity.
This HQL will give you a List<OtherEntity> with only id set in the bean.

Categories

Resources