예제 #1
0
        /// <summary>
        /// Gets MetadataItem object for URI relative path under the specified EntityContainer instance
        /// </summary>
        /// <param name="container">The EntityContainer instance</param>
        /// <param name="pathSegment">The URI relative path</param>
        /// <param name="uriType">Output parameter of UriType value</param>
        /// <returns>The MetadataItem instance if one is found; null otherwise</returns>
        private static MetadataItem GetTargetType(EntityContainer container, IEnumerable <string> pathSegment, ref UriType uriType)
        {
            ODataUriItem curr = new ODataUriItem(container, UriType.URI_Container);

            foreach (var segment in pathSegment)
            {
                // to normalize first segment
                string       segmentKey;
                string       segmentCore = ResourcePathHelper.ParseSegment(segment, out segmentKey);
                ODataUriItem subItem     = curr.GetItem(segmentCore);
                if (subItem == null)
                {
                    uriType = UriType.URIUNKNOWN;
                    return(null);
                }

                if (subItem.uriType == UriType.URI1 && !string.IsNullOrEmpty(segmentKey))
                {
                    subItem = new ODataUriItem(((EntitySet)subItem.Item).ElementType, UriType.URI2);
                }

                curr = subItem;
            }

            uriType = curr.uriType;
            return(curr.Item);
        }
예제 #2
0
        /// <summary>
        /// Gets the short name of the entity for the context
        /// </summary>
        /// <param name="context">The context object which directly or indirectly points to an entry</param>
        /// <returns>The short name of entity</returns>
        public static string GetEntityName(ServiceContext context)
        {
            string entityName = context.EntityTypeShortName;

            if (string.IsNullOrEmpty(entityName))
            {
                var     edmxHelper   = new EdmxHelper(XElement.Parse(context.MetadataDocument));
                var     segments     = ResourcePathHelper.GetPathSegments(context);
                var     segsToEntity = GetEntryUriSegments(segments.Take(segments.Count() - 1), edmxHelper);
                UriType uriType;
                var     target = edmxHelper.GetTargetType(segsToEntity, out uriType);
                entityName = ((EntityType)target).Name;
            }
            return(entityName);
        }
예제 #3
0
        /// <summary>
        /// Checks whether the entity type definition has any property mapping
        /// </summary>
        /// <param name="meta">The metadata document</param>
        /// <param name="entityType">The entity type</param>
        /// <returns>flag of proerty being mapped</returns>
        public static bool HasPropertyMapping(XElement meta, string entityType)
        {
            if (meta == null)
            {
                throw new ArgumentNullException("meta");
            }

            if (string.IsNullOrEmpty(entityType))
            {
                throw new ArgumentException("parameter should not be null or empty", "entityType");
            }

            const string tmplXPath2EntityType = @"//*[local-name()='EntityType' and @Name = '{0}']";
            const string xPath2Property       = @"./*[local-name()='Property' and @m:FC_KeepInContent='false']";

            string typeShortName = ResourcePathHelper.GetBaseName(entityType);

            string xPath2EntityType = string.Format(tmplXPath2EntityType, typeShortName);
            var    nodeEntityType   = meta.XPathSelectElement(xPath2EntityType, ODataNamespaceManager.Instance);
            var    nodeProperty     = nodeEntityType.XPathSelectElement(xPath2Property, ODataNamespaceManager.Instance);

            if (nodeProperty != null)
            {
                return(true);
            }
            else
            {
                string baseType = nodeEntityType.GetAttributeValue("BaseType");
                if (baseType == null)
                {
                    return(false);
                }
                else
                {
                    return(HasPropertyMapping(meta, baseType));
                }
            }
        }
예제 #4
0
        /// <summary>
        /// Gets segments of URI relative path from ServiceContext instance
        /// </summary>
        /// <param name="context">The ServiceContext instance</param>
        /// <returns>The segments of relative path</returns>
        public static IEnumerable <string> GetPathSegments(ServiceContext context)
        {
            var path = context.DestinationBasePath.Substring(context.ServiceBaseUri.AbsoluteUri.Length);

            return(ResourcePathHelper.GetPathSegments(path));
        }
예제 #5
0
        /// <summary>
        /// Builds the uri for purpose of probing any remaining entries satisfying the request of service context
        /// use the last entry's token in the feed as the marker of skiptoken;
        /// and reduce the $top count if top was in context request URI.
        /// </summary>
        /// <param name="context">The service context object</param>
        /// <returns>Uri object if a meaningful prober can be constructed; null otherwise </returns>
        private static Uri ConstructProbeUri(ServiceContext context)
        {
            Uri result = null;

            JObject response = JsonParserHelper.GetResponseObject(context);
            if (response != null)
            {
                JArray entries = JsonParserHelper.GetEntries(response);
                if (entries != null)
                {
                    JObject lastEntry = JsonParserHelper.GetLastEntry(entries);
                    if (lastEntry != null)
                    {
                        string lastToken = JsonParserHelper.GetTokenOfEntry(lastEntry);
                        string lastTokenOfValues = ResourcePathHelper.GetValuesOfKey(lastToken);

                        var uri = context.Destination;
                        ResourcePathHelper pathHelper = new ResourcePathHelper(uri);

                        // replace top value with the reduced value, if $top was in context request
                        string topValue = pathHelper.GetQueryValue("$top");
                        if (!string.IsNullOrEmpty(topValue))
                        {
                            pathHelper.RemoveQueryOption("$top");

                            int entriesGot = entries.Count;
                            int entriesToGet;
                            if (Int32.TryParse(topValue, out entriesToGet) && entriesToGet > entriesGot)
                            {
                                int entriesLeft = entriesToGet - entriesGot;
                                pathHelper.AddQueryOption("$top", entriesLeft.ToString(CultureInfo.InvariantCulture));
                            }
                        }

                        // set up new skiptoken query
                        pathHelper.RemoveQueryOption("$skiptoken");
                        pathHelper.AddQueryOption("$skiptoken", lastTokenOfValues);

                        result = new Uri(pathHelper.Product);
                    }
                }
            }

            return result;
        }
예제 #6
0
        /// <summary>
        /// Builds the uri for purpose of probing the empty feed based on the base uri string.
        /// </summary>
        /// <param name="context">The service context object</param>
        /// <returns>Uri object if a meaningful prober can be constructed; null otherwise </returns>
        private static Uri ConstructProbeUri(ServiceContext context)
        {
            int safetyTopping = 20;
            Uri result = null;

            // find out how many entries in the base feed
            Uri uriFeedCount = new Uri(context.DestinationBasePath + "/$count");
            var resp = WebHelper.Get(uriFeedCount, Constants.AcceptHeaderAtom, RuleEngineSetting.Instance().DefaultMaximumPayloadSize, context.RequestHeaders);
            if (resp.StatusCode.HasValue && resp.StatusCode.Value == System.Net.HttpStatusCode.OK && !string.IsNullOrEmpty(resp.ResponsePayload))
            {
                string payload = resp.ResponsePayload.Trim();
                int count = 0;
                if (Int32.TryParse(payload, out count) && count >= 0)
                {
                    int countToSkip = count + safetyTopping;
                    Uri uriBaseFeed = new Uri(context.DestinationBasePath);
                    ResourcePathHelper pathHelper = new ResourcePathHelper(uriBaseFeed);
                    pathHelper.AddQueryOption("$skip", countToSkip.ToString(CultureInfo.InvariantCulture));

                    result = new Uri(pathHelper.Product);
                }
            }

            return result;
        }