예제 #1
0
        public override object Execute(Expression expression)
        {
            var methodCallExpression = expression as MethodCallExpression;
            var elementType          = GetElementTypeFromExpression(expression) ?? TypeSystem.GetElementType(expression.Type);

            if (!typeof(crmbaseentity).IsAssignableFrom(elementType))
            {
                throw new NotSupportedException($"Type '{elementType.FullName}' is not supported with GenericRepository<>.");
            }

            var webapi = _serviceProvider.GetService(typeof(GenericRepository <>).MakeGenericType(elementType));

            var genericRepositoryType = webapi.GetType();
            var command = Translate(expression, elementType);

            try
            {
                var methodCall = genericRepositoryType.GetMethod("RetrieveMultiple").Invoke(webapi, new object[] { command });
                var result     = methodCall.GetType().GetProperty("Result").GetGetMethod().Invoke(methodCall, null);

                if (methodCallExpression == null)
                {
                    return(result);
                }

                if (methodCallExpression.Method.Name == "OrderBy" || methodCallExpression.Method.Name == "OrderByDescending")
                {
                    var mc = methodCallExpression;
                    while (mc != null)
                    {
                        if (mc.Arguments.Count == 0)
                        {
                            break;
                        }
                        mc = mc.Arguments[0] as MethodCallExpression;
                        if (mc?.Method.Name == "Select")
                        {
                            methodCallExpression = mc;
                            break;
                        }
                    }
                }

                if (methodCallExpression.Method.Name == "Select")
                {
                    var operand = (methodCallExpression.Arguments[1] as UnaryExpression).Operand as LambdaExpression;
                    if (operand?.ReturnType != elementType)
                    {
                        var resultWithLambdaInvoked = (IList)Activator.CreateInstance(typeof(List <>).MakeGenericType(operand.ReturnType));
                        var fn = operand.Compile();
                        foreach (var item in (IEnumerable)result)
                        {
                            resultWithLambdaInvoked.Add(fn.DynamicInvoke(item));
                        }
                        result = resultWithLambdaInvoked;
                    }
                }

                return(result);
            }
            finally
            {
                genericRepositoryType.GetMethod("Dispose").Invoke(webapi, null);
            }
        }