public void SetUp () { _predicate1 = Expression.Constant (true); _predicate2 = Expression.Constant (false, typeof (bool?)); _value1 = Expression.Constant (17); _value2 = Expression.Constant (4); _nullableValue1 = Expression.Constant (47, typeof (int?)); _elseValue = Expression.Constant (42); _caseExpressionWithElse = new SqlCaseExpression ( typeof (int), new[] { new SqlCaseExpression.CaseWhenPair (_predicate1, _value1), new SqlCaseExpression.CaseWhenPair (_predicate2, _value2) }, _elseValue); _caseExpressionWithoutElse = new SqlCaseExpression ( typeof (int?), new[] { new SqlCaseExpression.CaseWhenPair (_predicate1, _nullableValue1), new SqlCaseExpression.CaseWhenPair (_predicate2, _value2) }, null); }
protected override Expression VisitMemberExpression (MemberExpression expression) { ArgumentUtility.CheckNotNull ("expression", expression); var newInnerExpression = VisitExpression (expression.Expression); var innerExpressionAsSqlCaseExpression = newInnerExpression as SqlCaseExpression; if (innerExpressionAsSqlCaseExpression != null) { var originalCases = innerExpressionAsSqlCaseExpression.Cases; var originalElseCase = innerExpressionAsSqlCaseExpression.ElseCase; var newCases = originalCases.Select (c => new SqlCaseExpression.CaseWhenPair (c.When, Expression.MakeMemberAccess (c.Then, expression.Member))); var newElseCase = originalElseCase != null ? Expression.MakeMemberAccess (originalElseCase, expression.Member) : null; // If there is no else case, ensure that the resulting type is nullable var caseExpressionType = newElseCase == null && expression.Type.IsValueType && Nullable.GetUnderlyingType (expression.Type) == null ? typeof (Nullable<>).MakeGenericType (expression.Type) : expression.Type; var newSqlCaseExpression = new SqlCaseExpression (caseExpressionType, newCases, newElseCase); return VisitExpression (newSqlCaseExpression); } if (newInnerExpression.NodeType == ExpressionType.Coalesce) { var innerExpressionAsBinaryExpression = (BinaryExpression) newInnerExpression; var newConditionalExpression = Expression.Condition ( new SqlIsNotNullExpression (innerExpressionAsBinaryExpression.Left), Expression.MakeMemberAccess (innerExpressionAsBinaryExpression.Left, expression.Member), Expression.MakeMemberAccess (innerExpressionAsBinaryExpression.Right, expression.Member)); return VisitExpression (newConditionalExpression); } var innerExpressionAsSqlSubStatementExpression = newInnerExpression as SqlSubStatementExpression; if (innerExpressionAsSqlSubStatementExpression != null) { var sqlStatementBuilder = new SqlStatementBuilder (innerExpressionAsSqlSubStatementExpression.SqlStatement); var namedExpression = (NamedExpression) sqlStatementBuilder.SelectProjection; sqlStatementBuilder.SelectProjection = new NamedExpression ( namedExpression.Name, VisitExpression (Expression.MakeMemberAccess (namedExpression.Expression, expression.Member))); sqlStatementBuilder.RecalculateDataInfo (innerExpressionAsSqlSubStatementExpression.SqlStatement.SelectProjection); return new SqlSubStatementExpression (sqlStatementBuilder.GetSqlStatement()); } var memberAsPropertyInfo = expression.Member as PropertyInfo; if (memberAsPropertyInfo != null) { var methodInfo = memberAsPropertyInfo.GetGetMethod(); if (methodInfo != null) { var methodCallExpression = Expression.Call (expression.Expression, methodInfo); var tranformer = _methodCallTransformerProvider.GetTransformer(methodCallExpression); if (tranformer != null) { var tranformedExpression = tranformer.Transform (methodCallExpression); return VisitExpression (tranformedExpression); } } } return base.VisitMemberExpression (expression); }
public Expression VisitSqlCaseExpression (SqlCaseExpression expression) { ArgumentUtility.CheckNotNull ("expression", expression); var newCases = VisitList ( expression.Cases, caseWhenPair => { var newWhen = ApplyPredicateContext (caseWhenPair.When); var newThen = ApplySingleValueContext (caseWhenPair.Then); return caseWhenPair.Update (newWhen, newThen); }); var newElseCase = expression.ElseCase != null ? ApplySingleValueContext (expression.ElseCase) : null; return expression.Update (newCases, newElseCase); }
public void VisitSqlCaseExpression_WithElse () { var case1 = new SqlCaseExpression.CaseWhenPair (new SqlCustomTextExpression ("test1", typeof (bool)), new SqlCustomTextExpression ("value1", typeof (int))); var case2 = new SqlCaseExpression.CaseWhenPair (new SqlCustomTextExpression ("test2", typeof (bool)), new SqlCustomTextExpression ("value2", typeof (int))); var elseCase = new SqlCustomTextExpression ("elseValue", typeof (int)); var expression = new SqlCaseExpression (typeof (int), new[] { case1, case2 }, elseCase); SqlGeneratingExpressionVisitor.GenerateSql (expression, _commandBuilder, _stageMock); Assert.That (_commandBuilder.GetCommandText (), Is.EqualTo ("CASE WHEN test1 THEN value1 WHEN test2 THEN value2 ELSE elseValue END")); }
public void VisitSqlCaseExpression_NoElse () { var case1 = new SqlCaseExpression.CaseWhenPair (Expression.Constant (true), Expression.Constant (true)); var case2 = new SqlCaseExpression.CaseWhenPair (Expression.Constant (false), Expression.Constant (false)); var expression = new SqlCaseExpression (typeof (bool?), new[] { case1, case2 }, null); var result = _valueRequiredVisitor.VisitSqlCaseExpression (expression); var expectedCase1 = new SqlCaseExpression.CaseWhenPair ( Expression.Equal (Expression.Constant (1), new SqlLiteralExpression (1)), new SqlConvertedBooleanExpression (Expression.Constant (1))); var expectedCase2 = new SqlCaseExpression.CaseWhenPair ( Expression.Equal (Expression.Constant (0), new SqlLiteralExpression (1)), new SqlConvertedBooleanExpression (Expression.Constant (0))); var expectedExpression = new SqlCaseExpression (typeof (bool?), new[] { expectedCase1, expectedCase2 }, null); SqlExpressionTreeComparer.CheckAreEqualTrees (expectedExpression, result); }
public void VisitSqlCaseExpression_RequiresSingleValue_InElse () { var entity = SqlStatementModelObjectMother.CreateSqlEntityDefinitionExpression (typeof (Cook)); var nonEntity = Expression.Constant (null, typeof (Cook)); var case1 = new SqlCaseExpression.CaseWhenPair (Expression.Constant (true), nonEntity); var elseCase = entity; var expression = new SqlCaseExpression (typeof (Cook), new[] { case1 }, elseCase); Assert.That ( () => _valueRequiredVisitor.VisitSqlCaseExpression (expression), Throws.TypeOf<NotSupportedException> ().With.Message.EqualTo ( "Cannot use an entity expression ('[t0]' of type 'Cook') in a place where SQL requires a single value.")); }