2009-09-11 14 views
6

consideran mesaentidad plano con ayuda de consulta en Hibernate

sales (id, seller_id, amount, date) 

y aquí es una vista que se genera a partir de sales mediante consulta SELECT seller_id, SUM(amount) FROM sales GROUP BY seller_id

total_sales (seller_id, amount) 

Quiero hacer una entidad para las ventas totales, pero sin la ver en el lado sql.

Esta entidad se construirá a partir de una consulta. Lo más parecido que encontré es this, pero no pude hacerlo funcionar.

Incluso si defino el cargador, hibernate busca la tabla de la entidad y da un error si no puede encontrarla. Si creo la tabla, no carga la entidad desde la consulta especificada que definí, Hibernate genera la consulta en sí misma.

¿Hay alguna manera de hacer que @Loader funcione o existe otra forma de asignar una consulta a la entidad?

+1

NO podrá hacer que el trabajo 'session.createCriteria (TotalSales.class)' funcione a través del cargador personalizado. No puede (ni debería) mapearlo como entidad sin tener un objeto de respaldo (tabla o vista) en la base de datos. – ChssPly76

Respuesta

18

¿Por qué no solo usa new en la consulta?

select new TotalSales(seller_id, count(seller_id)) 
from sales 
group by seller_id 

Usted acaba de escribir una clase TotalSales con un constructor tomando el vend_id y un entero.


Editar: Al utilizar criterios API, puede utilizar el AliasToBeanResultTransformer (Ver API docs). Copia cada nombre de alias a una propiedad del mismo nombre.

List list = s.createCriteria(Sales.class) 
    .setProjection(Projections.projectionList() 
    .add(Projections.property("id"), "SellerId") 
    .add(Projections.rowCount("id"), "Count")) 
    .setResultTransformer( 
    new AliasToBeanResultTransformer(TotalSales.class)) 
    .list(); 

Luego, su TotalSales necesita una propiedad SellerId y Count.

+0

+1 por buena primera respuesta. – KLE

+0

Porque quiero usar la nueva entidad como 'session.createCriteria (TotalSale.class) .list()' – nimcap

+0

Agregar agregué una sección a mi respuesta para los criterios. –

0

Además de la respuesta de Stefan, también se puede utilizar una consulta HQL explícita a

SELECT seller_id, SUM(amount) FROM sales GROUP BY seller_id 

El resultado se almacena de forma natural en la lista. Si este tipo de datos no es conveniente para usted, usted podría:

  • crear nuevos objetos VentaTotal con ellos (utilizar la respuesta de Stefan sería mejor probablemente)
  • crear un mapa para almacenar los datos (también se puede incrustar este directamente en la solicitud).
0

Puede intentar definir un cargador personalizado. Nunca lo usé, pero parece ser razonable:

<sql-query name="totalSale"> 
    <return alias="ts" class="TotalSale" /> 
    SELECT seller_id as {ts.seller_id}, SUM(amount) as ts.amount 
    FROM sales 
    WHERE seller_id = ? 
    GROUP BY seller_id 
</sql-query> 

No estoy seguro de si es necesario el filtro en el_veedor_id.

hace referencia a esta consulta con nombre en una asignación de clase:

<class name="TotalSale"> 
    <id name="seller_id"> 
     <generator class="increment"/> 
    </id> 
    <property name="seller_id" /> 
    <property name="amount" /> 
    <loader query-ref="totalSale"/> 
</class> 

Hay more details in the manual.

Como alternativa, puede usar directamente una consulta de nombre desde el código, de esta manera no necesita una asignación de TotalSale y no tiene que escribir la consulta en el código. Las consultas con nombre también pueden devolver objetos. Consulte details about named queries en la documentación.

+0

Esto no va a ayudar con 'session.createCriteria()' de ninguna manera. – ChssPly76

+0

Realmente dudo que crearCriteria sea muy necesario en este caso, entonces propongo enfoques alternativos. –

+0

Sí, y elevé tu otra respuesta. – ChssPly76

0

si realmente quieres una entidad específica sólo para este trabajo se puede utilizar una 'fórmula' en una propiedad personalizada

<class name="SellerSales" table="Sales" lazy="true"> 
    <id name="SellerId" column="SellerId" type="int"> 
     <generator class="native" /> 
    </id> 
    <property name="SalesSum" type="float" update="false" insert="false" 
      formula="select SUM(sal.ammount) from sales sal where sal.seller_id = SellerId)" /> 
</class> 

public class SellerSales 
{ 
    public int SellerId {get; set;} 
    public float SalesSum {get; set;} 
} 

como tal, su accesible al motor Criterios para la order-by, restricciones, etc, que i piensa que es la razón por la que quieres usarlo.

+0

Esto no funcionará a menos que exista la tabla "Vendedor" Y no esté mapeada a ninguna otra entidad. Y si ese fuera el caso, el punto es discutible. – ChssPly76

+0

en realidad tengo un montón de errores en la publicación, la única razón por la que publiqué es que quizás el iniciador de temas tenga una idea o proporcione información sobre lo que realmente necesita. De lo contrario, la respuesta de Stefan parece adecuada – Jaguar

Cuestiones relacionadas