我正在构建一个半复杂的报表查询(可能不是最好的方法,但在此问题之前它可以正常工作)。
// total appointments
var appts = DetachedCriteria.For<Appointment>("appt")
.CreateAlias("Lead", "lead")
.CreateAlias("lead.Promoter", "leadPromoter", JoinType.LeftOuterJoin)
.Add(Restrictions.EqProperty("leadPromoter.Id", "promoter.Id"))
.SetProjection(Projections.ProjectionList()
.Add(Projections.CountDistinct("appt.Id"));
// total sales
var sales = DetachedCriteria.For<Appointment>("sales")
.CreateAlias("Lead", "lead")
.CreateAlias("Sale", "sale")
.CreateAlias("lead.Promoter", "leadPromoter", JoinType.LeftOuterJoin)
.Add(Restrictions.EqProperty("leadPromoter.Id", "promoter.Id"))
.SetProjection(Projections.ProjectionList()
.Add(Projections.CountDistinct("sales.Id"));
var projections = Projections.ProjectionList()
.Add(Projections.SubQuery(appts), "Appointments")
.Add(Projections.SubQuery(sales), "Sales");
var reports = Session.CreateCriteria<Promoter>("promoter")
.SetProjection(projections)
.SetResultTransformer(Transformers.AliasToBean(typeof(PromoterReportDto)))
.List<PromoterReportDto>();
这样可以正常工作并返回正确的结果,但是现在我需要在每个投影的工作日对每个投影(num约会,num销售等)引入一个where子句。
为此,我将此添加到我的预测中:
// total appointments
var appts = DetachedCriteria.For<Appointment>("appt")
.CreateAlias("Lead", "lead")
.CreateAlias("lead.Promoter", "leadPromoter", JoinType.LeftOuterJoin)
.Add(Restrictions.EqProperty("leadPromoter.Id", "promoter.Id"))
.Add(Restrictions.Eq(
Projections.SqlFunction("day", NHibernateUtil.DateTime, Projections.Property("appt.AppointmentDate")), selectedDayOfWeek)
)
.SetProjection(Projections.ProjectionList()
.Add(Projections.CountDistinct("appt.Id"));
// total sales
var sales = DetachedCriteria.For<Appointment>("sales")
.CreateAlias("Lead", "lead")
.CreateAlias("Sale", "sale")
.CreateAlias("lead.Promoter", "leadPromoter", JoinType.LeftOuterJoin)
.Add(Restrictions.EqProperty("leadPromoter.Id", "promoter.Id"))
.Add(Restrictions.Eq(
Projections.SqlFunction("day", NHibernateUtil.DateTime, Projections.Property("sales.AppointmentDate")), selectedDayOfWeek)
)
.SetProjection(Projections.ProjectionList()
.Add(Projections.CountDistinct("sales.Id"));
然而,它抱怨这个错误:
NHibernate.QueryException:找不到属性sales.AppointmentDate
该属性肯定存在,如果我删除了Projections.Property(Projections.Property(“AppointmentDate”))中的别名,它可以工作,但是它产生了这个SQL:
and datepart(day, this_0_.AppointmentDate) = 0 /* @p4 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p5 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p6 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p7 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p8 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p9 */
and datepart(day, this_0_.AppointmentDate) = 0 /* @p10 */) as y0_,
正如您所看到的那样,它使用的是我的实体的第一个实例,而不是每个特定分离标准的实体。
很抱歉这个问题很长,我不太清楚如何在没有所有代码的情况下解释这个问题。
如果需要,我可以粘贴更多代码/ SQL。
保
答案 0 :(得分:1)
我认为问题可能是您将子查询别名为“Sales”,但您已经在分离的条件中定义了别名“sales”。 Sql肯定不区分大小写(我不认为NHibernate别名是?)
无论如何,我会尝试更改投影列表中的别名,例如
var projections = Projections.ProjectionList()
.Add(Projections.SubQuery(appts), "Appointments")
.Add(Projections.SubQuery(sales), "MySales");
这样您就没有两个可能存在冲突的别名。