RE: Consult with Dynamic Query (Projection)

Danny A Granados, modified 6 Years ago. New Member Posts: 3 Join Date: 4/12/19 Recent Posts
Hi, i need to execute the following script whit DinamicQuery, Someone can hel me...

SELECT person, count(person) as totalQuantity, SUM(Amount) as totalAmountByPerson FROM contribution 
GROUP BY person
ORDER BY totalAmountByPerson desc;

Up to now I have managed to group the data, I have not achieved the Sum of the Amount column according to the Grouping Obtained ...
Can anybody help me.


        DynamicQuery query = ContributionLocalServiceUtil.dynamicQuery();
        query.add(RestrictionsFactoryUtil.eq("companyId",companyId));
        query.setProjection(ProjectionFactoryUtil.groupProperty("constituentId"));
        query.addOrder(OrderFactoryUtil.desc("totalByDonor"));
Danny A Granados, modified 6 Years ago. New Member Posts: 3 Join Date: 4/12/19 Recent Posts
  DynamicQuery query = ContributionLocalServiceUtil.dynamicQuery();
        query.setProjection(ProjectionFactoryUtil.groupProperty("person"));
        query.addOrder(OrderFactoryUtil.desc("totalByDonor"));
thumbnail
Jorge Díaz, modified 6 Years ago. Liferay Master Posts: 753 Join Date: 1/9/14 Recent Posts
Hi Danny,

Using dynamic queries, in order to do count or other advanced queries, you can use:
  • count(*) => ProjectionFactoryUtil.rowCount()
  • sum or other other aggregations => ProjectionFactoryUtil.sqlProjection("sum(column) as sumColumn") , new String[] {"sumColumn"}, new Type[] {Type.BIG_DECIMAL});

In your example, perhaps you could do this. IMPORTANT!! I didn't compile or test this code!!
Projection groupProjection = ProjectionFactoryUtil.groupProperty("constituentId")
Projection sizeProjection = ProjectionFactoryUtil.sqlProjection("sum(Amount) as sumAmount") , new String[] {"sumAmount"}, new Type[] {Type.BIG_DECIMAL});

Projection projection = ProjectionFactoryUtil.projectionList().add(groupProjection).add(sizeProjection).add(ProjectionFactoryUtil.rowCount());

DynamicQuery query = ContributionLocalServiceUtil.dynamicQuery();
query.add(RestrictionsFactoryUtil.eq("companyId",companyId));
query.setProjection(projection);
query.addOrder(OrderFactoryUtil.desc("totalByDonor"));


I have never used both count and sum with "group by" in a dynamic query so perhaps you can have problems.

Hope it helps
Amos Fong, modified 6 Years ago. New Member Posts: 3 Join Date: 4/12/19 Recent Posts
Hello Jorge

Thank you very much for your help ... but I have the following problem

When executing the Query with the projection I am returning the following:   

[Ljava.lang.Object;@511cee17
[Ljava.lang.Object;@68d902a4
[Ljava.lang.Object;@e2c1dfe
[Ljava.lang.Object;@d9b9e4c​​​​​​​


The truth is I'm just starting to handle the queries with DynamicQuery and I'm a bit concerned about this type of errors.
thumbnail
Andrew Jardine, modified 6 Years ago. Liferay Legend Posts: 2416 Join Date: 12/22/10 Recent Posts
Hey Danny, 

If you use a debugger on those lines I think what you will find is that the actual type is a BigInteger -- so you should be able to cast the results accordingly.
thumbnail
Jorge Díaz, modified 6 Years ago. Liferay Master Posts: 753 Join Date: 1/9/14 Recent Posts
I am sorry, I copy-paste an example that was using BigDecimal.

You can cast that Object to BigDecimal as Andrew said in his message.

You can also change Type.BIG_DECIMAL with other type, for example Type.LONG for more information see types here: https://github.com/liferay/liferay-portal/blob/7.1.x/portal-kernel/src/com/liferay/portal/kernel/dao/orm/Type.java
thumbnail
Andrew Jardine, modified 6 Years ago. Liferay Legend Posts: 2416 Join Date: 12/22/10 Recent Posts
Hah! I didn't know that Jorge! Thanks for sharing that information about the types emoticon