protected ProcessingResult GetKeys(LambdaExpression keySelector, ProcessingResult parentResult, DataContext context)
        {
            if (!parentResult.IsDeferred())
            {
                var keys             = (IList)Activator.CreateInstance(typeof(List <>).MakeGenericType(keySelector.ReturnType));
                var compiledSelector = CompiledExpressionStorage.GetOrAddCompiledLambda(keySelector);

                foreach (var item in parentResult.GetItems())
                {
                    keys.Add(compiledSelector.DynamicInvoke(item));
                }

                return(new ProcessingResult(true, keys));
            }

            var nodeReferences = parentResult.GetDeferredList();
            var keysResult     = ExpressionProcessingHelper.ProcessExpression(keySelector.Body, nodeReferences, context);

            if (!keysResult.IsSuccess)
            {
                return(ProcessingResult.Unsuccessful);
            }

            if (keysResult.IsSingleItem)
            {
                keysResult = ExpressionProcessingHelper.CopyInstances(keysResult, nodeReferences.Count,
                                                                      () => ExpressionProcessingHelper.ProcessExpression(keySelector.Body, nodeReferences, context).Result);
            }

            keysResult = new ProcessingResult(true, keysResult.GetLoadedItems(keySelector.ReturnType));
            return(QueryProcessingHelper.NormalizeMultipleResult(keysResult, keySelector.ReturnType));
        }
        public ProcessingResult ProcessExpression(Expression expression, List <NodeReference> references, DataContext context)
        {
            var memberInitExpression = expression as MemberInitExpression;

            if (memberInitExpression == null)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var instanceResult = ExpressionProcessingHelper.ProcessExpression(memberInitExpression.NewExpression, references, context);

            if (!instanceResult.IsSuccess)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var evaluatedBindings = MemberBindingEvaluator.EvaluateBindings(memberInitExpression.Bindings.ToList(), references, context);

            if (evaluatedBindings.Any(b => !b.IsSuccess))
            {
                return(ProcessingResult.Unsuccessful);
            }

            if (instanceResult.IsSingleItem && evaluatedBindings.Any(b => !b.IsSingle))
            {
                instanceResult = ExpressionProcessingHelper.CopyInstances(instanceResult, references.Count,
                                                                          () => ExpressionProcessingHelper.ProcessExpression(memberInitExpression.NewExpression, references, context).Result);
            }

            return(MemberBindingProcessingHelper.ProcessBindings(evaluatedBindings, instanceResult));
        }
Exemple #3
0
        public ProcessingResult ProcessExpression(Expression expression, List <NodeReference> references, DataContext context)
        {
            var listInitExpression = expression as ListInitExpression;

            if (listInitExpression == null)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var instanceResult = ExpressionProcessingHelper.ProcessExpression(listInitExpression.NewExpression, references, context);

            if (instanceResult == null)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var evaluatedInitializers = EvaluateInitializers(listInitExpression.Initializers, references, context);

            var isSuccess = evaluatedInitializers.All(i => i.Arguments.All(a => a.IsSuccess));

            if (!isSuccess)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var isSingleInitializers = evaluatedInitializers.All(i => i.Arguments.All(a => a.IsSingleItem));

            if (instanceResult.IsSingleItem && !isSingleInitializers)
            {
                instanceResult = ExpressionProcessingHelper.CopyInstances(instanceResult, references.Count,
                                                                          () => ExpressionProcessingHelper.ProcessExpression(listInitExpression.NewExpression, references, context).Result);
            }

            instanceResult = evaluatedInitializers.Aggregate(instanceResult,
                                                             (current, initializer) => MemberBindingProcessingHelper.ProcessListInitializer(initializer, current));

            return(instanceResult);
        }
        public ProcessingResult ProcessQuery(MethodCallExpression query, ProcessingResult parentResult, DataContext context)
        {
            if (!parentResult.IsDeferred())
            {
                return(ProcessingResult.Unsuccessful);
            }

            var unaryExpression  = (UnaryExpression)query.Arguments[1];
            var lambdaExpression = (LambdaExpression)unaryExpression.Operand;

            if (lambdaExpression.Parameters.Count > 1)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var memberExpression = lambdaExpression.Body;
            var nodeReferences   = parentResult.GetDeferredList();

            var result = ExpressionProcessingHelper.ProcessExpression(memberExpression, nodeReferences, context);

            if (!result.IsSuccess)
            {
                return(ProcessingResult.Unsuccessful);
            }

            var targetItemType = QueryProcessingHelper.GetReturnParameterType(query);

            if (!result.IsSingleItem)
            {
                return(QueryProcessingHelper.NormalizeMultipleResult(result, targetItemType));
            }

            var multipleResult = ExpressionProcessingHelper.CopyInstances(result, nodeReferences.Count,
                                                                          () => ExpressionProcessingHelper.ProcessExpression(memberExpression, nodeReferences, context).Result);

            return(new ProcessingResult(true, QueryProcessingHelper.NormalizeMultipleResult(multipleResult, targetItemType).Result));
        }