2011-04-08 14 views
7

Tengo esta situación:Crear SqlProjection con el alias de la tabla unida

public class AnswerSet { 
public virtual IList<Answer> Answers {set; get;} 
} 

session.CreateCriteria<AnswerSet>() 
     .CreateAlias("Answers", "a") 
     .SetProjection(Projections.ProjectionList() 
      .Add(Projections.GroupProperty("TopicId"), "TopicId") 
      .Add(Projections.GroupProperty("TopicName"), "TopicName") 
      .Add(Projections.SqlProjection("count (case **{a}**.numerical_answer 
when 1 then 1 when -1 then 1 else null end) as YesAnswers", 
     new[] { "YesAnswers" }, new IType[] { NHibernateUtil.Int32 }), "YesAnswers") 

¿Cómo puedo especificar el alias de recogida de niños? {a} .numerical_answer no funciona y {alias} se refiere al AnswerSet.

El SQL es equivalente

select 
     [as].topic_id as TopicId 
     , [as].topic_name as TopicName 
     , count (case [a].numerical_answer 
       when 1 then 1 
       when -1 then 1 
       else null 
       end) as YesAnswers 
from answer_set [as] join answer [a] on [a].answer_set_id = [as].id 

Gracias,
Daniel

Respuesta

4

Si numerical_answer no aparece en ninguna otra parte de la consulta, sólo podría omitir el nombre de tabla, por ejemplo,

"count (case numerical_answer when 1 then 1 when -1 then 1 else null end) as YesAnswers" 
+1

Hacerlo es un desastre que está por ocurrir. Esto podría funcionar hoy, pero cuando más tarde se agregue una nueva columna a la base de datos, puede romper esta consulta sin que nadie lo note. Mire aquí: http://sqlblog.com/blogs/alexander_kuznetsov/archive/2008/10/25/defensive-database-programming-qualifying-column-names.aspx – Alejandro

+0

Una preocupación válida. A partir de hoy, probablemente resolvería esto utilizando QueryOver y calculando el resultado deseado en código en lugar de tener tantas cadenas mágicas en primer lugar. –

0

Sé que es tarde, pero creo que sirve a nadie. Lo descubrí en el código donde NHiberate cambia el nombre de los alias para las tablas combinadas al generar el SQL.

Cada alias de proyección se modifica con un índice del alias y un _.

Así, en su caso, puede utilizar

a1_.numerical_answer 

Si ha añadido más alias, puede utilizarlos en las proyecciones de SQL como esto:

b2_.some_property, c3_.another_property, etc. 

cuenta de que las cuestiones de orden en el cual se crean alias En mi caso, tenía una tabla con muchas combinaciones en orden y ocurrencia definida por el usuario, así que tuve que recurrir a esto y funciona muy bien.

Cuestiones relacionadas