Skip to content

Commit

Permalink
Merge pull request #66 from hazzik/NH-3032
Browse files Browse the repository at this point in the history
NH-3032: Linq - Group By with contains inside where clause throws exceptions (regression)
  • Loading branch information
oskarb committed Jan 24, 2012
2 parents e20f9be + b0ca240 commit 6038541
Show file tree
Hide file tree
Showing 2 changed files with 40 additions and 8 deletions.
30 changes: 30 additions & 0 deletions src/NHibernate.Test/Linq/ByMethod/GroupByTests.cs
Expand Up @@ -201,6 +201,36 @@ public void SingleKeyGroupAndOrderByKeyProjection()
AssertOrderedBy.Ascending(result, x => x.UnitPrice);
}

[Test]
public void GroupByWithAndAlsoContainsInWhereClause()
{
//NH-3032
var collection = db.Products.Select(x => x.Supplier).ToList();

var result = db.Products
.Where(x => x.Discontinued == true && collection.Contains(x.Supplier))
.GroupBy(x => x.UnitPrice)
.Select(x => new {x.Key, Count = x.Count()})
.ToList();

Assert.That(result.Count, Is.EqualTo(8));
}

[Test]
public void GroupByWithContainsInWhereClause()
{
//NH-3032
var collection = db.Products.Select(x => x.Supplier).ToList();

var result = db.Products
.Where(x => collection.Contains(x.Supplier))
.GroupBy(x => x.UnitPrice)
.Select(x => new {x.Key, Count = x.Count()})
.ToList();

Assert.That(result.Count, Is.EqualTo(62));
}

private static void CheckGrouping<TKey, TElement>(IEnumerable<IGrouping<TKey, TElement>> groupedItems, Func<TElement, TKey> groupBy)
{
var used = new HashSet<object>();
Expand Down
18 changes: 10 additions & 8 deletions src/NHibernate/Linq/GroupBy/AggregatingGroupByRewriter.cs
Expand Up @@ -54,13 +54,18 @@ private static void FlattenSubQuery(SubQueryExpression subQueryExpression, Query

queryModel.ResultOperators.Add(groupBy);

foreach (var whereClause in queryModel.BodyClauses.OfType<WhereClause>().ToArray())
for (int i = 0; i < queryModel.BodyClauses.Count; i++)
{
//all outer where clauses actually are having clauses
var clause = new NhHavingClause(whereClause.Predicate);
var clause = queryModel.BodyClauses[i];
clause.TransformExpressions(s => GroupBySelectClauseRewriter.ReWrite(s, groupBy, subQueryExpression.QueryModel));

queryModel.BodyClauses.Add(clause);
queryModel.BodyClauses.Remove(whereClause);
//all outer where clauses actually are having clauses
var whereClause = clause as WhereClause;
if (whereClause != null)
{
queryModel.BodyClauses.RemoveAt(i);
queryModel.BodyClauses.Insert(i, new NhHavingClause(whereClause.Predicate));
}
}

foreach (var bodyClause in subQueryExpression.QueryModel.BodyClauses)
Expand All @@ -72,9 +77,6 @@ private static void FlattenSubQuery(SubQueryExpression subQueryExpression, Query
queryModel.SelectClause.TransformExpressions(s =>
GroupBySelectClauseRewriter.ReWrite(s, groupBy, subQueryExpression.QueryModel));

foreach (var clause in queryModel.BodyClauses)
clause.TransformExpressions(s => GroupBySelectClauseRewriter.ReWrite(s, groupBy, subQueryExpression.QueryModel));

// Point all query source references to the outer from clause
queryModel.TransformExpressions(s =>
new SwapQuerySourceVisitor(queryModel.MainFromClause, subQueryExpression.QueryModel.MainFromClause).Swap(s));
Expand Down

0 comments on commit 6038541

Please sign in to comment.