当我们想要查询 “不同记录的条数” 时,我们可能会这样写:
int totalCampaignUser = CampaignParticipation.where {
eq "campaign.id", campaignToJoin.id
}.distinct("user").count()?.intValue() ?: 0
但这样会生成一个错误的 SQL
select distinct this_.user_id as y0_, count(*) as y1_ from campaign_participation this_ where this_.campaign_id=? limit ?
原因是用了聚合函数count(*),但 select 子句中的字段"user_id"没有出现在 group by 中。
报错信息:
2020-04-30 13:28:00.351 DEBUG --- [ Test worker] org.hibernate.SQL : select distinct this_.user_id as y0_, count(*) as y1_ from campaign_participation this_ where this_.campaign_id=? limit ?
2020-04-30 13:28:00.351 TRACE --- [ Test worker] o.h.type.descriptor.sql.BasicBinder : binding parameter [1] as [BIGINT] - [188]
2020-04-30 13:28:00.446 ERROR --- [ Test worker] o.h.engine.jdbc.spi.SqlExceptionHelper : In aggregated query without GROUP BY, expression #1 of SELECT list contains nonaggregated column 'chess_test.this_.user_id'; this is incompatible with sql_mode=only_full_group_by
解决办法:
可以用 countDistinct(),例如这样:
def c = Account.createCriteria()
def numberOfBranches = c.get {
projections {
countDistinct('branch')
}
}
具体项目中,试验成功的代码:
Number totalCampaignUser = CampaignParticipation.where {
eq "campaign.id", campaignToJoin.id
projections {
countDistinct "user"
}
}.get() as Number ?: 0