private Expression BuildSkipTakeSource(Expression source, OeSkipTokenNameValue[] skipTokenNameValues, bool isDatabaseNullHighestValue) { BuildOrderBySkipTake(_rootNavigationItem, _odataUri.OrderBy, HasSelectItems(_odataUri.SelectAndExpand)); source = BuildJoin(source, new OeNavigationSelectItem[] { _rootNavigationItem }); long?top = GetTop(_rootNavigationItem, _odataUri.Top); if (top == null && _odataUri.Skip == null) { return(source); } var expressionBuilder = new OeExpressionBuilder(_joinBuilder); source = expressionBuilder.ApplySkipToken(source, skipTokenNameValues, _odataUri.OrderBy, isDatabaseNullHighestValue); source = expressionBuilder.ApplyOrderBy(source, _odataUri.OrderBy); source = expressionBuilder.ApplySkip(source, _odataUri.Skip, _odataUri.Path); return(expressionBuilder.ApplyTake(source, top, _odataUri.Path)); bool HasSelectItems(SelectExpandClause selectExpandClause) { if (selectExpandClause != null) { foreach (SelectItem odataSelectItem in selectExpandClause.SelectedItems) { if (odataSelectItem is PathSelectItem pathSelectItem && pathSelectItem.SelectedPath.LastSegment is PropertySegment) { return(true); } } } return(false); } }
private Expression GetInnerSource(OeSelectItem navigationItem, ExpandedNavigationSelectItem item) { Type clrEntityType = _visitor.EdmModel.GetClrType(navigationItem.EdmProperty.DeclaringType); PropertyInfo navigationClrProperty = OeEdmClrHelper.GetPropertyIgnoreCase(clrEntityType, navigationItem.EdmProperty); Type itemType = OeExpressionHelper.GetCollectionItemType(navigationClrProperty.PropertyType); if (itemType == null) { itemType = navigationClrProperty.PropertyType; } var visitor = new OeQueryNodeVisitor(_visitor, Expression.Parameter(itemType)); var expressionBuilder = new OeExpressionBuilder(_joinBuilder, visitor); Expression innerSource = Expression.Constant(null, typeof(IEnumerable <>).MakeGenericType(itemType)); innerSource = expressionBuilder.ApplyFilter(innerSource, item.FilterOption); if (item.SkipOption != null || item.TopOption != null) { Expression source = Expression.Constant(null, typeof(IEnumerable <>).MakeGenericType(navigationClrProperty.DeclaringType)); innerSource = OeCrossApplyBuilder.Build(source, innerSource, item, navigationItem.Path, expressionBuilder); } return(innerSource); }
private Expression GetInnerSource(OeSelectItem navigationItem, ExpandedNavigationSelectItem item) { Type clrEntityType = _visitor.EdmModel.GetClrType(navigationItem.EdmProperty.DeclaringType); PropertyInfo navigationClrProperty = clrEntityType.GetPropertyIgnoreCase(navigationItem.EdmProperty); Type itemType = OeExpressionHelper.GetCollectionItemType(navigationClrProperty.PropertyType); if (itemType == null) { itemType = navigationClrProperty.PropertyType; } var visitor = new OeQueryNodeVisitor(_visitor, Expression.Parameter(itemType)); var expressionBuilder = new OeExpressionBuilder(_joinBuilder, visitor); var navigationEdmProperty = (IEdmNavigationProperty)navigationItem.EdmProperty; if (navigationEdmProperty.ContainsTarget) { ModelBuilder.ManyToManyJoinDescription joinDescription = _visitor.EdmModel.GetManyToManyJoinDescription(navigationEdmProperty); navigationEdmProperty = joinDescription.TargetNavigationProperty; } IEdmEntitySet innerEntitySet = OeEdmClrHelper.GetEntitySet(_visitor.EdmModel, navigationEdmProperty); Expression innerSource = OeEnumerableStub.CreateEnumerableStubExpression(itemType, innerEntitySet); innerSource = expressionBuilder.ApplyFilter(innerSource, item.FilterOption); if (item.SkipOption != null || item.TopOption != null) { Expression source = OeEnumerableStub.CreateEnumerableStubExpression(navigationClrProperty.DeclaringType, (IEdmEntitySet)_navigationItem.EntitySet); innerSource = OeCrossApplyBuilder.Build(source, innerSource, item, navigationItem.Path, expressionBuilder); } return(innerSource); }
private static Expression BuildSkipTakeSource(Expression source, OeQueryContext queryContext, OeSelectItem navigationItem) { bool hasSelectItems = HasSelectItems(queryContext.ODataUri.SelectAndExpand); source = BuildOrderBySkipToken(navigationItem, queryContext.ODataUri.OrderBy, source, queryContext.JoinBuilder, hasSelectItems); queryContext.JoinBuilder.Visitor.ChangeParameterType(source); var expressionBuilder = new OeExpressionBuilder(queryContext.JoinBuilder); source = expressionBuilder.ApplySkipToken(source, queryContext.SkipTokenNameValues, queryContext.ODataUri.OrderBy, queryContext.IsDatabaseNullHighestValue); source = expressionBuilder.ApplyOrderBy(source, queryContext.ODataUri.OrderBy); source = expressionBuilder.ApplySkip(source, queryContext.ODataUri.Skip, queryContext.ODataUri.Path); return(expressionBuilder.ApplyTake(source, queryContext.ODataUri.Top, queryContext.ODataUri.Path)); }
private Expression GetInnerSource(OeNavigationSelectItem navigationItem) { if (navigationItem.Parent == null) { throw new InvalidOperationException("Inner source cannot exist for root item"); } Type clrEntityType = _edmModel.GetClrType(navigationItem.EdmProperty.DeclaringType); PropertyInfo navigationClrProperty = clrEntityType.GetPropertyIgnoreCase(navigationItem.EdmProperty); Type itemType = OeExpressionHelper.GetCollectionItemTypeOrNull(navigationClrProperty.PropertyType) ?? navigationClrProperty.PropertyType; var visitor = new OeQueryNodeVisitor(_joinBuilder.Visitor, Expression.Parameter(itemType)); var expressionBuilder = new OeExpressionBuilder(_joinBuilder, visitor); IEdmNavigationProperty navigationProperty = navigationItem.EdmProperty; if (navigationItem.EdmProperty.ContainsTarget) { ModelBuilder.ManyToManyJoinDescription joinDescription = _edmModel.GetManyToManyJoinDescription(navigationProperty); navigationProperty = joinDescription.TargetNavigationProperty; } IEdmEntitySet innerEntitySet = OeEdmClrHelper.GetEntitySet(_edmModel, navigationProperty); Expression innerSource = OeEnumerableStub.CreateEnumerableStubExpression(itemType, innerEntitySet); ExpandedNavigationSelectItem item = navigationItem.NavigationSelectItem; innerSource = expressionBuilder.ApplyFilter(innerSource, item.FilterOption); long?top = GetTop(navigationItem, item.TopOption); if (top == null && item.SkipOption == null) { return(innerSource); } OrderByClause orderByClause = item.OrderByOption; if (navigationItem.PageSize > 0) { orderByClause = OeSkipTokenParser.GetUniqueOrderBy(navigationItem.EntitySet, item.OrderByOption, null); } var entitySet = (IEdmEntitySet)navigationItem.Parent.EntitySet; Expression source = OeEnumerableStub.CreateEnumerableStubExpression(navigationClrProperty.DeclaringType, entitySet); var crossApplyBuilder = new OeCrossApplyBuilder(_edmModel, expressionBuilder); return(crossApplyBuilder.Build(source, innerSource, navigationItem.Path, orderByClause, item.SkipOption, top)); }
private Expression BuildSkipTakeSource(Expression source, OeSkipTokenNameValue[] skipTokenNameValues, bool isDatabaseNullHighestValue) { BuildOrderBySkipTake(_rootNavigationItem, _odataUri.OrderBy, HasSelectItems(_odataUri.SelectAndExpand)); source = BuildJoin(source, new OeNavigationSelectItem[] { _rootNavigationItem }); long?top = GetTop(_rootNavigationItem, _odataUri.Top); if (top == null && _odataUri.Skip == null) { return(source); } var expressionBuilder = new OeExpressionBuilder(_joinBuilder); source = expressionBuilder.ApplySkipToken(source, skipTokenNameValues, _odataUri.OrderBy, isDatabaseNullHighestValue); source = expressionBuilder.ApplyOrderBy(source, _odataUri.OrderBy); source = expressionBuilder.ApplySkip(source, _odataUri.Skip, _odataUri.Path); return(expressionBuilder.ApplyTake(source, top, _odataUri.Path));
public OeCrossApplyBuilder(IEdmModel edmModel, OeExpressionBuilder expressionBuilder) { _edmModel = edmModel; _expressionBuilder = expressionBuilder; }
public static MethodCallExpression Build(Expression outer, Expression inner, ExpandedNavigationSelectItem item, ODataPath odataPath, OeExpressionBuilder expressionBuilder) { var segment = (NavigationPropertySegment)item.PathToNavigationProperty.LastSegment; Type outerType = OeExpressionHelper.GetCollectionItemType(outer.Type); var outerParameter = Expression.Parameter(outerType, outerType.Name); Expression subquery = CreateWhereExpression(outerParameter, inner, segment.NavigationProperty); subquery = expressionBuilder.ApplyOrderBy(subquery, item.OrderByOption); subquery = expressionBuilder.ApplySkip(subquery, item.SkipOption, odataPath); subquery = expressionBuilder.ApplyTake(subquery, item.TopOption, odataPath); Type innerType = OeExpressionHelper.GetCollectionItemType(inner.Type); MethodInfo selectManyMethdoInfo = OeMethodInfoHelper.GetSelectManyMethodInfo(outerType, innerType); return(Expression.Call(selectManyMethdoInfo, outer, Expression.Lambda(subquery, outerParameter))); }