DClick

Utilizando funções aninhadas no Hibernate


Quem utiliza Criteria já deve ter precisado utilizar funções aninhadas ( como sum(abs(propriedade)) ). Infelizmente a class Projections não dispoem deste recurso, e a classe que implementa as agregações ( AggregateProjection ) não foi projetada pensando nisso.

Baseado na class AggregateProjection implementei uma solução com um construtor que recebe um array de string com as funções a serem aninhadas na ordem do array

JAVA:
  1. package br.com.dclick.hibernate.criterion;
  2.  
  3. import org.hibernate.Criteria;
  4. import org.hibernate.HibernateException;
  5. import org.hibernate.criterion.CriteriaQuery;
  6. import org.hibernate.criterion.SimpleProjection;
  7. import org.hibernate.type.Type;
  8.  
  9. public class AggregateFunctionsProjection extends SimpleProjection {
  10.  
  11.     protected final String propertyName;
  12.     private final String aggregate[];
  13.    
  14.     public AggregateFunctionsProjection(String[] aggregate, String propertyName) {
  15.         this.aggregate = aggregate;
  16.         this.propertyName = propertyName;
  17.     }
  18.  
  19.     public String toString() {
  20.         return this.mountSql(this.propertyName).toString();
  21.     }
  22.  
  23.     public Type[] getTypes(Criteria criteria, CriteriaQuery criteriaQuery) throws HibernateException {
  24.         return new Type[] { criteriaQuery.getType(criteria, propertyName) };
  25.     }
  26.  
  27.     public String toSqlString(Criteria criteria, int loc, CriteriaQuery criteriaQuery) throws HibernateException {
  28.         return this.mountSql( criteriaQuery.getColumn(criteria, propertyName) )
  29.         .append(" as y")
  30.         .append(loc)
  31.         .append('_')
  32.         .toString();
  33.     }   
  34.  
  35.     private StringBuffer mountSql(String property) {
  36.        
  37.         StringBuffer start = new StringBuffer();
  38.         StringBuffer end = new StringBuffer();
  39.        
  40.         for (int i = 0; i <this.aggregate.length; i++) {
  41.             start.append( this.aggregate[i] + "(" );
  42.             end.append( ")" );
  43.         }
  44.        
  45.         return start.append(property).append(end);
  46.        
  47.     }
  48.    
  49. }

Pronto. Agora e so adicionar ao seu criterio:

JAVA:
  1. String[] funcoes = {"sum", "abs"};
  2.        
  3. HibernateSessionFactory.getSession()
  4. .createCriteria(Produto.class)
  5. .setProjection( new AggregateFunctionsProjection(funcoes, "nomeDaPropriedadeDaSuaClasse") )
  6. .list();

Por Daniel Passos em 4/December/2007 | Comentar | Trackback


No Translations

Um comentário para “Utilizando funções aninhadas no Hibernate”


Muito bom!. Já estou utilizando…

Adicionar comentário

(requerido)
(requerido, não será publicado)