Database:
I want to get a list User, who have the same Monhoc (it has maMH= MH1).
My code :
private final SessionFactory sf = HibernateUtil.getSessionFactory();
Public List<User> listUserMonHoc() {
try {
sf.getCurrentSession().beginTransaction();
Query query = sf.getCurrentSession().createSQLQuery("select a.username, a.name from Monhoc b join b.User a where b.mamh = :id");
query.setString("id", "MH1");
List<User> list = query.list();
sf.getCurrentSession().getTransaction().commit();
return list;
} catch (Exception e) {
System.out.println("sai");
System.out.println(e.toString());
//return null;
e.printStackTrace();
return null;
}
}
ERROR message: ERROR: Table 'b.user' doesn't exist.
Thank you!
As i can see you have problems with your query. First you must join your third table and then search by id from the monhoc table.
Second there is a problem here
Query query = sf.getCurrentSession().createSQLQuery("select a.username, a.name from Monhoc b join b.User a where b.mamh = :id");
you must change b.User to User, cause b is allias of your Monhoc table.
So as a native query in MySql will look something like this :
SELECT u.username, u.name
FROM user AS u
INNER JOIN user_monhoc AS um
ON u.username = um.user_id
INNER JOIN monhoc AS m
ON um.mh_id = m.mamh
WHERE ....
I am using inner join (it can be different depents on your needs).
Related
I have entity Customer, Car:
#Entity
public class Customer{
List<Car> cars;
...
}
#Entity
public class Car{
List<Customer> previousOwners;
...
}
Basicly Customer can have multiple cars rented, and Cars remember previous owners.
Both entities have more relations, and i am omiting them.
Now want to retrieve all cars of Customer:
public List<Car> getCars(int customerId) {
List<Car> cars= new ArrayList<>();
Transaction tx = null;
try (Session session = HibernateUtil.getSessionFactory().openSession()) {
tx = session.beginTransaction();
cars= (List<Car>) session.createQuery("SELECT cars FROM Customer u JOIN u.cars cars WHERE u.id IN :ids ").setParameter("ids", customerId).list();
} catch (HibernateException e) {
if (tx != null) tx.rollback();
e.printStackTrace();
}
return cars;
}
This will return list of Cars, i need to use JOIN cuz lazyinitialization is set to FALSE.
Now i want to fetch Cars and their previos owners. But i am unable to think of any query, i tried using:
"SELECT cars FROM Customer u JOIN u.cars cars JOIN u.cars.previousOwners previousOwners WHERE u.id IN :ids " but this did nothing.
What i am aming for is to return object Car, with list inside, when i tried using
"SELECT cars, cars.previousOwner FROM Customer u JOIN u.cars cars JOIN u.cars.previousOwner previosOwner WHERE u.id IN :ids "
it returned the list of previousOwners, but not inside Car object, but as second element in returned list...
How can i create such query? Thanks fo help!
You probably want a (LEFT) JOIN FETCH query:
SELECT cars FROM Customer u
JOIN u.cars cars
JOIN FETCH cars.previousOwners
WHERE u.id IN :ids
This instructs Hibernate to join the cars.previousOwners relation even when it's declared to use lazy-fetching by default. Use a left join fetch if you also want to return cars with no previousOwners.
See the docs for more info.
Currently i'm using PostgreSQL database in my Spring MVC web application. I'm able to get the values when i execute the query in PgAdmin tool.
In my query, I'm trying to join 4 tables and get the values.
My query is:
SELECT (s.school_id, u.first_name, u.last_name, u.username, u.email, p.plan_name, s.start_date, s.end_date, s.subscription_price, (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'T' and t.school_id = s.school_id), (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'A' and t.school_id = s.school_id), (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'S' and t.school_id = s.school_id)) FROM school s inner join user u on s.user_created = u.user_id inner join plan p on s.current_plan = p.plan_Id where s.application_id = 30 and s.site_id = 42;
When I use this same query in my Dao method, I'm getting error like:
No Dialect mapping for JDBC type: 1111
Code used in dao method:
public List<Object[]> getInformationValues(int applicationId, int siteId) throws HibernateException {
Session session = getCurrentSession();
Query query = session.createSQLQuery("SELECT (s.school_id, u.first_name, u.last_name, u.username, u.email, p.plan_name, s.start_date, s.end_date, s.subscription_price, (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'T' and t.school_id = s.school_id), (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'A' and t.school_id = s.school_id), (SELECT COUNT(*) FROM school_user t WHERE t.user_type = 'S' and t.school_id = s.school_id)) FROM school s inner join user u on (s.user_created = u.user_id) inner join plan p on (s.current_plan = p.plan_Id) where s.application_id = :applicationId and s.site_id = :siteId") .setParameter("applicationId", applicationId) .setParameter("siteId", siteId);
List<Object[]> results = query.list();
return results;
}
Is there any way to fix this issue?
Here is how I fetch data:
public static List<SubjectSubjectUsersUsers> getAllSubjectUsers()
{
List<SubjectSubjectUsersUsers> theList = null;
Session session = ServiceLocator.getSessionFactory().openSession();
try{
theList = session.createSQLQuery("SELECT s.name as subject_name, u.name as user_name, u.surname as user_surname, su.id as id from subjects s "
+ "join subject_users su on s.id = su.subject_id join users u on su.user_id = u.id")
.addScalar("subject_name", StandardBasicTypes.STRING)
.addScalar("user_name", StandardBasicTypes.STRING)
.addScalar("user_surname", StandardBasicTypes.STRING)
.addScalar("id", StandardBasicTypes.LONG)
.setResultTransformer(Transformers.aliasToBean(SubjectSubjectUsersUsers.class)).list();
}catch(Exception e){
e.printStackTrace();
}finally{
session.flush();
session.close();
}
return theList;
}
The problem is when I update data manually in the DB, the fetched data is not changed. But when I reload the server and IDE it works. What could be the cause of the problem? I guess I used the session object in the incorrect way. Thank you.
you need to set CacheMode to refresh
query.setCacheMode(CacheMode.REFRESH);
Your query will look like -
theList = session.createSQLQuery("SELECT s.name as subject_name, u.name as user_name, u.surname as user_surname, su.id as id from subjects s "
+ "join subject_users su on s.id = su.subject_id join users u on su.user_id = u.id")
.setCacheMode(CacheMode.REFRESH)
.addScalar("subject_name", StandardBasicTypes.STRING)
.addScalar("user_name", StandardBasicTypes.STRING)
.addScalar("user_surname", StandardBasicTypes.STRING)
.addScalar("id", StandardBasicTypes.LONG)
.setResultTransformer(Transformers.aliasToBean(SubjectSubjectUsersUsers.class)).list();
However it's a bad idea to update DB from outsite while using hibernate, otherwise you won't get benefits of hibernate cache.
Query :
#Query("Select p.name,t.points from Player p,Tournament t where t.id=?1 And p.id=t.player_id")
I have my player and tournament entity and their corresponding JPA repositories. But the problem is we can get only entities from our query, but i want to do above query, please help me with this i am new to it.
this is my sql query i want to add but where to add i am not getting:
Select p.name, t.points_rewarded from player p, participant t where t.tournament_id="1" and t.player_id=p.id;
This is how you can do it with JPQL for JPA:
String queryString = "select p.name, t.points from Tournament t," +
" Player p where t.player_id=p.id " +
"and t.id= :id_tournament";
Query query = this.entityManager.createQuery(queryString);
query.setParameter("id_tournament", 1);
List results = query.getResultList();
You can take a look at this JPA Query Structure (JPQL / Criteria) for further information about JPQL queries.
And this is ho you can do it using HQL for Hibernate, these are two ways of doing it:
String hql = "SELECT p.name, t.points from Player p,Tournament t WHERE t.id= '1' And p.id=t.player_id";
Query query = session.createQuery(hql);
List results = query.list();
Or using query.setParameter() method like this:
String hql = "SELECT p.name, t.points from Player p,Tournament t WHERE t.id= :tournament_id And p.id=t.player_id";
Query query = session.createQuery(hql);
query.setParameter("tournament_id",1);
List results = query.list();
You can take a look at this HQL Tutorial for further information about HQL queries.
Note:
In both cases you will get a list of Object's array List<Object[]> where element one array[0] is the p.name and the second one is t.points.
TypedQuery instead of normal Query in JPA
this is what i was looking for, thanks chsdk for help, i have to create pojos class, and in above link answer is working fine foe me,
Here is my code sample
String querystring = "SELECT new example.restDTO.ResultDTO(p.name,t.pointsRewarded) FROM Player p, Participant t where t.tournamentId=?1 AND t.playerId = p.id ORDER by t.pointsRewarded DESC";
EntityManager em = this.emf.createEntityManager();
try {
Query queryresults = em.createQuery(querystring).setParameter(1, tournamentId);
List<ResultDTO> result =queryresults.getResultList();
return new ResponseEntity<>(result, HttpStatus.OK);
} catch (Exception e) {
e.printStackTrace();
return new ResponseEntity<>(HttpStatus.BAD_REQUEST);
} finally {
if (em != null) {
em.close();
}}
I am trying to inner join multiple and get as result an entity class Medecin so here is the methode :
public Medecin getMedecinByLoginPassword(String login, String password) {
String sql = "SELECT {m.*},{r.*},{s.*},{c.*} FROM medecin m INNER JOIN role r ON m.idrole = r.idrole INNER JOIN service s ON m.service_idservice = s.idservice INNER JOIN centre c ON s.centre_idcentre = c.idcentre WHERE m.login = :login AND m.password = :password";
SQLQuery query = getSessionFactory().getCurrentSession().createSQLQuery(sql);
query.addEntity("m",Medecin.class).addJoin("r", "m.role").addJoin("s", "m.service").addJoin("c", "s.centre").setResultTransformer(Transformers.aliasToBean(Medecin.class));
query.setParameter("login", login);
query.setParameter("password", password);
List results = query.list();
return (Medecin) results.get(0);
}
But i get this Error
GRAVE: org.hibernate.PropertyNotFoundException: Could not find setter for m on class com.mdsoft.gelt.model.Medecin
at org.hibernate.property.ChainedPropertyAccessor.getSetter(ChainedPropertyAccessor.java:44)
at org.hibernate.transform.AliasToBeanResultTransformer.transformTuple(AliasToBeanResultTransformer.java:57)
how can i get ride from this error