public override void HandleResultOperator( GroupResultOperator resultOperator, SqlStatementBuilder sqlStatementBuilder, UniqueIdentifierGenerator generator, ISqlPreparationStage stage, ISqlPreparationContext context) { ArgumentUtility.CheckNotNull("resultOperator", resultOperator); ArgumentUtility.CheckNotNull("sqlStatementBuilder", sqlStatementBuilder); ArgumentUtility.CheckNotNull("generator", generator); ArgumentUtility.CheckNotNull("stage", stage); ArgumentUtility.CheckNotNull("context", context); EnsureNoTopExpression(sqlStatementBuilder, generator, stage, context); EnsureNoGroupExpression(sqlStatementBuilder, generator, stage, context); EnsureNoDistinctQuery(sqlStatementBuilder, generator, stage, context); UpdateDataInfo(resultOperator, sqlStatementBuilder, sqlStatementBuilder.DataInfo); var preparedKeySelector = stage.PrepareResultOperatorItemExpression(resultOperator.KeySelector, context); preparedKeySelector = HandlePotentialConstantExpression(preparedKeySelector); preparedKeySelector = HandlePotentialSubStatementExpression(preparedKeySelector, sqlStatementBuilder, generator); var preparedElementSelector = stage.PrepareResultOperatorItemExpression(resultOperator.ElementSelector, context); sqlStatementBuilder.GroupByExpression = preparedKeySelector; sqlStatementBuilder.SelectProjection = SqlGroupingSelectExpression.CreateWithNames(preparedKeySelector, preparedElementSelector); }
public void HandleResultOperator() { var keySelector = new SqlColumnDefinitionExpression(typeof(string), "c", "Name", false); var elementSelector = Expression.Constant("elementSelector"); var resultOperator = new GroupResultOperator("itemName", keySelector, elementSelector); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(keySelector, _context)) .Return(keySelector); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(elementSelector, _context)) .Return(elementSelector); _stageMock.Replay(); _handler.HandleResultOperator(resultOperator, _sqlStatementBuilder, _generator, _stageMock, _context); _stageMock.VerifyAllExpectations(); Assert.That(_sqlStatementBuilder.GroupByExpression, Is.SameAs(keySelector)); var expectedSelectProjection = new SqlGroupingSelectExpression( new NamedExpression("key", keySelector), new NamedExpression("element", elementSelector)); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedSelectProjection, _sqlStatementBuilder.SelectProjection); Assert.That( _sqlStatementBuilder.DataInfo.DataType, Is.EqualTo(typeof(IQueryable <>).MakeGenericType(typeof(IGrouping <,>).MakeGenericType(typeof(string), typeof(string))))); }
public void AddGroupReferenceMapping(SqlGroupingSelectExpression groupingSelectExpression, SqlTableBase sqlTable) { ArgumentUtility.CheckNotNull("groupingSelectExpression", groupingSelectExpression); ArgumentUtility.CheckNotNull("sqlTable", sqlTable); _groupReferenceMapping[groupingSelectExpression] = sqlTable; }
public void SetUp() { _context = new MappingResolutionContext(); _entityExpression = SqlStatementModelObjectMother.CreateSqlEntityDefinitionExpression(typeof(Cook), null, "c"); _groupingSelectExpression = new SqlGroupingSelectExpression(Expression.Constant("key"), Expression.Constant("element")); _sqlTable = new SqlTable(new ResolvedSimpleTableInfo(typeof(Cook), "CookTable", "c"), JoinSemantics.Inner); }
public void VisitSqlGroupingSelectExpression_WithoutAggregationExpressions() { var groupingExpression = new SqlGroupingSelectExpression(Expression.Constant("keyExpression"), Expression.Constant("elementExpression")); SqlGeneratingSelectExpressionVisitor.GenerateSql(groupingExpression, _commandBuilder, _stageMock); Assert.That(_commandBuilder.GetCommandText(), Is.EqualTo("@1")); Assert.That(_commandBuilder.GetCommandParameters()[0].Value, Is.EqualTo("keyExpression")); }
public virtual Expression VisitSqlGroupingSelect(SqlGroupingSelectExpression expression) { ArgumentUtility.CheckNotNull("expression", expression); var groupExpressions = new[] { expression.KeyExpression }.Concat(expression.AggregationExpressions); CommandBuilder.AppendSeparated(", ", groupExpressions, (cb, exp) => Visit(exp)); return(expression); }
public Expression VisitSqlGroupingSelect(SqlGroupingSelectExpression expression) { ArgumentUtility.CheckNotNull("expression", expression); // Scenario: grouping.Key Assertion.DebugAssert(_memberInfo.Equals(expression.Type.GetProperty("Key"))); // No problem, just use the KeyExpression (without a name, we don't care about the original name of the expression when we resolve members). return(_context.RemoveNamesAndUpdateMapping(expression.KeyExpression)); }
public void ResolveMemberAccess_OnGroupingSelectExpression_StripsNames() { var expression = new SqlGroupingSelectExpression( new NamedExpression("k", Expression.Constant("key")), new NamedExpression("e", Expression.Constant("element"))); var memberInfo = typeof(IGrouping <string, string>).GetProperty("Key"); var result = MemberAccessResolver.ResolveMemberAccess(expression, memberInfo, _resolverMock, _stageMock, _mappingResolutionContext); Assert.That(result, Is.SameAs(((NamedExpression)expression.KeyExpression).Expression)); }
public void CreateWithNames() { var result = SqlGroupingSelectExpression.CreateWithNames(_keyExpression, _elementExpression); var expectedKeyExpression = new NamedExpression("key", _keyExpression); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedKeyExpression, result.KeyExpression); var expectedElementExpression = new NamedExpression("element", _elementExpression); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedElementExpression, result.ElementExpression); }
public ResolvedJoinedGroupingTableInfo( string tableAlias, SqlStatement sqlStatement, SqlGroupingSelectExpression associatedGroupingSelectExpression, string groupSourceTableAlias) : base(tableAlias, sqlStatement) { ArgumentUtility.CheckNotNull("associatedGroupingSelectExpression", associatedGroupingSelectExpression); ArgumentUtility.CheckNotNull("groupSourceTableAlias", groupSourceTableAlias); _associatedGroupingSelectExpression = associatedGroupingSelectExpression; _groupSourceTableAlias = groupSourceTableAlias; }
public void SetUp() { _keyExpression = Expression.Constant("key"); _elementExpression = Expression.Constant("element"); _aggregateExpression1 = Expression.Constant("agg1"); _aggregateExpression2 = Expression.Constant("agg2"); _sqlGroupingSelectExpression = new SqlGroupingSelectExpression( _keyExpression, _elementExpression, new [] { _aggregateExpression1 }); }
public ResolvedJoinedGroupingTableInfo ( string tableAlias, SqlStatement sqlStatement, SqlGroupingSelectExpression associatedGroupingSelectExpression, string groupSourceTableAlias) : base (tableAlias, sqlStatement) { ArgumentUtility.CheckNotNull ("associatedGroupingSelectExpression", associatedGroupingSelectExpression); ArgumentUtility.CheckNotNull ("groupSourceTableAlias", groupSourceTableAlias); _associatedGroupingSelectExpression = associatedGroupingSelectExpression; _groupSourceTableAlias = groupSourceTableAlias; }
public SqlTableBase GetReferencedGroupSource(SqlGroupingSelectExpression groupingSelectExpression) { ArgumentUtility.CheckNotNull("groupingSelectExpression", groupingSelectExpression); SqlTableBase result; if (_groupReferenceMapping.TryGetValue(groupingSelectExpression, out result)) { return(result); } var message = string.Format("No associated table found for grouping select expression '{0}'.", groupingSelectExpression); throw new InvalidOperationException(message); }
public void VisitSqlGroupingSelectExpression_WithAggregationExpressions_AndNames() { var groupingExpression = SqlGroupingSelectExpression.CreateWithNames(Expression.Constant("keyExpression"), Expression.Constant("elementExpression")); groupingExpression.AddAggregationExpressionWithName(Expression.Constant("aggregation1")); groupingExpression.AddAggregationExpressionWithName(Expression.Constant("aggregation2")); SqlGeneratingSelectExpressionVisitor.GenerateSql(groupingExpression, _commandBuilder, _stageMock); Assert.That(_commandBuilder.GetCommandText(), Is.EqualTo("@1 AS [key], @2 AS [a0], @3 AS [a1]")); Assert.That(_commandBuilder.GetCommandParameters()[0].Value, Is.EqualTo("keyExpression")); Assert.That(_commandBuilder.GetCommandParameters()[1].Value, Is.EqualTo("aggregation1")); Assert.That(_commandBuilder.GetCommandParameters()[2].Value, Is.EqualTo("aggregation2")); }
public SqlGroupingSelectExpression UpdateGroupingSelectAndAddMapping( SqlGroupingSelectExpression expression, Expression newKey, Expression newElement, IEnumerable <Expression> aggregations) { ArgumentUtility.CheckNotNull("expression", expression); ArgumentUtility.CheckNotNull("newKey", newKey); ArgumentUtility.CheckNotNull("newElement", newElement); ArgumentUtility.CheckNotNull("aggregations", aggregations); var newSqlGroupingSelectExpression = expression.Update(newKey, newElement, aggregations); SqlTableBase tableForGroupingSelectExpression; if (_groupReferenceMapping.TryGetValue(expression, out tableForGroupingSelectExpression)) { AddGroupReferenceMapping(newSqlGroupingSelectExpression, tableForGroupingSelectExpression); } return(newSqlGroupingSelectExpression); }
public void ResolveSubStatementReferenceExpression_CreatesSqlGroupingSelectExpressionWithNamedExpressions() { var expression = new SqlGroupingSelectExpression( Expression.Constant("key"), Expression.Constant("element"), new[] { Expression.Constant("aggregation") }); var tableInfo = new ResolvedSubStatementTableInfo("q0", SqlStatementModelObjectMother.CreateSqlStatement_Resolved(typeof(Cook))); var sqlTable = SqlStatementModelObjectMother.CreateSqlTable(typeof(Cook)); var exprectedResult = new SqlGroupingSelectExpression( new NamedExpression("key", Expression.Constant("key")), new NamedExpression("element", Expression.Constant("element")), new[] { new NamedExpression("a0", Expression.Constant("aggregation")) }); var result = SubStatementReferenceResolver.ResolveSubStatementReferenceExpression(expression, tableInfo, sqlTable, _context); SqlExpressionTreeComparer.CheckAreEqualTrees(result, exprectedResult); Assert.That(_context.GetReferencedGroupSource(((SqlGroupingSelectExpression)result)), Is.SameAs(sqlTable)); }
public Expression VisitSqlGroupingSelect(SqlGroupingSelectExpression expression) { var newKeyExpression = ApplyValueContext(expression.KeyExpression); var newElementExpression = ApplyValueContext(expression.ElementExpression); var newAggregationExpressions = expression.AggregationExpressions .Select(ApplyValueContext) .ToArray(); if (newKeyExpression != expression.KeyExpression || newElementExpression != expression.ElementExpression || !newAggregationExpressions.SequenceEqual(expression.AggregationExpressions)) { return(_context.UpdateGroupingSelectAndAddMapping(expression, newKeyExpression, newElementExpression, newAggregationExpressions)); } return(expression); }
public override Expression VisitSqlGroupingSelect(SqlGroupingSelectExpression expression) { throw new NotSupportedException( "This SQL generator does not support queries returning groupings that result from a GroupBy operator because SQL is not suited to " + "efficiently return " + "LINQ groupings. Use 'group into' and either return the items of the groupings by feeding them into an additional from clause, or perform " + "an aggregation on the groupings. " + Environment.NewLine + Environment.NewLine + "Eg., instead of: " + Environment.NewLine + "'from c in Cooks group c.ID by c.Name', " + Environment.NewLine + "write: " + Environment.NewLine + "'from c in Cooks group c.ID by c.Name into groupedCooks " + Environment.NewLine + " from c in groupedCooks select new { Key = groupedCooks.Key, Item = c }', " + Environment.NewLine + "or: " + Environment.NewLine + "'from c in Cooks group c.ID by c.Name into groupedCooks " + Environment.NewLine + " select new { Key = groupedCooks.Key, Count = groupedCooks.Count() }'."); }
public void HandleResultOperator_DetectConstantKeysAndReplaceWithSubStatement() { var keySelector = Expression.Constant("keySelector"); var elementSelector = Expression.Constant("elementSelector"); var resultOperator = new GroupResultOperator("itemName", keySelector, elementSelector); var preparedConstantKeySelector = Expression.Constant("test"); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(keySelector, _context)) .Return(preparedConstantKeySelector); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(elementSelector, _context)) .Return(elementSelector); _stageMock.Replay(); _handler.HandleResultOperator(resultOperator, _sqlStatementBuilder, _generator, _stageMock, _context); _stageMock.VerifyAllExpectations(); Assert.That(_sqlStatementBuilder.SqlTables.Count, Is.EqualTo(2)); Assert.That(_sqlStatementBuilder.SqlTables[1], Is.TypeOf(typeof(SqlTable))); Assert.That(((SqlTable)_sqlStatementBuilder.SqlTables[1]).TableInfo, Is.TypeOf(typeof(ResolvedSubStatementTableInfo))); var groupKeyTableTableInfo = (ResolvedSubStatementTableInfo)((SqlTable)_sqlStatementBuilder.SqlTables[1]).TableInfo; var expectedSelectExpression = new NamedExpression(null, preparedConstantKeySelector); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedSelectExpression, groupKeyTableTableInfo.SqlStatement.SelectProjection); var expectedStatement = new SqlStatementBuilder { DataInfo = new StreamedSequenceInfo(typeof(IEnumerable <string>), groupKeyTableTableInfo.SqlStatement.SelectProjection), SelectProjection = groupKeyTableTableInfo.SqlStatement.SelectProjection } .GetSqlStatement(); Assert.That(groupKeyTableTableInfo.SqlStatement, Is.EqualTo(expectedStatement)); var expectedGroupGyExpression = new SqlTableReferenceExpression(_sqlStatementBuilder.SqlTables[1]); SqlExpressionTreeComparer.CheckAreEqualTrees(_sqlStatementBuilder.GroupByExpression, expectedGroupGyExpression); SqlExpressionTreeComparer.CheckAreEqualTrees( _sqlStatementBuilder.SelectProjection, SqlGroupingSelectExpression.CreateWithNames(expectedGroupGyExpression, elementSelector)); }
public Expression VisitSqlGroupingSelectExpression(SqlGroupingSelectExpression expression) { ArgumentUtility.CheckNotNull("expression", expression); var referenceToKeyExpression = ResolveChildExpression(expression.KeyExpression); var referenceToElementExpression = ResolveChildExpression(expression.ElementExpression); var referenceToAggregationExpressions = expression.AggregationExpressions.Select(expr => ResolveChildExpression(expr)); var newGroupingExpression = SqlGroupingSelectExpression.CreateWithNames(referenceToKeyExpression, referenceToElementExpression); foreach (var aggregationExpression in referenceToAggregationExpressions) { newGroupingExpression.AddAggregationExpressionWithName(aggregationExpression); } _context.AddGroupReferenceMapping(newGroupingExpression, _sqlTable); return(newGroupingExpression); }
public void HandleResultOperator_TransformSubqueriesUsedAsGroupByKeys() { var keySelector = Expression.Constant("keySelector"); var elementSelector = Expression.Constant("elementSelector"); var resultOperator = new GroupResultOperator("itemName", keySelector, elementSelector); var sqlStatement = SqlStatementModelObjectMother.CreateSqlStatement_Single(); var preparedSubStatementKeySelector = new SqlSubStatementExpression(sqlStatement); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(keySelector, _context)) .Return(preparedSubStatementKeySelector); _stageMock .Expect(mock => mock.PrepareResultOperatorItemExpression(elementSelector, _context)) .Return(elementSelector); _stageMock.Replay(); _handler.HandleResultOperator(resultOperator, _sqlStatementBuilder, _generator, _stageMock, _context); _stageMock.VerifyAllExpectations(); Assert.That(_sqlStatementBuilder.SqlTables.Count, Is.EqualTo(2)); Assert.That(_sqlStatementBuilder.SqlTables[1], Is.TypeOf(typeof(SqlTable))); Assert.That(((SqlTable)_sqlStatementBuilder.SqlTables[1]).TableInfo, Is.TypeOf(typeof(ResolvedSubStatementTableInfo))); var groupKeyTableTableInfo = (ResolvedSubStatementTableInfo)((SqlTable)_sqlStatementBuilder.SqlTables[1]).TableInfo; var expectedStatement = new SqlStatementBuilder(sqlStatement) { DataInfo = new StreamedSequenceInfo(typeof(IEnumerable <int>), sqlStatement.SelectProjection) } .GetSqlStatement(); Assert.That(groupKeyTableTableInfo.SqlStatement, Is.EqualTo(expectedStatement)); var expectedGroupGyExpression = new SqlTableReferenceExpression(_sqlStatementBuilder.SqlTables[1]); SqlExpressionTreeComparer.CheckAreEqualTrees(_sqlStatementBuilder.GroupByExpression, expectedGroupGyExpression); SqlExpressionTreeComparer.CheckAreEqualTrees( _sqlStatementBuilder.SelectProjection, SqlGroupingSelectExpression.CreateWithNames(expectedGroupGyExpression, elementSelector)); }
public void SetUp() { _dataInfo = new StreamedScalarValueInfo(typeof(int)); _resolvedElementExpressionReference = new SqlColumnDefinitionExpression(typeof(string), "q0", "element", false); _resolvedSelectProjection = new NamedExpression( null, new AggregationExpression(typeof(int), _resolvedElementExpressionReference, AggregationModifier.Min)); _associatedGroupingSelectExpression = new SqlGroupingSelectExpression( new NamedExpression("key", Expression.Constant("k")), new NamedExpression("element", Expression.Constant("e"))); _resolvedJoinedGroupingSubStatement = SqlStatementModelObjectMother.CreateSqlStatement(_associatedGroupingSelectExpression); _resolvedJoinedGroupingTable = new SqlTable( new ResolvedJoinedGroupingTableInfo( "q1", _resolvedJoinedGroupingSubStatement, _associatedGroupingSelectExpression, "q0"), JoinSemantics.Inner); _simplifiableResolvedSqlStatement = new SqlStatement( _dataInfo, _resolvedSelectProjection, new[] { _resolvedJoinedGroupingTable }, null, null, new Ordering[0], null, false, Expression.Constant(0), Expression.Constant(0)); _simplifiableUnresolvedProjection = new AggregationExpression( typeof(int), new SqlTableReferenceExpression(_resolvedJoinedGroupingTable), AggregationModifier.Count); _stageMock = MockRepository.GenerateStrictMock <IMappingResolutionStage> (); _context = new MappingResolutionContext(); _groupAggregateSimplifier = new GroupAggregateSimplifier(_stageMock, _context); }
public void ProcessNames_SqlGroupingSelectExpression() { var keyExpression = new NamedExpression("key", Expression.Constant("key")); var elementExpression = new NamedExpression("element", Expression.Constant("element")); var aggregationExpression = new NamedExpression("a0", Expression.Constant("aggregation")); var groupingSelectExpression = new SqlGroupingSelectExpression(keyExpression, elementExpression, new[] { aggregationExpression }); var expression = new NamedExpression("outer", groupingSelectExpression); var sqlTable = SqlStatementModelObjectMother.CreateSqlTable(typeof(Cook)); _context.AddGroupReferenceMapping(groupingSelectExpression, sqlTable); var expectedResult = new SqlGroupingSelectExpression( new NamedExpression("outer_key", Expression.Constant("key")), new NamedExpression("outer_element", Expression.Constant("element")), new[] { new NamedExpression("outer_a0", Expression.Constant("aggregation")) }); var result = _namedExpressionCombiner.ProcessNames(expression); SqlExpressionTreeComparer.CheckAreEqualTrees(result, expectedResult); Assert.That(_context.GetReferencedGroupSource(((SqlGroupingSelectExpression)result)), Is.SameAs(sqlTable)); }
public void ResolveSubStatementReferenceExpression_CreatesSqlGroupingReferenceExpression_ForSqlGroupingSelectExpression() { var groupingSelectExpression = new SqlGroupingSelectExpression( SqlStatementModelObjectMother.CreateSqlEntityDefinitionExpression(typeof(Cook), "key"), new NamedExpression("element", Expression.Constant(0)), new[] { new NamedExpression("a0", Expression.Constant(1)) }); var sqlStatement = new SqlStatementBuilder(SqlStatementModelObjectMother.CreateSqlStatement_Resolved(typeof(Cook))) { SelectProjection = groupingSelectExpression, DataInfo = new StreamedSequenceInfo(typeof(IGrouping <int, int>[]), Expression.Constant(null, typeof(IGrouping <int, int>))) }.GetSqlStatement(); var tableInfo = new ResolvedSubStatementTableInfo("q0", sqlStatement); var sqlTable = new SqlTable(tableInfo, JoinSemantics.Inner); var result = SubStatementReferenceResolver.ResolveSubStatementReferenceExpression(groupingSelectExpression, tableInfo, sqlTable, _context); Assert.That(result, Is.TypeOf(typeof(SqlGroupingSelectExpression))); var referencedKeyExpression = ((SqlGroupingSelectExpression)result).KeyExpression; var expectedReferencedKeyExpression = new NamedExpression("key", new SqlEntityReferenceExpression( typeof(Cook), "q0", null, (SqlEntityExpression)groupingSelectExpression.KeyExpression)); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedReferencedKeyExpression, referencedKeyExpression); var referencedElementExpression = ((SqlGroupingSelectExpression)result).ElementExpression; var expectedReferencedElementExpression = new NamedExpression("element", new SqlColumnDefinitionExpression(typeof(int), "q0", "element", false)); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedReferencedElementExpression, referencedElementExpression); Assert.That(((SqlGroupingSelectExpression)result).AggregationExpressions.Count, Is.EqualTo(1)); var referencedAggregationExpression = ((SqlGroupingSelectExpression)result).AggregationExpressions[0]; var expectedReferencedAggregationExpression = new NamedExpression("a0", new SqlColumnDefinitionExpression(typeof(int), "q0", "a0", false)); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedReferencedAggregationExpression, referencedAggregationExpression); Assert.That(_context.GetReferencedGroupSource(((SqlGroupingSelectExpression)result)), Is.SameAs(sqlTable)); }
public void ResolveTableInfo_GroupReferenceTableInfo() { var sqlTable = SqlStatementModelObjectMother.CreateSqlTable(typeof(Cook)); var groupingSelect = new SqlGroupingSelectExpression( Expression.MakeMemberAccess(new SqlTableReferenceExpression(sqlTable), typeof(Cook).GetProperty("Name")), Expression.MakeMemberAccess(new SqlTableReferenceExpression(sqlTable), typeof(Cook).GetProperty("ID"))); var dataInfo = new StreamedSequenceInfo( typeof(IEnumerable <>).MakeGenericType(groupingSelect.Type), Expression.Constant(null, groupingSelect.Type)); var whereCondition = Expression.Constant(false); var groupByExpression = groupingSelect.KeyExpression; var groupingSubStatement = new SqlStatementBuilder { DataInfo = dataInfo, SelectProjection = groupingSelect, SqlTables = { sqlTable }, WhereCondition = whereCondition, GroupByExpression = groupByExpression }.GetSqlStatement(); var groupSource = SqlStatementModelObjectMother.CreateSqlTable(new ResolvedSubStatementTableInfo("q0", groupingSubStatement)); var tableInfo = new UnresolvedGroupReferenceTableInfo(groupSource); var expectedKeyViaElement = Expression.MakeMemberAccess(new SqlTableReferenceExpression(sqlTable), typeof(Cook).GetProperty("Name")); var expectedKeyViaGroupSource = Expression.MakeMemberAccess(new SqlTableReferenceExpression(groupSource), groupSource.ItemType.GetProperty("Key")); var expectedResultWhereCondition = Expression.OrElse( Expression.AndAlso(new SqlIsNullExpression(expectedKeyViaElement), new SqlIsNullExpression(expectedKeyViaGroupSource)), Expression.AndAlso( Expression.AndAlso(new SqlIsNotNullExpression(expectedKeyViaElement), new SqlIsNotNullExpression(expectedKeyViaGroupSource)), Expression.Equal(expectedKeyViaElement, expectedKeyViaGroupSource))); var fakeWhereCondition = Expression.Constant(false); _stageMock .Expect(mock => mock.ResolveWhereExpression(Arg <Expression> .Is.Anything, Arg.Is(_mappingResolutionContext))) .WhenCalled(mi => SqlExpressionTreeComparer.CheckAreEqualTrees(expectedResultWhereCondition, (Expression)mi.Arguments[0])) .Return(fakeWhereCondition); _stageMock.Replay(); var result = ResolvingTableInfoVisitor.ResolveTableInfo(tableInfo, _resolverMock, _generator, _stageMock, _mappingResolutionContext); _stageMock.VerifyAllExpectations(); Assert.That(result, Is.TypeOf(typeof(ResolvedJoinedGroupingTableInfo))); var castResult = ((ResolvedJoinedGroupingTableInfo)result); var resultGroupingSelector = castResult.AssociatedGroupingSelectExpression; Assert.That(resultGroupingSelector, Is.SameAs(groupingSelect)); Assert.That(castResult.GroupSourceTableAlias, Is.EqualTo("q0")); var resultSqlStatement = castResult.SqlStatement; Assert.That(resultSqlStatement.SqlTables, Is.EqualTo(groupingSubStatement.SqlTables)); Assert.That(resultSqlStatement.Orderings, Is.Empty); Assert.That(resultSqlStatement.GroupByExpression, Is.Null); SqlExpressionTreeComparer.CheckAreEqualTrees( Expression.AndAlso(groupingSubStatement.WhereCondition, fakeWhereCondition), resultSqlStatement.WhereCondition); var expectedResultSelectProjection = Expression.MakeMemberAccess(new SqlTableReferenceExpression(resultSqlStatement.SqlTables[0]), typeof(Cook).GetProperty("ID")); SqlExpressionTreeComparer.CheckAreEqualTrees(expectedResultSelectProjection, resultSqlStatement.SelectProjection); Assert.That(resultSqlStatement.DataInfo, Is.TypeOf(typeof(StreamedSequenceInfo))); Assert.That(resultSqlStatement.DataInfo.DataType, Is.SameAs(typeof(IQueryable <int>))); var expectedItemExpression = resultSqlStatement.SelectProjection; SqlExpressionTreeComparer.CheckAreEqualTrees(expectedItemExpression, ((StreamedSequenceInfo)resultSqlStatement.DataInfo).ItemExpression); }