protected override void FlattenSubQuery(SubQueryExpression subQueryExpression, FromClauseBase fromClause, QueryModel queryModel,
     int destinationIndex)
 {
     var subQueryModel = subQueryExpression.QueryModel;
     MoveResultOperatorsToParent(queryModel, subQueryModel);
     base.FlattenSubQuery(subQueryExpression, fromClause, queryModel, destinationIndex);
 }
예제 #2
0
        /// <summary>Visits a type binary expression.</summary>
        /// <param name="expression">Expression to be visited.</param>
        /// <returns>Expression visited</returns>
        protected override System.Linq.Expressions.Expression VisitTypeBinary(System.Linq.Expressions.TypeBinaryExpression expression)
        {
            var classMappings = MappingsRepository.FindMappedClasses(expression.TypeOperand);

            if (classMappings.Any())
            {
                Remotion.Linq.Clauses.FromClauseBase sourceExpression = GetSourceExpression(expression.Expression);
                StrongEntityAccessor entityAccessor = _query.FindAllComponents <StrongEntityAccessor>().FirstOrDefault(item => item.SourceExpression == sourceExpression);
                if (entityAccessor == null)
                {
                    entityAccessor = this.GetEntityAccessor(sourceExpression);
                    _query.Elements.Add(entityAccessor);
                }

                EntityTypeConstrain typeConstrain = this.CreateTypeConstrain(expression.TypeOperand, entityAccessor.SourceExpression.FromExpression);
                _lastComponent = typeConstrain;
                if ((_currentComponent.Count > 0) && (_currentComponent.Peek() is BinaryOperatorNavigator))
                {
                    HandleComponent(typeConstrain);
                }
                else if (!entityAccessor.Elements.Contains(typeConstrain))
                {
                    entityAccessor.Elements.Add(typeConstrain);
                }
            }
            else
            {
                return(base.VisitTypeBinary(expression));
            }

            return(expression);
        }
예제 #3
0
        private void FlattenSubQuery(SubQueryExpression subQueryExpression, FromClauseBase fromClause,
		                             QueryModel queryModel)
        {
            // Move the result operator up
            if (queryModel.ResultOperators.Count != 0)
            {
                throw new NotImplementedException();
            }

            var groupBy = (GroupResultOperator) subQueryExpression.QueryModel.ResultOperators[0];

            // Replace the outer select clause...
            queryModel.SelectClause.TransformExpressions(s => GroupBySelectClauseRewriter.ReWrite(s, groupBy, subQueryExpression.QueryModel));

            queryModel.SelectClause.TransformExpressions(
                s =>
                new SwapQuerySourceVisitor(queryModel.MainFromClause, subQueryExpression.QueryModel.MainFromClause).Swap
                    (s));

            MainFromClause innerMainFromClause = subQueryExpression.QueryModel.MainFromClause;
            CopyFromClauseData(innerMainFromClause, fromClause);

            foreach (var bodyClause in subQueryExpression.QueryModel.BodyClauses)
            {
                queryModel.BodyClauses.Add(bodyClause);
            }

            queryModel.ResultOperators.Add(groupBy);
        }
예제 #4
0
        /// <summary>Visits a member expression.</summary>
        /// <param name="expression">Expression to be visited.</param>
        /// <returns>Expression visited</returns>
        protected override System.Linq.Expressions.Expression VisitMember(System.Linq.Expressions.MemberExpression expression)
        {
            if ((expression.Member.Name == "Id") && (typeof(IEntity).IsAssignableFrom(expression.Member.DeclaringType)))
            {
                Remotion.Linq.Clauses.FromClauseBase target = GetMemberTarget(expression);
                if (target != null)
                {
                    return(VisitEntityId(new EntityIdentifierExpression(expression, target)));
                }

                ExceptionHelper.ThrowInvalidCastException(typeof(IEntity), expression.Member.DeclaringType);
            }
            else if (expression.Member is PropertyInfo)
            {
                IPropertyMapping propertyMapping = _entityContext.Mappings.FindPropertyMapping((PropertyInfo)expression.Member);
                if (propertyMapping != null)
                {
                    Remotion.Linq.Clauses.FromClauseBase target = GetMemberTarget(expression);
                    if (target != null)
                    {
                        return(VisitEntityProperty(new EntityPropertyExpression(expression, propertyMapping, target, (_itemNameOverride ?? expression.Member.Name))));
                    }

                    ExceptionHelper.ThrowInvalidCastException(typeof(IEntity), expression.Member.DeclaringType);
                }
                else
                {
                    return(VisitProperty(expression));
                }
            }

            return(base.VisitMember(expression));
        }
예제 #5
0
        /// <summary>Visits a sub-query expression.</summary>
        /// <param name="expression">Expression to be visited.</param>
        /// <returns>Expression visited</returns>
        protected override System.Linq.Expressions.Expression VisitSubQuery(SubQueryExpression expression)
        {
            Remotion.Linq.Clauses.FromClauseBase sourceExpression = (Remotion.Linq.Clauses.FromClauseBase)((QuerySourceReferenceExpression)expression.QueryModel.SelectClause.Selector).ReferencedQuerySource;
            StrongEntityAccessor entityAccessor = (sourceExpression.FromExpression is System.Linq.Expressions.ConstantExpression ? null : this.GetEntityAccessor(sourceExpression));

            if (entityAccessor != null)
            {
                Query query = _query.CreateSubQuery(entityAccessor.About);
                query.AddEntityAccessor(entityAccessor);
                EntityQueryModelVisitor queryModelVisitor = new EntityQueryModelVisitor(query, _entityContext);
                queryModelVisitor.VisitQueryModel(expression.QueryModel);
                _lastComponent = queryModelVisitor.Result;
                HandleComponent(_lastComponent);
            }
            else
            {
                NonEntityQueryModelVisitor       queryModelVisitor = new NonEntityQueryModelVisitor(this, ConstantFromClause);
                Stack <IQueryComponentNavigator> currentComponent  = _currentComponent;
                _currentComponent = new Stack <IQueryComponentNavigator>();
                queryModelVisitor.VisitQueryModel(expression.QueryModel);
                _currentComponent = currentComponent;
                _lastComponent    = queryModelVisitor.Result;
                HandleComponent(_lastComponent);
            }

            return(expression);
        }
예제 #6
0
        /// <summary>Visits an <see cref="EntityExtensions.Predicate" /> method call.</summary>
        /// <param name="expression">Expression to be visited.</param>
        /// <returns>Returns visited expression.</returns>
        protected virtual System.Linq.Expressions.Expression VisitPredicateMethodCall(System.Linq.Expressions.MethodCallExpression expression)
        {
            object objectValue = ((System.Linq.Expressions.ConstantExpression)expression.Arguments[1]).Value;

            if (objectValue is Uri)
            {
                Uri predicate = (Uri)objectValue;
                if (!predicate.IsAbsoluteUri)
                {
                    predicate = new Uri(_entityContext.BaseUriSelector.SelectBaseUri(new EntityId(predicate)), predicate.ToString());
                }

                Visit(expression.Arguments[0]);
                StrongEntityAccessor entityAccessor = null;
                Remotion.Linq.Clauses.FromClauseBase sourceExpression = null;
                if (expression.Arguments[0] is System.Linq.Expressions.MemberExpression)
                {
                    System.Linq.Expressions.MemberExpression memberExpression = (System.Linq.Expressions.MemberExpression)expression.Arguments[0];
                    if (memberExpression.Member is PropertyInfo)
                    {
                        PropertyInfo propertyInfo = (PropertyInfo)memberExpression.Member;
                        sourceExpression = new AdditionalFromClause(propertyInfo.Name, propertyInfo.PropertyType, memberExpression);
                        _query.AddEntityAccessor(entityAccessor = this.GetEntityAccessor(sourceExpression));
                    }
                    else
                    {
                        return(base.VisitMethodCall(expression));
                    }
                }
                else
                {
                    entityAccessor = this.GetEntityAccessor(GetSourceExpression(expression.Arguments[0]));
                }

                if (entityAccessor != null)
                {
                    return(VisitPredicateMethodCallInternal(expression, predicate, entityAccessor));
                }

                return(expression);
            }
            else
            {
                return(base.VisitMethodCall(expression));
            }
        }
예제 #7
0
        private Remotion.Linq.Clauses.FromClauseBase GetSourceExpression(System.Linq.Expressions.Expression expression)
        {
            Remotion.Linq.Clauses.FromClauseBase result            = null;
            System.Linq.Expressions.Expression   currentExpression = expression;
            bool isChange = false;

            while (currentExpression != null)
            {
                if (currentExpression is System.Linq.Expressions.MemberExpression)
                {
                    System.Linq.Expressions.MemberExpression memberExpression = (System.Linq.Expressions.MemberExpression)currentExpression;
                    if (!(memberExpression.Member is PropertyInfo))
                    {
                        throw CreateUnhandledItemException <System.Linq.Expressions.MemberExpression>(memberExpression, "GetSourceExpression");
                    }

                    currentExpression = memberExpression.Expression;
                    isChange          = true;
                }
                else if (currentExpression is Remotion.Linq.Clauses.Expressions.QuerySourceReferenceExpression)
                {
                    result = (Remotion.Linq.Clauses.FromClauseBase)((Remotion.Linq.Clauses.Expressions.QuerySourceReferenceExpression)currentExpression).ReferencedQuerySource;
                    if (!typeof(IQueryable).IsAssignableFrom(result.FromExpression.Type))
                    {
                        Stack <IQueryComponentNavigator> currentComponent = _currentComponent;
                        _currentComponent = new Stack <IQueryComponentNavigator>();
                        Visit(result.FromExpression);
                        _currentComponent = currentComponent;
                        isChange          = true;
                    }

                    break;
                }

                if (isChange)
                {
                    isChange = false;
                }
                else
                {
                    break;
                }
            }

            return(result);
        }
		private static void FlattenSubQuery(SubQueryExpression subQueryExpression, FromClauseBase fromClause, QueryModel queryModel, int destinationIndex)
		{
			if (!CheckFlattenable(subQueryExpression.QueryModel))
				return;

			var mainFromClause = subQueryExpression.QueryModel.MainFromClause;
			CopyFromClauseData(mainFromClause, fromClause);

			var innerSelectorMapping = new QuerySourceMapping();
			innerSelectorMapping.AddMapping(fromClause, subQueryExpression.QueryModel.SelectClause.Selector);
			queryModel.TransformExpressions((ex => ReferenceReplacingExpressionTreeVisitor.ReplaceClauseReferences(ex, innerSelectorMapping, false)));

			InsertBodyClauses(subQueryExpression.QueryModel.BodyClauses, queryModel, destinationIndex);
			CopyResultOperators(subQueryExpression.QueryModel.ResultOperators, queryModel);

			var innerBodyClauseMapping = new QuerySourceMapping();
			innerBodyClauseMapping.AddMapping(mainFromClause, new QuerySourceReferenceExpression(fromClause));
			queryModel.TransformExpressions((ex => ReferenceReplacingExpressionTreeVisitor.ReplaceClauseReferences(ex, innerBodyClauseMapping, false)));
		}
예제 #9
0
        internal static Remotion.Linq.Clauses.FromClauseBase TransformFromExpression(this IQueryVisitor visitor, Remotion.Linq.Clauses.FromClauseBase sourceExpression)
        {
            Remotion.Linq.Clauses.FromClauseBase result     = sourceExpression;
            System.Linq.Expressions.Expression   expression = visitor.TransformUnaryExpression(sourceExpression.FromExpression);
            if (expression != sourceExpression.FromExpression)
            {
                object item;
                if (!TransformedExpressionsCache.TryGetValue(sourceExpression, out item))
                {
                    TransformedExpressionsCache[sourceExpression] = result =
                        new AdditionalFromClause(sourceExpression.ItemName, sourceExpression.ItemType, (System.Linq.Expressions.MemberExpression)expression);
                }
                else
                {
                    result = (AdditionalFromClause)item;
                }
            }

            return(result);
        }
예제 #10
0
        internal Remotion.Linq.Clauses.FromClauseBase GetMemberTarget(System.Linq.Expressions.MemberExpression expression)
        {
            Remotion.Linq.Clauses.FromClauseBase     result           = null;
            System.Linq.Expressions.MemberExpression memberExpression = expression.Expression as System.Linq.Expressions.MemberExpression;
            if ((memberExpression == null) && ((memberExpression = ((IQueryVisitor)this).TransformUnaryExpression(expression.Expression) as System.Linq.Expressions.MemberExpression) != null))
            {
                SafeVisitExpression(memberExpression);
            }

            if (memberExpression is System.Linq.Expressions.MemberExpression)
            {
                if (memberExpression.Member is PropertyInfo)
                {
                    PropertyInfo         propertyInfo   = (PropertyInfo)memberExpression.Member;
                    string               itemName       = propertyInfo.Name.CamelCase();
                    StrongEntityAccessor entityAccessor = _query.FindAllComponents <StrongEntityAccessor>().Where(item => item.SourceExpression.FromExpression == memberExpression).FirstOrDefault();
                    if (entityAccessor != null)
                    {
                        itemName = _query.RetrieveIdentifier(entityAccessor.About.Name);
                    }
                    else
                    {
                        SafeVisitExpression(memberExpression);
                    }

                    result = new AdditionalFromClause(itemName, propertyInfo.PropertyType.FindItemType(), memberExpression);
                }
                else
                {
                    throw CreateUnhandledItemException <System.Linq.Expressions.MemberExpression>(expression, "GetMemberTarget");
                }
            }
            else
            {
                result = GetSourceExpression(expression);
            }

            return(result);
        }
예제 #11
0
        /// <summary>Visits a query source expression.</summary>
        /// <param name="expression">Expression to be visited.</param>
        /// <returns>Expression visited.</returns>
        protected override System.Linq.Expressions.Expression VisitQuerySourceReference(QuerySourceReferenceExpression expression)
        {
            Remotion.Linq.Clauses.FromClauseBase sourceExpression = GetSourceExpression(expression);
            StrongEntityAccessor entityAccessor = this.GetEntityAccessor(sourceExpression);

            if (entityAccessor != null)
            {
                _query.AddEntityAccessor(entityAccessor);
                _lastComponent = _query;
            }
            else
            {
                _lastComponent = (from entityConstrain in _query.FindAllComponents <EntityConstrain>()
                                  where entityConstrain.GetType() == typeof(EntityConstrain)
                                  let identifier = entityConstrain.Value as Identifier
                                                   let targetExpression = ((IQueryVisitor)this).TransformFromExpression(sourceExpression).FromExpression
                                                                          where (identifier != null) && (targetExpression != null) && (entityConstrain.TargetExpression.EqualsTo(targetExpression))
                                                                          select identifier).FirstOrDefault();
                HandleComponent(_lastComponent);
            }

            return(expression);
        }
		public PagingRewriterSelectClauseVisitor(FromClauseBase querySource)
		{
			this.querySource = querySource;
		}
예제 #13
0
    protected virtual void FlattenSubQuery (
        SubQueryExpression subQueryExpression, FromClauseBase fromClause, QueryModel queryModel, int destinationIndex)
    {
      ArgumentUtility.CheckNotNull ("subQueryExpression", subQueryExpression);
      ArgumentUtility.CheckNotNull ("fromClause", fromClause);
      ArgumentUtility.CheckNotNull ("queryModel", queryModel);

      CheckFlattenable (subQueryExpression.QueryModel);

      var innerMainFromClause = subQueryExpression.QueryModel.MainFromClause;
      CopyFromClauseData (innerMainFromClause, fromClause);

      var innerSelectorMapping = new QuerySourceMapping();
      innerSelectorMapping.AddMapping (fromClause, subQueryExpression.QueryModel.SelectClause.Selector);
      queryModel.TransformExpressions (ex => ReferenceReplacingExpressionTreeVisitor.ReplaceClauseReferences (ex, innerSelectorMapping, false));

      InsertBodyClauses (subQueryExpression.QueryModel.BodyClauses, queryModel, destinationIndex);

      var innerBodyClauseMapping = new QuerySourceMapping();
      innerBodyClauseMapping.AddMapping (innerMainFromClause, new QuerySourceReferenceExpression (fromClause));
      queryModel.TransformExpressions (ex => ReferenceReplacingExpressionTreeVisitor.ReplaceClauseReferences (ex, innerBodyClauseMapping, false));
    }
예제 #14
0
    protected void CopyFromClauseData (FromClauseBase source, FromClauseBase destination)
    {
      ArgumentUtility.CheckNotNull ("source", source);
      ArgumentUtility.CheckNotNull ("destination", destination);

      destination.FromExpression = source.FromExpression;
      destination.ItemName = source.ItemName;
      destination.ItemType = source.ItemType;
    }
예제 #15
0
        internal static EntityTypeConstrain CreateTypeConstrain(this IQueryVisitor visitor, Remotion.Linq.Clauses.FromClauseBase sourceExpression)
        {
            EntityTypeConstrain result = null;
            Type entityType            = sourceExpression.ItemType.FindEntityType();

            if ((entityType != null) && (entityType != typeof(IEntity)))
            {
                result = visitor.CreateTypeConstrain(entityType, sourceExpression.FromExpression);
            }

            return(result);
        }
예제 #16
0
 protected void CopyFromClauseData(FromClauseBase source, FromClauseBase destination)
 {
     destination.FromExpression = source.FromExpression;
     destination.ItemName = source.ItemName;
     destination.ItemType = source.ItemType;
 }
 /// <summary>Visits a from clause.</summary>
 /// <param name="fromClause">From clause to be visited.</param>
 /// <param name="queryModel">Query model containing given from clause.</param>
 /// <param name="index">Index of the where clause in the query model. In case of the main from clause this value is -1.</param>
 protected virtual void VisitQuerableFromClause(FromClauseBase fromClause, Remotion.Linq.QueryModel queryModel, int index)
 {
     if ((typeof(IQueryable).IsAssignableFrom(fromClause.FromExpression.Type)) &&
         (fromClause.FromExpression.Type.GetGenericArguments().Length > 0) &&
         (fromClause.FromExpression.Type.GetGenericArguments()[0] != typeof(IEntity)))
     {
         this.GetEntityAccessor(fromClause);
     }
 }
예제 #18
0
        internal static StrongEntityAccessor GetEntityAccessor(this IQueryVisitor visitor, Remotion.Linq.Clauses.FromClauseBase sourceExpression)
        {
            StrongEntityAccessor entityAccessor = null;

            if (typeof(IEntity).GetTypeInfo().IsAssignableFrom(sourceExpression.ItemType))
            {
                sourceExpression = visitor.TransformFromExpression(sourceExpression);
                entityAccessor   = visitor.Query.FindAllComponents <StrongEntityAccessor>().FirstOrDefault(item => item.SourceExpression.EqualsTo(sourceExpression));
                if (entityAccessor == null)
                {
                    Identifier identifier = visitor.Query.FindAllComponents <EntityConstrain>()
                                            .Where(item => (item.TargetExpression.EqualsTo(sourceExpression.FromExpression)) && (item.Value is Identifier))
                                            .Select(item => (Identifier)item.Value)
                                            .FirstOrDefault() ?? new Identifier(visitor.Query.CreateVariableName(sourceExpression.ItemName), sourceExpression.ItemType.FindEntityType());
                    entityAccessor = new StrongEntityAccessor(identifier, sourceExpression);
                    entityAccessor.UnboundGraphName = entityAccessor.About;
                    EntityTypeConstrain constrain = visitor.CreateTypeConstrain(sourceExpression);
                    if ((constrain != null) && (!entityAccessor.Elements.Contains(constrain)))
                    {
                        entityAccessor.Elements.Add(constrain);
                    }
                }
            }

            return(entityAccessor);
        }