protected virtual Expression AnalyzeOperands(Expression expression, TranslationContext context) { var operands = expression.GetOperands().ToList(); var newOperands = new List<Expression>(); for (int operandIndex = 0; operandIndex < operands.Count; operandIndex++) { var op = operands[operandIndex]; var newOp = Analyze(op, context); newOperands.Add(newOp); } return expression.ChangeOperands(newOperands, operands); }
/// <summary> /// Cuts tiers in CLR / SQL. /// The search for cut is top-down /// </summary> /// <param name="expression"></param> /// <param name="dataRecordParameter"></param> /// <param name="mappingContextParameter"></param> /// <param name="builderContext"></param> /// <returns></returns> protected virtual Expression CutOutOperands(Expression expression, ParameterExpression dataRecordParameter, ParameterExpression mappingContextParameter, BuilderContext builderContext) { // two options: we cut and return if (GetCutOutOperand(expression, builderContext)) { // "cutting out" means we replace the current expression by a SQL result reader // before cutting out, we check that we're not cutting a table // in this case, we convert it into its declared columns if (expression is TableExpression) { return GetOutputTableReader((TableExpression)expression, dataRecordParameter, mappingContextParameter, builderContext); } // for EntitySets, we have a special EntitySet builder if (expression is EntitySetExpression) { return GetEntitySetBuilder((EntitySetExpression) expression, dataRecordParameter, mappingContextParameter, builderContext); // TODO record EntitySet information, so we can initalize it with owner } // then, the result is registered return GetOutputValueReader(expression, dataRecordParameter, mappingContextParameter, builderContext); } // or we dig down var operands = new List<Expression>(); foreach (var operand in expression.GetOperands()) { operands.Add(operand == null ? null : CutOutOperands(operand, dataRecordParameter, mappingContextParameter, builderContext)); } return expression.ChangeOperands(operands); }
protected virtual Expression CutOutSqlTier(Expression expression, ParameterExpression dataRecordParameter, ParameterExpression sessionParameter, Type expectedType, TranslationContext context) { expectedType = expectedType ?? expression.Type; // two options: we cut and return if (IsSqlTier(expression, context)) { // "cutting out" means we replace the current expression by a SQL result reader // before cutting out, we check that we're not cutting a table in this case, we convert it into its declared columns if (expression is TableExpression) // RI: entity reader comes here return GetOutputTableReader((TableExpression)expression, dataRecordParameter, sessionParameter, context); // RI: single-value result goes here return GetOutputValueReader(expression, expectedType, dataRecordParameter, sessionParameter, context); } // RI: Anon types, custom types go here var newOperands = new List<Expression>(); var operands = expression.GetOperands(); var argTypes = expression.GetArgumentTypes(); for(int i = 0; i < operands.Count; i++ ) { var op = operands[i]; var newOp = op == null ? null : CutOutSqlTier(op, dataRecordParameter, sessionParameter, argTypes[i], context); newOperands.Add(newOp); } Expression newExpr; if (expression is MetaTableExpression) //Joins go here newExpr = ((MetaTableExpression)expression).ConvertToNew(newOperands); else newExpr = expression.ChangeOperands(newOperands, operands); return newExpr; }