Ejemplo n.º 1
0
        /// <summary>
        /// Returns whether or not the uri refers to a WebInvoke service operation call
        /// </summary>
        /// <param name="uri">The uri to extend</param>
        /// <returns>whether or not the uri refers to a WebInvoke service operation call</returns>
        public static bool IsWebInvokeServiceOperation(this ODataUri uri)
        {
            if (uri.IsServiceOperation())
            {
                ODataUriSegment functionSegment = uri.Segments.First(s => s is FunctionSegment);
                return(functionSegment.CheckSegment <FunctionSegment>(f => f.Function.Annotations.OfType <LegacyServiceOperationAnnotation>().Single().Method == Http.HttpVerb.Post));
            }

            return(false);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Gets the expected payload type for a request to the given uri
        /// </summary>
        /// <param name="requestUri">The request uri</param>
        /// <returns>The expected payload type</returns>
        public static ODataPayloadElementType GetExpectedPayloadType(this ODataUri requestUri)
        {
            if (requestUri.Segments.OfType <UnrecognizedSegment>().Any())
            {
                return(ODataPayloadElementType.Unknown);
            }

            if (requestUri.IsMetadata())
            {
                return(ODataPayloadElementType.MetadataPayloadElement);
            }

            if (requestUri.IsBatch())
            {
                return(ODataPayloadElementType.BatchResponsePayload);
            }

            if (requestUri.IsCount() || requestUri.IsPropertyValue() || requestUri.IsMediaResource() || requestUri.IsNamedStream())
            {
                return(ODataPayloadElementType.PrimitiveValue);
            }

            if (requestUri.IsEntity())
            {
                return(ODataPayloadElementType.EntityInstance);
            }

            if (requestUri.IsEntitySet())
            {
                return(ODataPayloadElementType.EntitySetInstance);
            }

            if (requestUri.IsEntityReferenceLink())
            {
                return(requestUri.GetExpectedLinkPayloadType());
            }

            if (requestUri.IsProperty())
            {
                var property = requestUri.Segments.OfType <PropertySegment>().Last();
                return(property.Property.GetExpectedPayloadType());
            }

            if (requestUri.IsServiceOperation() || requestUri.IsAction())
            {
                var serviceOp = requestUri.Segments.OfType <FunctionSegment>().Last();
                return(serviceOp.Function.GetExpectedPayloadType());
            }

            return(ODataPayloadElementType.Unknown);
        }
        /// <summary>
        /// Generates the expected next link for a top-level feed
        /// </summary>
        /// <param name="requestUri">The request URI.</param>
        /// <param name="pageSize">The page size.</param>
        /// <param name="lastEntityValue">The last entity value.</param>
        /// <returns>
        /// The expected next link
        /// </returns>
        public string GenerateNextLink(ODataUri requestUri, int pageSize, QueryStructuralValue lastEntityValue)
        {
            ExceptionUtilities.CheckArgumentNotNull(requestUri, "requestUri");
            ExceptionUtilities.CheckArgumentNotNull(lastEntityValue, "lastEntityValue");
            
            var queryBasedUri = requestUri as QueryBasedODataUri;
            ExceptionUtilities.CheckObjectNotNull(queryBasedUri, "Only uris which were generated from queries are supported");
            
            var skipTokenValues = new List<object>();
            foreach (var keySelector in queryBasedUri.OrderByExpressions.SelectMany(o => o.KeySelectors))
            {
                skipTokenValues.Add(this.EvaluateLambdaForEntity(lastEntityValue, keySelector));
            }

            foreach (var keyProperty in lastEntityValue.Type.Properties.Where(p => p.IsPrimaryKey))
            {
                skipTokenValues.Add(lastEntityValue.GetScalarValue(keyProperty.Name).Value);
            }

            var skiptoken = this.BuildSkipTokenFromValues(skipTokenValues);

            // copy request uri segments exactly
            var nextLinkUri = new ODataUri(requestUri.Segments);

            // copy over $orderby, $filter, $expand, $select, and $inlinecount
            nextLinkUri.OrderBy = ModifyQueryOptionToMatchProduct(requestUri.OrderBy);
            nextLinkUri.Filter = ModifyQueryOptionToMatchProduct(requestUri.Filter);
            nextLinkUri.ExpandSegments = requestUri.ExpandSegments;
            nextLinkUri.SelectSegments = requestUri.SelectSegments;

            string inlineCountValue;
            if (requestUri.TryGetInlineCountValue(out inlineCountValue))
            {
                nextLinkUri.InlineCount = inlineCountValue;
            }

            // add the $skiptoken generated above
            nextLinkUri.SkipToken = skiptoken;

            // generate a new $top value
            if (requestUri.Top.HasValue)
            {
                var top = requestUri.Top.Value - pageSize;
                if (top > 0)
                {
                    nextLinkUri.Top = top;
                }
            }

            if (requestUri.IsServiceOperation())
            {
                var functionSegment = requestUri.Segments.OfType<FunctionSegment>().Last();
                foreach (var paramName in functionSegment.Function.Parameters.Select(p => p.Name))
                {
                    string paramValue;
                    if (requestUri.CustomQueryOptions.TryGetValue(paramName, out paramValue))
                    {
                        nextLinkUri.CustomQueryOptions[paramName] = paramValue;
                    }
                }
            }

            return this.UriToStringConverter.ConvertToString(nextLinkUri);
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Builds the ODataPayloadContext context from OODataUri.
        /// </summary>
        /// <param name="uri">The URI.</param>
        /// <returns>A OData Payload Context</returns>
        public static ODataPayloadContext BuildODataPayloadContextFromODataUri(ODataUri uri)
        {
            var payloadContext = new ODataPayloadContext();

            payloadContext.PayloadUri          = uri;
            payloadContext.ExpectedPayloadKind = uri.GetExpectedPayloadType();

            switch (payloadContext.ExpectedPayloadKind)
            {
            case ODataPayloadElementType.EntitySetInstance:
            case ODataPayloadElementType.EntityInstance:
                SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);
                break;

            case ODataPayloadElementType.PrimitiveProperty:
            case ODataPayloadElementType.PrimitiveMultiValueProperty:
            case ODataPayloadElementType.ComplexProperty:
            case ODataPayloadElementType.ComplexMultiValueProperty:
            case ODataPayloadElementType.EmptyCollectionProperty:
                var propertySegment = uri.Segments.OfType <PropertySegment>().LastOrDefault();
                if (propertySegment != null)
                {
                    payloadContext.ExpectedMemberProperty = propertySegment.Property;
                    SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);

                    var parentPropertySegment = uri.Segments.GetSecondToLastOrDefault <PropertySegment>();
                    if (parentPropertySegment != null)
                    {
                        var collectionDataType = parentPropertySegment.Property.PropertyType as CollectionDataType;
                        if (collectionDataType != null)
                        {
                            var elementComplexDataType = collectionDataType.ElementDataType as ComplexDataType;
                            ExceptionUtilities.CheckObjectNotNull(elementComplexDataType, "Expected non complex DataType");
                            payloadContext.ExpectedPropertyDeclaringParentType = elementComplexDataType.Definition;
                        }
                        else
                        {
                            var complexDataType = parentPropertySegment.Property.PropertyType as ComplexDataType;
                            ExceptionUtilities.CheckObjectNotNull(complexDataType, "Expected non null complex DataType");
                            payloadContext.ExpectedPropertyDeclaringParentType = complexDataType.Definition;
                        }
                    }
                    else
                    {
                        payloadContext.ExpectedPropertyDeclaringParentType = payloadContext.ExpectedEntityType;
                    }
                }
                else
                {
                    ExceptionUtilities.Assert(
                        uri.IsFunction() || uri.IsServiceOperation() || uri.IsAction(),
                        "Property uri contains no property segments and is not a function/service operation/action.");
                    var functionSegment = uri.Segments.Last() as FunctionSegment ?? uri.Segments[uri.Segments.Count - 2] as FunctionSegment;
                    ExceptionUtilities.CheckObjectNotNull(functionSegment, "Failed to find function segment in finction/service operation uri");
                    payloadContext.ExpectedFunction = functionSegment.Function;
                }

                break;

            case ODataPayloadElementType.DeferredLink:
            case ODataPayloadElementType.LinkCollection:
                var navigationSegment = uri.Segments.OfType <NavigationSegment>().Last();
                ExceptionUtilities.CheckObjectNotNull(navigationSegment, "No navigation segments found for expected navigation property uri");
                payloadContext.ExpectedNavigationProperty = navigationSegment.NavigationProperty;
                SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);
                break;
            }

            return(payloadContext);
        }
Ejemplo n.º 5
0
        /// <summary>
        /// Builds the ODataPayloadContext context from OODataUri.
        /// </summary>
        /// <param name="uri">The URI.</param>
        /// <returns>A OData Payload Context</returns>
        public static ODataPayloadContext BuildODataPayloadContextFromODataUri(ODataUri uri)
        {
            var payloadContext = new ODataPayloadContext();
            payloadContext.PayloadUri = uri;
            payloadContext.ExpectedPayloadKind = uri.GetExpectedPayloadType();

            switch (payloadContext.ExpectedPayloadKind)
            {
                case ODataPayloadElementType.EntitySetInstance:
                case ODataPayloadElementType.EntityInstance:
                    SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);
                    break;

                case ODataPayloadElementType.PrimitiveProperty:
                case ODataPayloadElementType.PrimitiveMultiValueProperty:
                case ODataPayloadElementType.ComplexProperty:
                case ODataPayloadElementType.ComplexMultiValueProperty:
                case ODataPayloadElementType.EmptyCollectionProperty:
                    var propertySegment = uri.Segments.OfType<PropertySegment>().LastOrDefault();
                    if (propertySegment != null)
                    {
                        payloadContext.ExpectedMemberProperty = propertySegment.Property;
                        SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);

                        var parentPropertySegment = uri.Segments.GetSecondToLastOrDefault<PropertySegment>();
                        if (parentPropertySegment != null)
                        {
                            var collectionDataType = parentPropertySegment.Property.PropertyType as CollectionDataType;
                            if (collectionDataType != null)
                            {
                                var elementComplexDataType = collectionDataType.ElementDataType as ComplexDataType;
                                ExceptionUtilities.CheckObjectNotNull(elementComplexDataType, "Expected non complex DataType");
                                payloadContext.ExpectedPropertyDeclaringParentType = elementComplexDataType.Definition;
                            }
                            else
                            {
                                var complexDataType = parentPropertySegment.Property.PropertyType as ComplexDataType;
                                ExceptionUtilities.CheckObjectNotNull(complexDataType, "Expected non null complex DataType");
                                payloadContext.ExpectedPropertyDeclaringParentType = complexDataType.Definition;
                            }
                        }
                        else
                        {
                            payloadContext.ExpectedPropertyDeclaringParentType = payloadContext.ExpectedEntityType;
                        }
                    }
                    else
                    {
                        ExceptionUtilities.Assert(
                            uri.IsFunction() || uri.IsServiceOperation() || uri.IsAction(),
                            "Property uri contains no property segments and is not a function/service operation/action.");
                        var functionSegment = uri.Segments.Last() as FunctionSegment ?? uri.Segments[uri.Segments.Count - 2] as FunctionSegment;
                        ExceptionUtilities.CheckObjectNotNull(functionSegment, "Failed to find function segment in finction/service operation uri");
                        payloadContext.ExpectedFunction = functionSegment.Function;
                    }

                    break;

                case ODataPayloadElementType.DeferredLink:
                case ODataPayloadElementType.LinkCollection:
                    var navigationSegment = uri.Segments.OfType<NavigationSegment>().Last();
                    ExceptionUtilities.CheckObjectNotNull(navigationSegment, "No navigation segments found for expected navigation property uri");
                    payloadContext.ExpectedNavigationProperty = navigationSegment.NavigationProperty;
                    SetExpectedEntitySetAndTypeFromUri(payloadContext, uri);
                    break;
            }

            return payloadContext;
        }