diff --git a/src/Http/WebUtilities/src/QueryHelpers.cs b/src/Http/WebUtilities/src/QueryHelpers.cs
index c1c23b64e9..a3b13b033c 100644
--- a/src/Http/WebUtilities/src/QueryHelpers.cs
+++ b/src/Http/WebUtilities/src/QueryHelpers.cs
@@ -9,6 +9,9 @@ using Microsoft.Extensions.Primitives;
namespace Microsoft.AspNetCore.WebUtilities
{
+ ///
+ /// Provides methods for parsing and manipulating query strings.
+ ///
public static class QueryHelpers
{
///
@@ -18,6 +21,9 @@ namespace Microsoft.AspNetCore.WebUtilities
/// The name of the query key.
/// The query value.
/// The combined result.
+ /// is null.
+ /// is null.
+ /// is null.
public static string AddQueryString(string uri, string name, string value)
{
if (uri == null)
@@ -45,6 +51,8 @@ namespace Microsoft.AspNetCore.WebUtilities
/// The base uri.
/// A collection of name value query pairs to append.
/// The combined result.
+ /// is null.
+ /// is null.
public static string AddQueryString(string uri, IDictionary queryString)
{
if (uri == null)
@@ -91,6 +99,11 @@ namespace Microsoft.AspNetCore.WebUtilities
sb.Append(uriToBeAppended);
foreach (var parameter in queryString)
{
+ if (parameter.Value == null)
+ {
+ continue;
+ }
+
sb.Append(hasQuery ? '&' : '?');
sb.Append(UrlEncoder.Default.Encode(parameter.Key));
sb.Append('=');
@@ -119,7 +132,6 @@ namespace Microsoft.AspNetCore.WebUtilities
return result;
}
-
///
/// Parse a query string into its component key and value parts.
///
@@ -188,4 +200,4 @@ namespace Microsoft.AspNetCore.WebUtilities
return accumulator.GetResults();
}
}
-}
\ No newline at end of file
+}
diff --git a/src/Http/WebUtilities/test/QueryHelpersTests.cs b/src/Http/WebUtilities/test/QueryHelpersTests.cs
index 5607ab87aa..a64bcbf03b 100644
--- a/src/Http/WebUtilities/test/QueryHelpersTests.cs
+++ b/src/Http/WebUtilities/test/QueryHelpersTests.cs
@@ -1,6 +1,7 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
+using System;
using System.Collections.Generic;
using System.Linq;
using Xunit;
@@ -53,6 +54,12 @@ namespace Microsoft.AspNetCore.WebUtilities
Assert.Equal(new[] { "value1", "" }, collection[""]);
}
+ [Fact]
+ public void AddQueryStringWithNullValueThrows()
+ {
+ Assert.Throws("value" ,() => QueryHelpers.AddQueryString("http://contoso.com/", "hello", null));
+ }
+
[Theory]
[InlineData("http://contoso.com/", "http://contoso.com/?hello=world")]
[InlineData("http://contoso.com/someaction", "http://contoso.com/someaction?hello=world")]
@@ -81,34 +88,36 @@ namespace Microsoft.AspNetCore.WebUtilities
}
[Theory]
- [InlineData("http://contoso.com/", "http://contoso.com/?hello=world&some=text")]
- [InlineData("http://contoso.com/someaction", "http://contoso.com/someaction?hello=world&some=text")]
- [InlineData("http://contoso.com/someaction?q=1", "http://contoso.com/someaction?q=1&hello=world&some=text")]
- [InlineData("http://contoso.com/some#action", "http://contoso.com/some?hello=world&some=text#action")]
- [InlineData("http://contoso.com/some?q=1#action", "http://contoso.com/some?q=1&hello=world&some=text#action")]
- [InlineData("http://contoso.com/#action", "http://contoso.com/?hello=world&some=text#action")]
+ [InlineData("http://contoso.com/", "http://contoso.com/?hello=world&some=text&another=")]
+ [InlineData("http://contoso.com/someaction", "http://contoso.com/someaction?hello=world&some=text&another=")]
+ [InlineData("http://contoso.com/someaction?q=1", "http://contoso.com/someaction?q=1&hello=world&some=text&another=")]
+ [InlineData("http://contoso.com/some#action", "http://contoso.com/some?hello=world&some=text&another=#action")]
+ [InlineData("http://contoso.com/some?q=1#action", "http://contoso.com/some?q=1&hello=world&some=text&another=#action")]
+ [InlineData("http://contoso.com/#action", "http://contoso.com/?hello=world&some=text&another=#action")]
[InlineData(
"http://contoso.com/someaction?q=test#anchor?value",
- "http://contoso.com/someaction?q=test&hello=world&some=text#anchor?value")]
+ "http://contoso.com/someaction?q=test&hello=world&some=text&another=#anchor?value")]
[InlineData(
"http://contoso.com/someaction#anchor?stuff",
- "http://contoso.com/someaction?hello=world&some=text#anchor?stuff")]
+ "http://contoso.com/someaction?hello=world&some=text&another=#anchor?stuff")]
[InlineData(
"http://contoso.com/someaction?name?something",
- "http://contoso.com/someaction?name?something&hello=world&some=text")]
+ "http://contoso.com/someaction?name?something&hello=world&some=text&another=")]
[InlineData(
"http://contoso.com/someaction#name#something",
- "http://contoso.com/someaction?hello=world&some=text#name#something")]
+ "http://contoso.com/someaction?hello=world&some=text&another=#name#something")]
public void AddQueryStringWithDictionary(string uri, string expectedUri)
{
var queryStrings = new Dictionary()
{
{ "hello", "world" },
- { "some", "text" }
+ { "some", "text" },
+ { "another", string.Empty },
+ { "invisible", null }
};
var result = QueryHelpers.AddQueryString(uri, queryStrings);
Assert.Equal(expectedUri, result);
}
}
-}
\ No newline at end of file
+}