예제 #1
0
        internal Func <HttpRequestMessage, Task <HttpResponseMessage> > GetIfMatchNoneMatch()
        {
            return((request) =>
            {
                if (request.Method != HttpMethod.Get)
                {
                    return null;
                }

                ICollection <EntityTagHeaderValue> noneMatchTags = request.Headers.IfNoneMatch;
                ICollection <EntityTagHeaderValue> matchTags = request.Headers.IfMatch;

                if (matchTags.Count == 0 && noneMatchTags.Count == 0)
                {
                    return null; // no etag
                }

                if (matchTags.Count > 0 && noneMatchTags.Count > 0) // both if-match and if-none-match exist
                {
                    return new HttpResponseMessage(HttpStatusCode.BadRequest).ToTask();
                }

                bool isNoneMatch = noneMatchTags.Count > 0;
                ICollection <EntityTagHeaderValue> etags = isNoneMatch ? noneMatchTags : matchTags;

                string resource = UriTrimmer(request.RequestUri);
                IEnumerable <KeyValuePair <string, IEnumerable <string> > > headers =
                    request.Headers.Where(h => _varyByHeaders.Any(v => v.Equals(h.Key, StringComparison.CurrentCultureIgnoreCase)));
                EntityTagKey entityTagKey = EntityTagKeyGenerator(resource, headers);
                // compare the Etag with the one in the cache
                // do conditional get.
                TimedEntityTagHeaderValue actualEtag = null;

                bool matchFound = false;
                if (_entityTagStore.TryGetValue(entityTagKey, out actualEtag))
                {
                    if (etags.Any(etag => etag.Tag == actualEtag.Tag))
                    {
                        matchFound = true;
                    }
                }
                return matchFound ^ isNoneMatch ? null : new NotModifiedResponse(actualEtag.ToEntityTagHeaderValue()).ToTask();
            });
        }