internal override SqlExpression VisitClientParameter(SqlClientParameter cp) { if (cp.SqlType.CanBeParameter) { SqlParameter p = new SqlParameter(cp.ClrType, cp.SqlType, this.parameterizer.CreateParameterName(), cp.SourceExpression); this.currentParams.Add(new SqlParameterInfo(p, cp.Accessor.Compile())); return(p); } return(cp); }
private void CoerceToFirst(SqlExpression arg1, ref SqlExpression arg2) { if (arg1.SqlType != null && arg2.SqlType != null) { if (arg2.NodeType == SqlNodeType.Value) { SqlValue val = (SqlValue)arg2; arg2 = sql.Value( arg1.ClrType, arg1.SqlType, DBConvert.ChangeType(val.Value, arg1.ClrType), val.IsClientSpecified, arg2.SourceExpression ); } else if (arg2.NodeType == SqlNodeType.ClientParameter && arg2.SqlType != arg1.SqlType) { SqlClientParameter cp = (SqlClientParameter)arg2; cp.SetSqlType(arg1.SqlType); } else { arg2 = sql.UnaryConvert(arg1.ClrType, arg1.SqlType, arg2, arg2.SourceExpression); } } }
internal override SqlExpression VisitClientParameter(SqlClientParameter cp) { if (!this.isDebugMode) { throw Error.InvalidFormatNode("ClientParameter"); } else { sb.Append("client-parameter("); object value; try { value = cp.Accessor.Compile().DynamicInvoke(new object[] { null }); } catch (System.Reflection.TargetInvocationException e) { throw e.InnerException; } sb.Append(value); sb.Append(")"); } return cp; }
internal virtual SqlExpression VisitClientParameter(SqlClientParameter cp) { return cp; }
// inline lambda expressions w/o invocation are parameterized queries private SqlNode VisitLambda(LambdaExpression lambda) { // turn lambda parameters into client parameters for (int i = 0, n = lambda.Parameters.Count; i < n; i++) { ParameterExpression p = lambda.Parameters[i]; if (p.Type == typeof(Type)) { throw Error.BadParameterType(p.Type); } // construct accessor for parameter ParameterExpression pa = Expression.Parameter(typeof(object[]), "args"); LambdaExpression accessor = Expression.Lambda( typeof(Func<,>).MakeGenericType(typeof(object[]), p.Type), Expression.Convert( #pragma warning disable 618 // Disable the 'obsolete' warning Expression.ArrayIndex(pa, Expression.Constant(i)), p.Type ), #pragma warning restore 618 pa ); SqlClientParameter cp = new SqlClientParameter(p.Type, this.typeProvider.From(p.Type), accessor, this.dominatingExpression); // map references to lambda's parameter to client parameter node this.dupMap[p] = cp; } // call this so we don't erase 'outerNode' setting return this.VisitInner(lambda.Body); }
private SqlExpression TranslateVbLikeString(SqlMethodCall mc) { // these should be true per the method signature Debug.Assert(mc.Arguments.Count == 3); Debug.Assert(mc.Arguments[0].ClrType == typeof(string)); Debug.Assert(mc.Arguments[1].ClrType == typeof(string)); bool needsEscape = true; Expression source = mc.SourceExpression; SqlExpression pattern = mc.Arguments[1]; if (pattern.NodeType == SqlNodeType.Value) { string unescapedText = (string)((SqlValue)pattern).Value; string patternText = SqlHelpers.TranslateVBLikePattern(unescapedText, '~'); pattern = sql.ValueFromObject(patternText, typeof(string), true, source); needsEscape = unescapedText != patternText; } else if (pattern.NodeType == SqlNodeType.ClientParameter) { SqlClientParameter cp = (SqlClientParameter)pattern; pattern = new SqlClientParameter( cp.ClrType, cp.SqlType, Expression.Lambda( Expression.Call(typeof(SqlHelpers), "TranslateVBLikePattern", Type.EmptyTypes, cp.Accessor.Body, Expression.Constant('~')), cp.Accessor.Parameters[0] ), cp.SourceExpression ); } else { throw Error.NonConstantExpressionsNotSupportedFor("LIKE"); } SqlExpression escape = needsEscape ? sql.ValueFromObject("~", false, mc.SourceExpression) : null; return sql.Like(mc.Arguments[0], pattern, escape, source); }
private SqlExpression TranslateStringMethod(SqlMethodCall mc) { Expression source = mc.SourceExpression; switch (mc.Method.Name) { case "Contains": if (mc.Arguments.Count == 1) { SqlExpression pattern = mc.Arguments[0]; SqlExpression escape = null; bool needsEscape = true; if (pattern.NodeType == SqlNodeType.Value) { string unescapedText = (string)((SqlValue)pattern).Value; string patternText = SqlHelpers.GetStringContainsPattern(unescapedText, '~', out needsEscape); pattern = sql.ValueFromObject(patternText, true, pattern.SourceExpression); } else if (pattern.NodeType == SqlNodeType.ClientParameter) { SqlClientParameter cp = (SqlClientParameter)pattern; Func<string, char, string> getStringContainsPatternForced = SqlHelpers.GetStringContainsPatternForced; pattern = new SqlClientParameter( cp.ClrType, cp.SqlType, Expression.Lambda( Expression.Invoke(Expression.Constant(getStringContainsPatternForced), cp.Accessor.Body, Expression.Constant('~')), cp.Accessor.Parameters[0] ), cp.SourceExpression ); } else { throw Error.NonConstantExpressionsNotSupportedFor("String.Contains"); } if (needsEscape) { escape = sql.ValueFromObject("~", false, source); } return sql.Like(mc.Object, pattern, escape, source); } break; case "StartsWith": if (mc.Arguments.Count == 1) { SqlExpression pattern = mc.Arguments[0]; SqlExpression escape = null; bool needsEscape = true; if (pattern.NodeType == SqlNodeType.Value) { string unescapedText = (string)((SqlValue)pattern).Value; string patternText = SqlHelpers.GetStringStartsWithPattern(unescapedText, '~', out needsEscape); pattern = sql.ValueFromObject(patternText, true, pattern.SourceExpression); } else if (pattern.NodeType == SqlNodeType.ClientParameter) { SqlClientParameter cp = (SqlClientParameter)pattern; Func<string, char, string> getStringStartsWithPatternForced = SqlHelpers.GetStringStartsWithPatternForced; pattern = new SqlClientParameter( cp.ClrType, cp.SqlType, Expression.Lambda( Expression.Invoke(Expression.Constant(getStringStartsWithPatternForced), cp.Accessor.Body, Expression.Constant('~')), cp.Accessor.Parameters[0] ), cp.SourceExpression ); } else { throw Error.NonConstantExpressionsNotSupportedFor("String.StartsWith"); } if (needsEscape) { escape = sql.ValueFromObject("~", false, source); } return sql.Like(mc.Object, pattern, escape, source); } break; case "EndsWith": if (mc.Arguments.Count == 1) { SqlExpression pattern = mc.Arguments[0]; SqlExpression escape = null; bool needsEscape = true; if (pattern.NodeType == SqlNodeType.Value) { string unescapedText = (string)((SqlValue)pattern).Value; string patternText = SqlHelpers.GetStringEndsWithPattern(unescapedText, '~', out needsEscape); pattern = sql.ValueFromObject(patternText, true, pattern.SourceExpression); } else if (pattern.NodeType == SqlNodeType.ClientParameter) { SqlClientParameter cp = (SqlClientParameter)pattern; Func<string, char, string> getStringEndsWithPatternForced = SqlHelpers.GetStringEndsWithPatternForced; pattern = new SqlClientParameter( cp.ClrType, cp.SqlType, Expression.Lambda( Expression.Invoke(Expression.Constant(getStringEndsWithPatternForced), cp.Accessor.Body, Expression.Constant('~')), cp.Accessor.Parameters[0] ), cp.SourceExpression ); } else { throw Error.NonConstantExpressionsNotSupportedFor("String.EndsWith"); } if (needsEscape) { escape = sql.ValueFromObject("~", false, source); } return sql.Like(mc.Object, pattern, escape, source); } break; case "IndexOf": if (mc.Arguments.Count == 1) { if (mc.Arguments[0] is SqlValue && ((SqlValue)mc.Arguments[0]).Value == null) { throw Error.ArgumentNull("value"); } // if the search string is empty, return zero SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); SqlWhen when = new SqlWhen(lenZeroExpr, sql.ValueFromObject(0, source)); SqlExpression @else = sql.Subtract(sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { mc.Arguments[0], mc.Object }, source), 1); return sql.SearchedCase(new SqlWhen[] { when }, @else, source); } else if (mc.Arguments.Count == 2) { if (mc.Arguments[0] is SqlValue && ((SqlValue)mc.Arguments[0]).Value == null) { throw Error.ArgumentNull("value"); } if (mc.Arguments[1].ClrType == typeof(StringComparison)) { throw Error.IndexOfWithStringComparisonArgNotSupported(); } // if the search string is empty and the start index is in bounds, // return the start index SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); lenZeroExpr = sql.AndAccumulate(lenZeroExpr, sql.Binary(SqlNodeType.LE, sql.Add(mc.Arguments[1], 1), sql.CLRLENGTH(mc.Object))); SqlWhen when = new SqlWhen(lenZeroExpr, mc.Arguments[1]); SqlExpression @else = sql.Subtract(sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { mc.Arguments[0], mc.Object, sql.Add(mc.Arguments[1], 1) }, source), 1); return sql.SearchedCase(new SqlWhen[] { when }, @else, source); } else if (mc.Arguments.Count == 3) { if (mc.Arguments[0] is SqlValue && ((SqlValue)mc.Arguments[0]).Value == null) { throw Error.ArgumentNull("value"); } if (mc.Arguments[2].ClrType == typeof(StringComparison)) { throw Error.IndexOfWithStringComparisonArgNotSupported(); } // s1.IndexOf(s2, start, count) -> CHARINDEX(@s2, SUBSTRING(@s1, 1, @start + @count), @start + 1) // if the search string is empty and the start index is in bounds, // return the start index SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); lenZeroExpr = sql.AndAccumulate(lenZeroExpr, sql.Binary(SqlNodeType.LE, sql.Add(mc.Arguments[1], 1), sql.CLRLENGTH(mc.Object))); SqlWhen when = new SqlWhen(lenZeroExpr, mc.Arguments[1]); SqlExpression substring = sql.FunctionCall( typeof(string), "SUBSTRING", new SqlExpression[] { mc.Object, sql.ValueFromObject(1, false, source), sql.Add(mc.Arguments[1], mc.Arguments[2]) }, source); SqlExpression @else = sql.Subtract(sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { mc.Arguments[0], substring, sql.Add(mc.Arguments[1], 1) }, source), 1); return sql.SearchedCase(new SqlWhen[] { when }, @else, source); } break; case "LastIndexOf": if (mc.Arguments.Count == 1) { // s.LastIndexOf(part) --> // CASE WHEN CHARINDEX(@part, @s) = 0 THEN -1 // ELSE 1 + CLRLENGTH(@s) - CLRLENGTH(@part) - CHARINDEX(REVERSE(@part),REVERSE(@s)) // END SqlExpression exprPart = mc.Arguments[0]; if (exprPart is SqlValue && ((SqlValue)exprPart).Value == null) { throw Error.ArgumentNull("value"); } SqlExpression exprS = mc.Object; SqlExpression reverseS = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { exprS }, source); SqlExpression reversePart = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { exprPart }, source); SqlExpression charIndex = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { exprPart, exprS }, source); SqlExpression charIndexOfReverse = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { reversePart, reverseS }, source); SqlExpression notContained = sql.Binary(SqlNodeType.EQ, charIndex, sql.ValueFromObject(0, false, source)); SqlExpression len1 = sql.CLRLENGTH(exprS); SqlExpression len2 = sql.CLRLENGTH(exprPart); SqlExpression elseCase = sql.Add(sql.ValueFromObject(1, false, source), sql.Subtract(len1, sql.Add(len2, charIndexOfReverse))); SqlWhen whenNotContained = new SqlWhen(notContained, sql.ValueFromObject(-1, false, source)); // if the search string is empty, return zero SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); SqlWhen whenLenZero = new SqlWhen(lenZeroExpr, sql.Subtract(sql.CLRLENGTH(exprS), 1)); return sql.SearchedCase(new SqlWhen[] { whenLenZero, whenNotContained }, elseCase, source); } else if (mc.Arguments.Count == 2) { // s.LastIndexOf(part,i) --> // set @first = LEFT(@s, @i+1) // CASE WHEN CHARINDEX(@part, @first) = 0 THEN -1 // ELSE 1 + CLRLENGTH(@first) - CLRLENGTH(@part) - CHARINDEX(REVERSE(@part),REVERSE(@first)) // END if (mc.Arguments[1].ClrType == typeof(StringComparison)) { throw Error.LastIndexOfWithStringComparisonArgNotSupported(); } SqlExpression s = mc.Object; SqlExpression part = mc.Arguments[0]; if (part is SqlValue && ((SqlValue)part).Value == null) { throw Error.ArgumentNull("value"); } SqlExpression i = mc.Arguments[1]; SqlExpression first = sql.FunctionCall(typeof(string), "LEFT", new SqlExpression[] { s, sql.Add(i, 1) }, source); SqlExpression reverseFirst = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { first }, source); SqlExpression reversePart = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { part }, source); SqlExpression charIndex = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { part, first }, source); SqlExpression charIndexOfReverse = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { reversePart, reverseFirst }, source); SqlExpression notContained = sql.Binary(SqlNodeType.EQ, charIndex, sql.ValueFromObject(0, false, source)); SqlExpression len1 = sql.CLRLENGTH(first); SqlExpression len2 = sql.CLRLENGTH(part); SqlExpression elseCase = sql.Add(sql.ValueFromObject(1, false, source), sql.Subtract(len1, sql.Add(len2, charIndexOfReverse))); SqlWhen whenNotContained = new SqlWhen(notContained, sql.ValueFromObject(-1, false, source)); // if the search string is empty and the start index is in bounds, // return the start index SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); lenZeroExpr = sql.AndAccumulate(lenZeroExpr, sql.Binary(SqlNodeType.LE, sql.Add(mc.Arguments[1], 1), sql.CLRLENGTH(s))); SqlWhen whenLenZero = new SqlWhen(lenZeroExpr, mc.Arguments[1]); return sql.SearchedCase(new SqlWhen[] { whenLenZero, whenNotContained }, elseCase, source); } else if (mc.Arguments.Count == 3) { // s.LastIndexOf(part, i, count) --> // set @first = LEFT(@s, @i+1) // CASE WHEN (CHARINDEX(@part, @first) = 0) OR (1 + CLRLENGTH(@first) - CLRLENGTH(@part) - CHARINDEX(REVERSE(@part),REVERSE(@first))) < (@i - @count) THEN -1 // ELSE 1 + CLRLENGTH(@first) - CLRLENGTH(@part) - CHARINDEX(REVERSE(@part),REVERSE(@first)) // END if (mc.Arguments[2].ClrType == typeof(StringComparison)) { throw Error.LastIndexOfWithStringComparisonArgNotSupported(); } SqlExpression s = mc.Object; SqlExpression part = mc.Arguments[0]; if (part is SqlValue && ((SqlValue)part).Value == null) { throw Error.ArgumentNull("value"); } SqlExpression i = mc.Arguments[1]; SqlExpression count = mc.Arguments[2]; SqlExpression first = sql.FunctionCall(typeof(string), "LEFT", new SqlExpression[] { s, sql.Add(i, 1) }, source); SqlExpression reverseFirst = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { first }, source); SqlExpression reversePart = sql.FunctionCall(typeof(string), "REVERSE", new SqlExpression[] { part }, source); SqlExpression charIndex = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { part, first }, source); SqlExpression charIndexOfReverse = sql.FunctionCall(typeof(int), "CHARINDEX", new SqlExpression[] { reversePart, reverseFirst }, source); SqlExpression len1 = sql.CLRLENGTH(first); SqlExpression len2 = sql.CLRLENGTH(part); SqlExpression elseCase = sql.Add(sql.ValueFromObject(1, false, source), sql.Subtract(len1, sql.Add(len2, charIndexOfReverse))); SqlExpression notContained = sql.Binary(SqlNodeType.EQ, charIndex, sql.ValueFromObject(0, false, source)); notContained = sql.OrAccumulate(notContained, sql.Binary(SqlNodeType.LE, elseCase, sql.Subtract(i, count))); SqlWhen whenNotContained = new SqlWhen(notContained, sql.ValueFromObject(-1, false, source)); // if the search string is empty and the start index is in bounds, // return the start index SqlExpression lenZeroExpr = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Arguments[0]), sql.ValueFromObject(0, source)); lenZeroExpr = sql.AndAccumulate(lenZeroExpr, sql.Binary(SqlNodeType.LE, sql.Add(mc.Arguments[1], 1), sql.CLRLENGTH(s))); SqlWhen whenLenZero = new SqlWhen(lenZeroExpr, mc.Arguments[1]); return sql.SearchedCase(new SqlWhen[] { whenLenZero, whenNotContained }, elseCase, source); } break; case "Insert": // Create STUFF(str, insertPos + 1, 0, strToInsert) if (mc.Arguments.Count == 2) { if (mc.Arguments[1] is SqlValue && ((SqlValue)mc.Arguments[1]).Value == null) { throw Error.ArgumentNull("value"); } SqlFunctionCall stuffCall = sql.FunctionCall( typeof(string), "STUFF", new SqlExpression[] { mc.Object, sql.Add(mc.Arguments[0], 1), sql.ValueFromObject(0, false, source), mc.Arguments[1] }, source); // We construct SQL to handle the special case of when the length of the string // to modify is equal to the insert position. This occurs if the string is empty and // the insert pos is 0, or when the string is not empty, and the insert pos indicates // the end of the string. // CASE WHEN (CLRLENGTH(str) = insertPos) THEN str + strToInsert ELSE STUFF(...) SqlExpression insertingAtEnd = sql.Binary(SqlNodeType.EQ, sql.CLRLENGTH(mc.Object), mc.Arguments[0]); SqlExpression stringConcat = sql.Concat(mc.Object, mc.Arguments[1]); return sql.SearchedCase(new SqlWhen[] { new SqlWhen(insertingAtEnd, stringConcat) }, stuffCall, source); } break; case "PadLeft": if (mc.Arguments.Count == 1) { // s.PadLeft(i) --> // CASE WHEN CLRLENGTH(@s)>= @i THEN @s // ELSE SPACE(@i-CLRLENGTH(@s)) + @s // END SqlExpression exprS = mc.Object; SqlExpression exprI = mc.Arguments[0]; SqlExpression len2 = sql.CLRLENGTH(exprS); SqlExpression dontChange = sql.Binary(SqlNodeType.GE, len2, exprI); SqlExpression numSpaces = sql.Subtract(exprI, len2); SqlExpression padding = sql.FunctionCall(typeof(string), "SPACE", new SqlExpression[] { numSpaces }, source); SqlExpression elseCase = sql.Concat(padding, exprS); return sql.SearchedCase(new SqlWhen[] { new SqlWhen(dontChange, exprS) }, elseCase, source); } else if (mc.Arguments.Count == 2) { // s.PadLeft(i,c) --> // CASE WHEN CLRLENGTH(@s) >= @i THEN @s // ELSE REPLICATE(@c, @i - CLRLENGTH(@s)) + @s // END SqlExpression exprS = mc.Object; SqlExpression exprI = mc.Arguments[0]; SqlExpression exprC = mc.Arguments[1]; SqlExpression dontChange = sql.Binary(SqlNodeType.GE, sql.CLRLENGTH(exprS), exprI); SqlExpression len2 = sql.CLRLENGTH(exprS); SqlExpression numSpaces = sql.Subtract(exprI, len2); SqlExpression padding = sql.FunctionCall(typeof(string), "REPLICATE", new SqlExpression[] { exprC, numSpaces }, source); SqlExpression elseCase = sql.Concat(padding, exprS); return sql.SearchedCase(new SqlWhen[] { new SqlWhen(dontChange, exprS) }, elseCase, source); } break; case "PadRight": if (mc.Arguments.Count == 1) { // s.PadRight(i) --> // CASE WHEN CLRLENGTH(@s) >= @i THEN @s // ELSE @s + SPACE(@i - CLRLENGTH(@s)) // END SqlExpression exprS = mc.Object; SqlExpression exprI = mc.Arguments[0]; SqlExpression dontChange = sql.Binary(SqlNodeType.GE, sql.CLRLENGTH(exprS), exprI); SqlExpression len2 = sql.CLRLENGTH(exprS); SqlExpression numSpaces = sql.Subtract(exprI, len2); SqlExpression padding = sql.FunctionCall(typeof(string), "SPACE", new SqlExpression[] { numSpaces }, source); SqlExpression elseCase = sql.Concat(exprS, padding); return sql.SearchedCase(new SqlWhen[] { new SqlWhen(dontChange, exprS) }, elseCase, source); } else if (mc.Arguments.Count == 2) { // s.PadRight(i,c) --> // CASE WHEN CLRLENGTH(@s) >= @i THEN @s // ELSE @s + REPLICATE(@c, @i - CLRLENGTH(@s)) // END SqlExpression exprS = mc.Object; SqlExpression exprI = mc.Arguments[0]; SqlExpression exprC = mc.Arguments[1]; SqlExpression dontChange = sql.Binary(SqlNodeType.GE, sql.CLRLENGTH(exprS), exprI); SqlExpression len2 = sql.CLRLENGTH(exprS); SqlExpression numSpaces = sql.Subtract(exprI, len2); SqlExpression padding = sql.FunctionCall(typeof(string), "REPLICATE", new SqlExpression[] { exprC, numSpaces }, source); SqlExpression elseCase = sql.Concat(exprS, padding); return sql.SearchedCase(new SqlWhen[] { new SqlWhen(dontChange, exprS) }, elseCase, source); } break; case "Remove": if (mc.Arguments.Count == 1) { return sql.FunctionCall( typeof(string), "STUFF", new SqlExpression[] { mc.Object, sql.Add(mc.Arguments[0], 1), sql.CLRLENGTH(mc.Object), sql.ValueFromObject("", false, source) }, source); } else if (mc.Arguments.Count == 2) { return sql.FunctionCall( typeof(string), "STUFF", new SqlExpression[] { mc.Object, sql.Add(mc.Arguments[0], 1), mc.Arguments[1], sql.ValueFromObject("", false, source) }, source); } break; case "Replace": if (mc.Arguments[0] is SqlValue && ((SqlValue)mc.Arguments[0]).Value == null) { throw Error.ArgumentNull("old"); } if (mc.Arguments[1] is SqlValue && ((SqlValue)mc.Arguments[1]).Value == null) { throw Error.ArgumentNull("new"); } return sql.FunctionCall( typeof(string), "REPLACE", new SqlExpression[] { mc.Object, mc.Arguments[0], mc.Arguments[1] }, source); case "Substring": if (mc.Arguments.Count == 1) { return sql.FunctionCall( typeof(string), "SUBSTRING", new SqlExpression[] { mc.Object, sql.Add(mc.Arguments[0], 1), sql.CLRLENGTH(mc.Object) }, source); } else if (mc.Arguments.Count == 2) { return sql.FunctionCall( typeof(string), "SUBSTRING", new SqlExpression[] { mc.Object, sql.Add(mc.Arguments[0], 1), mc.Arguments[1] }, source); } break; case "Trim": if (mc.Arguments.Count == 0) { return sql.FunctionCall( typeof(string), "LTRIM", new SqlExpression[] { sql.FunctionCall(typeof(string), "RTRIM", new SqlExpression[] { mc.Object }, source) }, source); } break; case "ToLower": if (mc.Arguments.Count == 0) { return sql.FunctionCall(typeof(string), "LOWER", new SqlExpression[] { mc.Object }, source); } break; case "ToUpper": if (mc.Arguments.Count == 0) { return sql.FunctionCall(typeof(string), "UPPER", new SqlExpression[] { mc.Object }, source); } break; case "get_Chars": // s[i] --> SUBSTRING(@s, @i+1, 1) if (mc.Arguments.Count == 1) { return sql.FunctionCall(typeof(char), "SUBSTRING", new SqlExpression[] {mc.Object, sql.Add( mc.Arguments[0], 1), sql.ValueFromObject(1, false, source) }, source); } break; case "CompareTo": if (mc.Arguments.Count == 1) { if (mc.Arguments[0] is SqlValue && ((SqlValue)mc.Arguments[0]).Value == null) { throw Error.ArgumentNull("value"); } return CreateComparison(mc.Object, mc.Arguments[0], source); } break; } throw GetMethodSupportException(mc); }
internal override SqlExpression VisitClientParameter(SqlClientParameter cp) { if (cp.SqlType.CanBeParameter) { SqlParameter p = new SqlParameter(cp.ClrType, cp.SqlType, this.parameterizer.CreateParameterName(), cp.SourceExpression); this.currentParams.Add(new SqlParameterInfo(p, cp.Accessor.Compile())); return p; } else { return cp; } }