コード例 #1
0
        // Step 2: If the route is a match generate the appropriate URI
        public string BindValues(IDictionary <string, object> acceptedValues)
        {
            var context = new UriBuildingContext();

            for (var i = 0; i < _template.Segments.Count; i++)
            {
                Debug.Assert(context.BufferState == SegmentState.Beginning);
                Debug.Assert(context.UriState == SegmentState.Beginning);

                var segment = _template.Segments[i];

                for (var j = 0; j < segment.Parts.Count; j++)
                {
                    var part = segment.Parts[j];

                    if (part.IsLiteral)
                    {
                        if (!context.Accept(part.Text))
                        {
                            return(null);
                        }
                    }
                    else if (part.IsParameter)
                    {
                        // If it's a parameter, get its value
                        object value;
                        var    hasValue = acceptedValues.TryGetValue(part.Name, out value);
                        if (hasValue)
                        {
                            acceptedValues.Remove(part.Name);
                        }

                        var    isSameAsDefault = false;
                        object defaultValue;
                        if (_defaults != null && _defaults.TryGetValue(part.Name, out defaultValue))
                        {
                            if (RoutePartsEqual(value, defaultValue))
                            {
                                isSameAsDefault = true;
                            }
                        }

                        var converted = Convert.ToString(value, CultureInfo.InvariantCulture);
                        if (isSameAsDefault)
                        {
                            // If the accepted value is the same as the default value buffer it since
                            // we won't necessarily add it to the URI we generate.
                            if (!context.Buffer(converted))
                            {
                                return(null);
                            }
                        }
                        else
                        {
                            // If the value is not accepted, it is null or empty value in the
                            // middle of the segment. We accept this if the parameter is an
                            // optional parameter and it is preceded by an optional seperator.
                            // I this case, we need to remove the optional seperator that we
                            // have added to the URI
                            // Example: template = {id}.{format?}. parameters: id=5
                            // In this case after we have generated "5.", we wont find any value
                            // for format, so we remove '.' and generate 5.
                            if (!context.Accept(converted))
                            {
                                if (j != 0 && part.IsOptional && segment.Parts[j - 1].IsOptionalSeperator)
                                {
                                    context.Remove(segment.Parts[j - 1].Text);
                                }
                                else
                                {
                                    return(null);
                                }
                            }
                        }
                    }
                }

                context.EndSegment();
            }

            // Encode the URI before we append the query string, otherwise we would double encode the query string
            var encoded = new StringBuilder();

            encoded.Append(UriEncode(context.Build()));

            // Generate the query string from the remaining values
            var queryBuilder = new QueryBuilder();

            foreach (var kvp in acceptedValues)
            {
                if (_defaults != null && _defaults.ContainsKey(kvp.Key))
                {
                    // This value is a 'filter' we don't need to put it in the query string.
                    continue;
                }

                var converted = Convert.ToString(kvp.Value, CultureInfo.InvariantCulture);
                if (String.IsNullOrEmpty(converted))
                {
                    continue;
                }

                queryBuilder.Add(kvp.Key, converted);
            }

            encoded.Append(queryBuilder.ToString());
            return(encoded.ToString());
        }
コード例 #2
0
        private string BindValues(UriBuildingContext context, RouteValueDictionary acceptedValues)
        {
            for (var i = 0; i < _template.Segments.Count; i++)
            {
                Debug.Assert(context.BufferState == SegmentState.Beginning);
                Debug.Assert(context.UriState == SegmentState.Beginning);

                var segment = _template.Segments[i];

                for (var j = 0; j < segment.Parts.Count; j++)
                {
                    var part = segment.Parts[j];

                    if (part.IsLiteral)
                    {
                        if (!context.Accept(part.Text))
                        {
                            return(null);
                        }
                    }
                    else if (part.IsParameter)
                    {
                        // If it's a parameter, get its value
                        var hasValue = acceptedValues.TryGetValue(part.Name, out var value);
                        if (hasValue)
                        {
                            acceptedValues.Remove(part.Name);
                        }

                        var isSameAsDefault = false;
                        if (_defaults != null &&
                            _defaults.TryGetValue(part.Name, out var defaultValue) &&
                            RoutePartsEqual(value, defaultValue))
                        {
                            isSameAsDefault = true;
                        }

                        var converted = Convert.ToString(value, CultureInfo.InvariantCulture);
                        if (isSameAsDefault)
                        {
                            // If the accepted value is the same as the default value buffer it since
                            // we won't necessarily add it to the URI we generate.
                            if (!context.Buffer(converted))
                            {
                                return(null);
                            }
                        }
                        else
                        {
                            // If the value is not accepted, it is null or empty value in the
                            // middle of the segment. We accept this if the parameter is an
                            // optional parameter and it is preceded by an optional seperator.
                            // I this case, we need to remove the optional seperator that we
                            // have added to the URI
                            // Example: template = {id}.{format?}. parameters: id=5
                            // In this case after we have generated "5.", we wont find any value
                            // for format, so we remove '.' and generate 5.
                            if (!context.Accept(converted))
                            {
                                if (j != 0 && part.IsOptional && segment.Parts[j - 1].IsOptionalSeperator)
                                {
                                    context.Remove(segment.Parts[j - 1].Text);
                                }
                                else
                                {
                                    return(null);
                                }
                            }
                        }
                    }
                }

                context.EndSegment();
            }

            // Generate the query string from the remaining values
            var wroteFirst = false;

            foreach (var kvp in acceptedValues)
            {
                if (_defaults != null && _defaults.ContainsKey(kvp.Key))
                {
                    // This value is a 'filter' we don't need to put it in the query string.
                    continue;
                }

                var values = kvp.Value as IEnumerable;
                if (values != null && !(values is string))
                {
                    foreach (var value in values)
                    {
                        wroteFirst |= AddParameterToContext(context, kvp.Key, value, wroteFirst);
                    }
                }
                else
                {
                    wroteFirst |= AddParameterToContext(context, kvp.Key, kvp.Value, wroteFirst);
                }
            }
            return(context.ToString());
        }
コード例 #3
0
ファイル: TemplateBinder.cs プロジェクト: Kagamine/Routing
        // Step 2: If the route is a match generate the appropriate URI
        public string BindValues(IDictionary<string, object> acceptedValues)
        {
            var context = new UriBuildingContext();

            for (var i = 0; i < _template.Segments.Count; i++)
            {
                Debug.Assert(context.BufferState == SegmentState.Beginning);
                Debug.Assert(context.UriState == SegmentState.Beginning);

                var segment = _template.Segments[i];

                for (var j = 0; j < segment.Parts.Count; j++)
                {
                    var part = segment.Parts[j];

                    if (part.IsLiteral)
                    {
                        if (!context.Accept(part.Text))
                        {
                            return null;
                        }
                    }
                    else if (part.IsParameter)
                    {
                        // If it's a parameter, get its value
                        object value;
                        var hasValue = acceptedValues.TryGetValue(part.Name, out value);
                        if (hasValue)
                        {
                            acceptedValues.Remove(part.Name);
                        }

                        var isSameAsDefault = false;
                        object defaultValue;
                        if (_defaults != null && _defaults.TryGetValue(part.Name, out defaultValue))
                        {
                            if (RoutePartsEqual(value, defaultValue))
                            {
                                isSameAsDefault = true;
                            }
                        }

                        var converted = Convert.ToString(value, CultureInfo.InvariantCulture);
                        if (isSameAsDefault)
                        {
                            // If the accepted value is the same as the default value buffer it since
                            // we won't necessarily add it to the URI we generate.
                            if (!context.Buffer(converted))
                            {
                                    return null;
                            }
                        }
                        else
                        {
                            // If the value is not accepted, it is null or empty value in the
                            // middle of the segment. We accept this if the parameter is an
                            // optional parameter and it is preceded by an optional seperator.
                            // I this case, we need to remove the optional seperator that we
                            // have added to the URI
                            // Example: template = {id}.{format?}. parameters: id=5
                            // In this case after we have generated "5.", we wont find any value
                            // for format, so we remove '.' and generate 5.
                            if (!context.Accept(converted))
                            {
                                if (j != 0 && part.IsOptional && segment.Parts[j - 1].IsOptionalSeperator)
                                {
                                    context.Remove(segment.Parts[j - 1].Text);
                                }
                                else
                                {
                                    return null;
                                }
                            }
                        }
                    }
                }

                context.EndSegment();
            }

            // Encode the URI before we append the query string, otherwise we would double encode the query string
            var encoded = new StringBuilder();
            encoded.Append(UriEncode(context.Build()));

            // Generate the query string from the remaining values
            var queryBuilder = new QueryBuilder();
            foreach (var kvp in acceptedValues)
            {
                if (_defaults != null && _defaults.ContainsKey(kvp.Key))
                {
                    // This value is a 'filter' we don't need to put it in the query string.
                    continue;
                }

                var converted = Convert.ToString(kvp.Value, CultureInfo.InvariantCulture);
                if (String.IsNullOrEmpty(converted))
                {
                    continue;
                }

                queryBuilder.Add(kvp.Key, converted);
            }

            encoded.Append(queryBuilder.ToString());
            return encoded.ToString();
        }