Join tables hibernate + group by - java

I need to do this query with Java + Hibernate.
SELECT
table2.id,
COUNT(table2.id) AS count
FROM
table1
JOIN table2
ON table1.fk_tb2 = table2.id --many2one
GROUP BY
table2.id
I would use DetachedCriteria class.....how can i do this ?

Try using projections like this:
Criteria table1Crit = session.createCriteria("table1");
Criteria table2Crit = table1Crit.createCriteria("table2", Criteria.INNER_JOIN);
table2Crit.setProjection( Property.forName("id").count() );

use your query with createNativeQuery method

Related

How to do a subquery on the same table by using JPA Hibernate?

Help me to convert the below mentioned query to Hibernate JPA.
Query query= entityManager.createQuery("Select a,b,c,d from table1 where d IN (Select d from table1 where a=1 and b=2");
Just giving an alias should work
entityManager.createQuery("Select a,b,c,d from table1 t
where t.d IN (Select r.d from table1 r where r.a=1 and r.b=2");

JPA Criteria query with inner join of aggregation

I'm trying to write a CriteriaQuery which will query latest observation for each city. City is defined by city_code field, while latest record is defined by observation_time field.
I can easily write it in a plain SQL, but I cant understand how to do it with jpa criteria api.
select distinct m.* from
(select city_code cc, max(observation_time) mo
from observations group by city_code) mx, observations m
where m.city_code = mx.cc and m.observation_time = mx.mo`
It is possible when You are open for loose efficiency.
So first let's transform our query to logical equivalent one:
select distinct m.* from observations m where
m.observation_time = (select max(inn. observation_time) from observations inn
where inn.city_code = m.city_code);
then let's translate it to JPA CriteriaQuery:
public List<Observation> maxForEveryWithSubquery() {
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
CriteriaQuery<Observation> query = builder.createQuery(Observation.class);
Root<Observation> observation = query.from(Observation.class);
query.select(observation);
Subquery<LocalDateTime> subQuery = query.subquery(LocalDateTime.class);
Root<Observation> observationInner = subQuery.from(Observation.class);
subQuery.where(
builder.equal(
observation.get(Observation_.cityCode),
observationInner.get(Observation_.cityCode)
)
);
Subquery<LocalDateTime> subSelect = subQuery.select(builder.greatest(observationInner.get(Observation_.observationTime)));
query.where(
builder.equal(subSelect.getSelection(), observation.get(Observation_.observationTime))
);
TypedQuery<Observation> typedQuery = entityManager.createQuery(query);
return typedQuery.getResultList();
}
Unfortunately JPA does not support sub queries in FROM clause. You need to write a native query or use framework like FluentJPA.

Hibernate Criteria - Excluding group by clause in the select statement

I've written this in sql server:
select max(processed_trans_id) from EQUITY_TRANSACTION where transaction_date <= '2016-06-22' and company_id=75 group by comp_acct_id
But when I try to write the same in Hibernate Criteria, like this:
DetachedCriteria dCriteria = DetachedCriteria.forClass(EquityTransaction.class)
.add(Restrictions.eq("clientCompany.id", sb.getClientCompany().getId()))
.add(Restrictions.le("transactionDate", sb.getQualifyDate()))
.setProjection(Projections.projectionList()
.add(Projections.max("processedTransaction.id"), "processedTransaction.id")
.add(Projections.groupProperty("holderCompanyAccount.id")));
I get this as the sql query from hibernate:
select max(processed_trans_id), comp_acct_id from EQUITY_TRANSACTION where transaction_date <= '2016-06-22' and company_id=75 group by comp_acct_id
How do I replicate the original SQL query in Hibernate criteria?
I was able to resolve this using the following query. Worked like a charm!
DetachedCriteria dCriteriaEt1 = DetachedCriteria.forClass(EquityTransaction.class, "et1")
.add(Restrictions.eq("clientCompany.id", decldDvd.getClientCompany().getId()))
.add(Restrictions.le("transactionDate", decldDvd.getQualifyDate()))
.setProjection(Projections.projectionList()
.add(Projections.max("processedTransaction.id"), "processedTransaction.id"))
.add(Restrictions.eqProperty("et1.holderCompanyAccount.id", "et2.holderCompanyAccount.id"));
logger.info("Retrieving all qualified company account balances...");
Criteria getQualifiedBalances = dao.getSession().createCriteria(EquityTransaction.class, "et2")
.add(Subqueries.propertyIn("processedTransaction.id", dCriteriaEt1))
.add(Restrictions.gt("balance", 0l))
.setProjection(Projections.projectionList()
.add(Projections.property("holderCompanyAccount.id"),"holderCompanyAccount.id")
.add(Projections.property("balance"), "balance"))
.addOrder(Order.asc("holderCompanyAccount.id"))
.addOrder(Order.desc("processedTransaction.id"))
.setResultTransformer(new AliasToBeanNestedResultTransformer(EquityTransaction.class));

Add count of child table to select from parent with hibernate criteria API

How can I execute this SQL query using the Hibernate Criteria API?
SELECT c.*, count(r.id) FROM COURSE c left join REFERRAL r on c.id = r.course_id group by c.id
Something like this seems close enough:
Criteria criteria = currentSession().createCriteria(Referral.class, "r");
criteria.createAlias("r.course", "course");
ProjectionList projections = Projections.projectionList();
projections.add(Projections.groupProperty("course.id"));
projections.add(Projections.count("r.id"));
return list(criteria
.setProjection(projections));

Hibernate detached queries as a part of the criteria query

java experts can you please help me write detached queries as a part of the criteria query for the following SQL statement.
select A.*
FROM AETABLE A
where not exists
(
select entryid
FROM AETABLE B
where B.classpk = A.classpk
and B.userid = A.userid
and B.modifiedDate > A.modifiedDate
)
and userid = 10146
You need to write a correlated subquery. Assuming property / class names match column / table names above:
DetachedCriteria subquery = DetachedCriteria.forClass(AETable.class, "b")
.add(Property.forName("b.classpk").eqProperty("a.classpk"))
.add(Property.forName("b.userid").eqProperty("a.userid"))
.add(Property.forName("b.modifiedDate").gtProperty("a.modifiedDate"));
Criteria criteria = session.createCriteria(AETable.class, "a")
.add(Property.forName("userid").eq(new Integer(10146)))
.add(Subqueries.notExists(subquery);
Just one addition to the above query. If the entryid is not the primary key, then you'll need to add projection.
DetachedCriteria subquery = DetachedCriteria.forClass(AETable.class, "b")
.add(Property.forName("b.classpk").eqProperty("a.classpk"))
.add(Property.forName("b.userid").eqProperty("a.userid"))
.add(Property.forName("b.modifiedDate").gtProperty("a.modifiedDate"))
.add(setProjection(Projections.property("entryId")); // Additional projection property
Criteria criteria = session.createCriteria(AETable.class, "a")
.add(Property.forName("userid").eq(new Integer(10146)))
.add(Subqueries.notExists(subquery);

Categories