Add HttpProtocol (#18049)
This commit is contained in:
parent
337b951c15
commit
df712cc4a9
|
|
@ -100,7 +100,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
if (request.Version == HttpVersion.Version20)
|
if (request.Version == HttpVersion.Version20)
|
||||||
{
|
{
|
||||||
// https://tools.ietf.org/html/rfc7540
|
// https://tools.ietf.org/html/rfc7540
|
||||||
req.Protocol = "HTTP/2";
|
req.Protocol = HttpProtocol.Http2;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -41,7 +41,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
_requestLifetimeFeature = new RequestLifetimeFeature(Abort);
|
_requestLifetimeFeature = new RequestLifetimeFeature(Abort);
|
||||||
|
|
||||||
var request = _httpContext.Request;
|
var request = _httpContext.Request;
|
||||||
request.Protocol = "HTTP/1.1";
|
request.Protocol = HttpProtocol.Http11;
|
||||||
request.Method = HttpMethods.Get;
|
request.Method = HttpMethods.Get;
|
||||||
|
|
||||||
_requestPipe = new Pipe();
|
_requestPipe = new Pipe();
|
||||||
|
|
@ -98,7 +98,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
async Task RunRequestAsync()
|
async Task RunRequestAsync()
|
||||||
{
|
{
|
||||||
// HTTP/2 specific features must be added after the request has been configured.
|
// HTTP/2 specific features must be added after the request has been configured.
|
||||||
if (string.Equals("HTTP/2", _httpContext.Request.Protocol, StringComparison.OrdinalIgnoreCase))
|
if (HttpProtocol.IsHttp2(_httpContext.Request.Protocol))
|
||||||
{
|
{
|
||||||
_httpContext.Features.Set<IHttpResetFeature>(this);
|
_httpContext.Features.Set<IHttpResetFeature>(this);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
Method = "GET";
|
Method = "GET";
|
||||||
Path = "";
|
Path = "";
|
||||||
PathBase = "";
|
PathBase = "";
|
||||||
Protocol = "HTTP/1.1";
|
Protocol = HttpProtocol.Http11;
|
||||||
QueryString = "";
|
QueryString = "";
|
||||||
Scheme = "http";
|
Scheme = "http";
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -27,7 +27,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
var handler = new ClientHandler(new PathString("/A/Path/"), new DummyApplication(context =>
|
var handler = new ClientHandler(new PathString("/A/Path/"), new DummyApplication(context =>
|
||||||
{
|
{
|
||||||
// TODO: Assert.True(context.RequestAborted.CanBeCanceled);
|
// TODO: Assert.True(context.RequestAborted.CanBeCanceled);
|
||||||
Assert.Equal("HTTP/1.1", context.Request.Protocol);
|
Assert.Equal(HttpProtocol.Http11, context.Request.Protocol);
|
||||||
Assert.Equal("GET", context.Request.Method);
|
Assert.Equal("GET", context.Request.Method);
|
||||||
Assert.Equal("https", context.Request.Scheme);
|
Assert.Equal("https", context.Request.Scheme);
|
||||||
Assert.Equal("/A/Path", context.Request.PathBase.Value);
|
Assert.Equal("/A/Path", context.Request.PathBase.Value);
|
||||||
|
|
@ -53,7 +53,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
var handler = new ClientHandler(new PathString("/A/Path/"), new InspectingApplication(features =>
|
var handler = new ClientHandler(new PathString("/A/Path/"), new InspectingApplication(features =>
|
||||||
{
|
{
|
||||||
Assert.True(features.Get<IHttpRequestLifetimeFeature>().RequestAborted.CanBeCanceled);
|
Assert.True(features.Get<IHttpRequestLifetimeFeature>().RequestAborted.CanBeCanceled);
|
||||||
Assert.Equal("HTTP/1.1", features.Get<IHttpRequestFeature>().Protocol);
|
Assert.Equal(HttpProtocol.Http11, features.Get<IHttpRequestFeature>().Protocol);
|
||||||
Assert.Equal("GET", features.Get<IHttpRequestFeature>().Method);
|
Assert.Equal("GET", features.Get<IHttpRequestFeature>().Method);
|
||||||
Assert.Equal("https", features.Get<IHttpRequestFeature>().Scheme);
|
Assert.Equal("https", features.Get<IHttpRequestFeature>().Scheme);
|
||||||
Assert.Equal("/A/Path", features.Get<IHttpRequestFeature>().PathBase);
|
Assert.Equal("/A/Path", features.Get<IHttpRequestFeature>().PathBase);
|
||||||
|
|
|
||||||
|
|
@ -33,7 +33,7 @@ namespace Microsoft.AspNetCore.TestHost
|
||||||
});
|
});
|
||||||
|
|
||||||
Assert.True(context.RequestAborted.CanBeCanceled);
|
Assert.True(context.RequestAborted.CanBeCanceled);
|
||||||
Assert.Equal("HTTP/1.1", context.Request.Protocol);
|
Assert.Equal(HttpProtocol.Http11, context.Request.Protocol);
|
||||||
Assert.Equal("POST", context.Request.Method);
|
Assert.Equal("POST", context.Request.Method);
|
||||||
Assert.Equal("https", context.Request.Scheme);
|
Assert.Equal("https", context.Request.Scheme);
|
||||||
Assert.Equal("example.com", context.Request.Host.Value);
|
Assert.Equal("example.com", context.Request.Host.Value);
|
||||||
|
|
|
||||||
|
|
@ -250,6 +250,18 @@ namespace Microsoft.AspNetCore.Http
|
||||||
public static bool IsPut(string method) { throw null; }
|
public static bool IsPut(string method) { throw null; }
|
||||||
public static bool IsTrace(string method) { throw null; }
|
public static bool IsTrace(string method) { throw null; }
|
||||||
}
|
}
|
||||||
|
public static partial class HttpProtocol
|
||||||
|
{
|
||||||
|
public static readonly string Http10;
|
||||||
|
public static readonly string Http11;
|
||||||
|
public static readonly string Http2;
|
||||||
|
public static readonly string Http3;
|
||||||
|
public static string GetHttpProtocol(System.Version version) { throw null; }
|
||||||
|
public static bool IsHttp10(string protocol) { throw null; }
|
||||||
|
public static bool IsHttp11(string protocol) { throw null; }
|
||||||
|
public static bool IsHttp2(string protocol) { throw null; }
|
||||||
|
public static bool IsHttp3(string protocol) { throw null; }
|
||||||
|
}
|
||||||
public abstract partial class HttpRequest
|
public abstract partial class HttpRequest
|
||||||
{
|
{
|
||||||
protected HttpRequest() { }
|
protected HttpRequest() { }
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,96 @@
|
||||||
|
// 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;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNetCore.Http
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Contains methods to verify the request protocol version of an HTTP request.
|
||||||
|
/// </summary>
|
||||||
|
public static class HttpProtocol
|
||||||
|
{
|
||||||
|
// We are intentionally using 'static readonly' here instead of 'const'.
|
||||||
|
// 'const' values would be embedded into each assembly that used them
|
||||||
|
// and each consuming assembly would have a different 'string' instance.
|
||||||
|
// Using .'static readonly' means that all consumers get these exact same
|
||||||
|
// 'string' instance, which means the 'ReferenceEquals' checks below work
|
||||||
|
// and allow us to optimize comparisons when these constants are used.
|
||||||
|
|
||||||
|
// Please do NOT change these to 'const'
|
||||||
|
public static readonly string Http10 = "HTTP/1.0";
|
||||||
|
public static readonly string Http11 = "HTTP/1.1";
|
||||||
|
public static readonly string Http2 = "HTTP/2";
|
||||||
|
public static readonly string Http3 = "HTTP/3";
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns a value that indicates if the HTTP request protocol is HTTP/1.0.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="protocol">The HTTP request protocol.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// <see langword="true" /> if the protocol is HTTP/1.0; otherwise, <see langword="false" />.
|
||||||
|
/// </returns>
|
||||||
|
public static bool IsHttp10(string protocol)
|
||||||
|
{
|
||||||
|
return object.ReferenceEquals(Http10, protocol) || StringComparer.OrdinalIgnoreCase.Equals(Http10, protocol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns a value that indicates if the HTTP request protocol is HTTP/1.1.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="protocol">The HTTP request protocol.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// <see langword="true" /> if the protocol is HTTP/1.1; otherwise, <see langword="false" />.
|
||||||
|
/// </returns>
|
||||||
|
public static bool IsHttp11(string protocol)
|
||||||
|
{
|
||||||
|
return object.ReferenceEquals(Http11, protocol) || StringComparer.OrdinalIgnoreCase.Equals(Http11, protocol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns a value that indicates if the HTTP request protocol is HTTP/2.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="protocol">The HTTP request protocol.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// <see langword="true" /> if the protocol is HTTP/2; otherwise, <see langword="false" />.
|
||||||
|
/// </returns>
|
||||||
|
public static bool IsHttp2(string protocol)
|
||||||
|
{
|
||||||
|
return object.ReferenceEquals(Http2, protocol) || StringComparer.OrdinalIgnoreCase.Equals(Http2, protocol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns a value that indicates if the HTTP request protocol is HTTP/3.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="protocol">The HTTP request protocol.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// <see langword="true" /> if the protocol is HTTP/3; otherwise, <see langword="false" />.
|
||||||
|
/// </returns>
|
||||||
|
public static bool IsHttp3(string protocol)
|
||||||
|
{
|
||||||
|
return object.ReferenceEquals(Http3, protocol) || StringComparer.OrdinalIgnoreCase.Equals(Http3, protocol);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets the HTTP request protocol for the specified <see cref="Version"/>.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="version">The version.</param>
|
||||||
|
/// <returns>A HTTP request protocol.</returns>
|
||||||
|
public static string GetHttpProtocol(Version version)
|
||||||
|
{
|
||||||
|
if (version == null)
|
||||||
|
{
|
||||||
|
throw new ArgumentNullException(nameof(version));
|
||||||
|
}
|
||||||
|
|
||||||
|
return version switch
|
||||||
|
{
|
||||||
|
{ Major: 3, Minor: 0 } => Http3,
|
||||||
|
{ Major: 2, Minor: 0 } => Http2,
|
||||||
|
{ Major: 1, Minor: 1 } => Http11,
|
||||||
|
{ Major: 1, Minor: 0 } => Http10,
|
||||||
|
_ => throw new ArgumentOutOfRangeException(nameof(version), "Version doesn't map to a known HTTP protocol.")
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,117 @@
|
||||||
|
// 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 Xunit;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNetCore.Http.Abstractions
|
||||||
|
{
|
||||||
|
public class HttpProtocolTests
|
||||||
|
{
|
||||||
|
[Fact]
|
||||||
|
public void Http3_Success()
|
||||||
|
{
|
||||||
|
Assert.Equal("HTTP/3", HttpProtocol.Http3);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("HTTP/3", true)]
|
||||||
|
[InlineData("http/3", true)]
|
||||||
|
[InlineData("HTTP/1.1", false)]
|
||||||
|
[InlineData("HTTP/3.0", false)]
|
||||||
|
[InlineData("HTTP/1", false)]
|
||||||
|
[InlineData(" HTTP/3", false)]
|
||||||
|
[InlineData("HTTP/3 ", false)]
|
||||||
|
public void IsHttp3_Success(string protocol, bool match)
|
||||||
|
{
|
||||||
|
Assert.Equal(match, HttpProtocol.IsHttp3(protocol));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Http2_Success()
|
||||||
|
{
|
||||||
|
Assert.Equal("HTTP/2", HttpProtocol.Http2);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("HTTP/2", true)]
|
||||||
|
[InlineData("http/2", true)]
|
||||||
|
[InlineData("HTTP/1.1", false)]
|
||||||
|
[InlineData("HTTP/2.0", false)]
|
||||||
|
[InlineData("HTTP/1", false)]
|
||||||
|
[InlineData(" HTTP/2", false)]
|
||||||
|
[InlineData("HTTP/2 ", false)]
|
||||||
|
public void IsHttp2_Success(string protocol, bool match)
|
||||||
|
{
|
||||||
|
Assert.Equal(match, HttpProtocol.IsHttp2(protocol));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Http11_Success()
|
||||||
|
{
|
||||||
|
Assert.Equal("HTTP/1.1", HttpProtocol.Http11);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("HTTP/1.1", true)]
|
||||||
|
[InlineData("http/1.1", true)]
|
||||||
|
[InlineData("HTTP/2", false)]
|
||||||
|
[InlineData("HTTP/1.0", false)]
|
||||||
|
[InlineData("HTTP/1", false)]
|
||||||
|
[InlineData(" HTTP/1.1", false)]
|
||||||
|
[InlineData("HTTP/1.1 ", false)]
|
||||||
|
public void IsHttp11_Success(string protocol, bool match)
|
||||||
|
{
|
||||||
|
Assert.Equal(match, HttpProtocol.IsHttp11(protocol));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Http10_Success()
|
||||||
|
{
|
||||||
|
Assert.Equal("HTTP/1.0", HttpProtocol.Http10);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("HTTP/1.0", true)]
|
||||||
|
[InlineData("http/1.0", true)]
|
||||||
|
[InlineData("HTTP/2", false)]
|
||||||
|
[InlineData("HTTP/1.1", false)]
|
||||||
|
[InlineData("HTTP/1", false)]
|
||||||
|
[InlineData(" HTTP/1.0", false)]
|
||||||
|
[InlineData("HTTP/1.0 ", false)]
|
||||||
|
public void IsHttp10_Success(string protocol, bool match)
|
||||||
|
{
|
||||||
|
Assert.Equal(match, HttpProtocol.IsHttp10(protocol));
|
||||||
|
}
|
||||||
|
|
||||||
|
public static TheoryData<Version, string> s_ValidData = new TheoryData<Version, string>
|
||||||
|
{
|
||||||
|
{ new Version(3, 0), "HTTP/3" },
|
||||||
|
{ new Version(2, 0), "HTTP/2" },
|
||||||
|
{ new Version(1, 1), "HTTP/1.1" },
|
||||||
|
{ new Version(1, 0), "HTTP/1.0" }
|
||||||
|
};
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[MemberData(nameof(s_ValidData))]
|
||||||
|
public void GetHttpProtocol_CorrectIETFVersion(Version version, string expected)
|
||||||
|
{
|
||||||
|
var actual = HttpProtocol.GetHttpProtocol(version);
|
||||||
|
|
||||||
|
Assert.Equal(expected, actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static TheoryData<Version> s_InvalidData = new TheoryData<Version>
|
||||||
|
{
|
||||||
|
{ new Version(0, 3) },
|
||||||
|
{ new Version(2, 1) }
|
||||||
|
};
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[MemberData(nameof(s_InvalidData))]
|
||||||
|
public void GetHttpProtocol_ThrowErrorForUnknownVersion(Version version)
|
||||||
|
{
|
||||||
|
Assert.Throws<ArgumentOutOfRangeException>(() => HttpProtocol.GetHttpProtocol(version));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -57,7 +57,7 @@ namespace Microsoft.AspNetCore.Authentication.Negotiate
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
protected override Task<object> CreateEventsAsync() => Task.FromResult<object>(new NegotiateEvents());
|
protected override Task<object> CreateEventsAsync() => Task.FromResult<object>(new NegotiateEvents());
|
||||||
|
|
||||||
private bool IsHttp2 => string.Equals("HTTP/2", Request.Protocol, StringComparison.OrdinalIgnoreCase);
|
private bool IsSupportedProtocol => HttpProtocol.IsHttp11(Request.Protocol) || HttpProtocol.IsHttp10(Request.Protocol);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Intercepts incomplete Negotiate authentication handshakes and continues or completes them.
|
/// Intercepts incomplete Negotiate authentication handshakes and continues or completes them.
|
||||||
|
|
@ -80,10 +80,10 @@ namespace Microsoft.AspNetCore.Authentication.Negotiate
|
||||||
|
|
||||||
_requestProcessed = true;
|
_requestProcessed = true;
|
||||||
|
|
||||||
if (IsHttp2)
|
if (!IsSupportedProtocol)
|
||||||
{
|
{
|
||||||
// HTTP/2 is not supported. Do not throw because this may be running on a server that supports
|
// HTTP/1.0 and HTTP/1.1 are supported. Do not throw because this may be running on a server that supports
|
||||||
// both HTTP/1 and HTTP/2.
|
// additional protocols.
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -291,7 +291,7 @@ namespace Microsoft.AspNetCore.Authentication.Negotiate
|
||||||
throw new InvalidOperationException("AuthenticateAsync must not be called before the UseAuthentication middleware runs.");
|
throw new InvalidOperationException("AuthenticateAsync must not be called before the UseAuthentication middleware runs.");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (IsHttp2)
|
if (!IsSupportedProtocol)
|
||||||
{
|
{
|
||||||
// Not supported. We don't throw because Negotiate may be set as the default auth
|
// Not supported. We don't throw because Negotiate may be set as the default auth
|
||||||
// handler on a server that's running HTTP/1 and HTTP/2. We'll challenge HTTP/2 requests
|
// handler on a server that's running HTTP/1 and HTTP/2. We'll challenge HTTP/2 requests
|
||||||
|
|
|
||||||
|
|
@ -181,7 +181,7 @@ namespace Microsoft.AspNetCore.Server.HttpSys
|
||||||
{
|
{
|
||||||
if (IsNotInitialized(Fields.Protocol))
|
if (IsNotInitialized(Fields.Protocol))
|
||||||
{
|
{
|
||||||
_httpProtocolVersion = Request.ProtocolVersion.GetHttpProtocolVersion();
|
_httpProtocolVersion = HttpProtocol.GetHttpProtocol(Request.ProtocolVersion);
|
||||||
SetInitialized(Fields.Protocol);
|
SetInitialized(Fields.Protocol);
|
||||||
}
|
}
|
||||||
return _httpProtocolVersion;
|
return _httpProtocolVersion;
|
||||||
|
|
|
||||||
|
|
@ -87,7 +87,7 @@ namespace Microsoft.AspNetCore.Server.IIS.Core
|
||||||
|
|
||||||
string IHttpRequestFeature.Protocol
|
string IHttpRequestFeature.Protocol
|
||||||
{
|
{
|
||||||
get => _httpProtocolVersion ??= HttpVersion.GetHttpProtocolVersion();
|
get => _httpProtocolVersion ??= HttpProtocol.GetHttpProtocol(HttpVersion);
|
||||||
set => _httpProtocolVersion = value;
|
set => _httpProtocolVersion = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -146,21 +146,21 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
{
|
{
|
||||||
if (_httpVersion == Http.HttpVersion.Http11)
|
if (_httpVersion == Http.HttpVersion.Http3)
|
||||||
{
|
{
|
||||||
return HttpUtilities.Http11Version;
|
return AspNetCore.Http.HttpProtocol.Http3;
|
||||||
}
|
|
||||||
if (_httpVersion == Http.HttpVersion.Http10)
|
|
||||||
{
|
|
||||||
return HttpUtilities.Http10Version;
|
|
||||||
}
|
}
|
||||||
if (_httpVersion == Http.HttpVersion.Http2)
|
if (_httpVersion == Http.HttpVersion.Http2)
|
||||||
{
|
{
|
||||||
return HttpUtilities.Http2Version;
|
return AspNetCore.Http.HttpProtocol.Http2;
|
||||||
}
|
}
|
||||||
if (_httpVersion == Http.HttpVersion.Http3)
|
if (_httpVersion == Http.HttpVersion.Http11)
|
||||||
{
|
{
|
||||||
return HttpUtilities.Http3Version;
|
return AspNetCore.Http.HttpProtocol.Http11;
|
||||||
|
}
|
||||||
|
if (_httpVersion == Http.HttpVersion.Http10)
|
||||||
|
{
|
||||||
|
return AspNetCore.Http.HttpProtocol.Http10;
|
||||||
}
|
}
|
||||||
|
|
||||||
return string.Empty;
|
return string.Empty;
|
||||||
|
|
@ -171,21 +171,21 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http
|
||||||
{
|
{
|
||||||
// GetKnownVersion returns versions which ReferenceEquals interned string
|
// GetKnownVersion returns versions which ReferenceEquals interned string
|
||||||
// As most common path, check for this only in fast-path and inline
|
// As most common path, check for this only in fast-path and inline
|
||||||
if (ReferenceEquals(value, HttpUtilities.Http11Version))
|
if (ReferenceEquals(value, AspNetCore.Http.HttpProtocol.Http3))
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http11;
|
_httpVersion = Http.HttpVersion.Http3;
|
||||||
}
|
}
|
||||||
else if (ReferenceEquals(value, HttpUtilities.Http10Version))
|
else if (ReferenceEquals(value, AspNetCore.Http.HttpProtocol.Http2))
|
||||||
{
|
|
||||||
_httpVersion = Http.HttpVersion.Http10;
|
|
||||||
}
|
|
||||||
else if (ReferenceEquals(value, HttpUtilities.Http2Version))
|
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http2;
|
_httpVersion = Http.HttpVersion.Http2;
|
||||||
}
|
}
|
||||||
else if (ReferenceEquals(value, HttpUtilities.Http3Version))
|
else if (ReferenceEquals(value, AspNetCore.Http.HttpProtocol.Http11))
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http3;
|
_httpVersion = Http.HttpVersion.Http11;
|
||||||
|
}
|
||||||
|
else if (ReferenceEquals(value, AspNetCore.Http.HttpProtocol.Http10))
|
||||||
|
{
|
||||||
|
_httpVersion = Http.HttpVersion.Http10;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
@ -197,21 +197,21 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http
|
||||||
[MethodImpl(MethodImplOptions.NoInlining)]
|
[MethodImpl(MethodImplOptions.NoInlining)]
|
||||||
private void HttpVersionSetSlow(string value)
|
private void HttpVersionSetSlow(string value)
|
||||||
{
|
{
|
||||||
if (value == HttpUtilities.Http11Version)
|
if (AspNetCore.Http.HttpProtocol.IsHttp3(value))
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http11;
|
_httpVersion = Http.HttpVersion.Http3;
|
||||||
}
|
}
|
||||||
else if (value == HttpUtilities.Http10Version)
|
else if (AspNetCore.Http.HttpProtocol.IsHttp2(value))
|
||||||
{
|
|
||||||
_httpVersion = Http.HttpVersion.Http10;
|
|
||||||
}
|
|
||||||
else if (value == HttpUtilities.Http2Version)
|
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http2;
|
_httpVersion = Http.HttpVersion.Http2;
|
||||||
}
|
}
|
||||||
else if (value == HttpUtilities.Http3Version)
|
else if (AspNetCore.Http.HttpProtocol.IsHttp11(value))
|
||||||
{
|
{
|
||||||
_httpVersion = Http.HttpVersion.Http3;
|
_httpVersion = Http.HttpVersion.Http11;
|
||||||
|
}
|
||||||
|
else if (AspNetCore.Http.HttpProtocol.IsHttp10(value))
|
||||||
|
{
|
||||||
|
_httpVersion = Http.HttpVersion.Http10;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -12,11 +12,6 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Infrastructure
|
||||||
{
|
{
|
||||||
internal static partial class HttpUtilities
|
internal static partial class HttpUtilities
|
||||||
{
|
{
|
||||||
public const string Http10Version = "HTTP/1.0";
|
|
||||||
public const string Http11Version = "HTTP/1.1";
|
|
||||||
public const string Http2Version = "HTTP/2";
|
|
||||||
public const string Http3Version = "HTTP/3";
|
|
||||||
|
|
||||||
public const string HttpUriScheme = "http://";
|
public const string HttpUriScheme = "http://";
|
||||||
public const string HttpsUriScheme = "https://";
|
public const string HttpsUriScheme = "https://";
|
||||||
|
|
||||||
|
|
@ -429,13 +424,22 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Infrastructure
|
||||||
|
|
||||||
public static string VersionToString(HttpVersion httpVersion)
|
public static string VersionToString(HttpVersion httpVersion)
|
||||||
{
|
{
|
||||||
return httpVersion switch
|
switch (httpVersion)
|
||||||
{
|
{
|
||||||
HttpVersion.Http10 => Http10Version,
|
case HttpVersion.Http10:
|
||||||
HttpVersion.Http11 => Http11Version,
|
return AspNetCore.Http.HttpProtocol.Http10;
|
||||||
_ => null,
|
case HttpVersion.Http11:
|
||||||
|
return AspNetCore.Http.HttpProtocol.Http11;
|
||||||
|
case HttpVersion.Http2:
|
||||||
|
return AspNetCore.Http.HttpProtocol.Http2;
|
||||||
|
case HttpVersion.Http3:
|
||||||
|
return AspNetCore.Http.HttpProtocol.Http3;
|
||||||
|
default:
|
||||||
|
Debug.Fail("Unexpected HttpVersion: " + httpVersion);
|
||||||
|
return null;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public static string MethodToString(HttpMethod method)
|
public static string MethodToString(HttpMethod method)
|
||||||
{
|
{
|
||||||
var methodIndex = (int)method;
|
var methodIndex = (int)method;
|
||||||
|
|
|
||||||
|
|
@ -52,8 +52,8 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
|
||||||
}
|
}
|
||||||
|
|
||||||
[Theory]
|
[Theory]
|
||||||
[InlineData("HTTP/1.0\r", true, HttpUtilities.Http10Version, (int)HttpVersion.Http10)]
|
[InlineData("HTTP/1.0\r", true, "HTTP/1.0", (int)HttpVersion.Http10)]
|
||||||
[InlineData("HTTP/1.1\r", true, HttpUtilities.Http11Version, (int)HttpVersion.Http11)]
|
[InlineData("HTTP/1.1\r", true, "HTTP/1.1", (int)HttpVersion.Http11)]
|
||||||
[InlineData("HTTP/3.0\r", false, null, (int)HttpVersion.Unknown)]
|
[InlineData("HTTP/3.0\r", false, null, (int)HttpVersion.Unknown)]
|
||||||
[InlineData("http/1.0\r", false, null, (int)HttpVersion.Unknown)]
|
[InlineData("http/1.0\r", false, null, (int)HttpVersion.Unknown)]
|
||||||
[InlineData("http/1.1\r", false, null, (int)HttpVersion.Unknown)]
|
[InlineData("http/1.1\r", false, null, (int)HttpVersion.Unknown)]
|
||||||
|
|
|
||||||
|
|
@ -184,7 +184,7 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Transport.Libuv.Tests
|
||||||
return context.Response.WriteAsync("Hello World");
|
return context.Response.WriteAsync("Hello World");
|
||||||
});
|
});
|
||||||
|
|
||||||
listenOptions.UseHttpServer(serviceContext, testApplication, HttpProtocols.Http1);
|
listenOptions.UseHttpServer(serviceContext, testApplication, Core.HttpProtocols.Http1);
|
||||||
|
|
||||||
var transportContext = new TestLibuvTransportContext
|
var transportContext = new TestLibuvTransportContext
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
// Copyright (c) .NET Foundation. All rights reserved.
|
// 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.
|
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
|
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
||||||
// 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;
|
|
||||||
|
|
||||||
namespace Microsoft.AspNetCore.HttpSys.Internal
|
|
||||||
{
|
|
||||||
internal static class Extensions
|
|
||||||
{
|
|
||||||
public static string GetHttpProtocolVersion(this Version version) => version switch
|
|
||||||
{
|
|
||||||
{ Major: 2, Minor: 0 } => "HTTP/2",
|
|
||||||
{ Major: 1, Minor: 1 } => "HTTP/1.1",
|
|
||||||
{ Major: 1, Minor: 0 } => "HTTP/1.0",
|
|
||||||
_ => "HTTP/" + version.ToString(2)
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
@ECHO OFF
|
||||||
|
|
||||||
|
%~dp0..\..\startvs.cmd %~dp0Shared.sln
|
||||||
|
|
@ -1,29 +0,0 @@
|
||||||
// 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 Xunit;
|
|
||||||
|
|
||||||
namespace Microsoft.AspNetCore.HttpSys.Internal
|
|
||||||
{
|
|
||||||
public class HttpSysGetHttpProtocolVersionTest
|
|
||||||
{
|
|
||||||
public static TheoryData<Version, string> s_data = new TheoryData<Version, string>
|
|
||||||
{
|
|
||||||
{ new Version(2, 0), "HTTP/2" },
|
|
||||||
{ new Version(1, 1), "HTTP/1.1" },
|
|
||||||
{ new Version(1, 0), "HTTP/1.0" },
|
|
||||||
{ new Version(0, 3), "HTTP/0.3" },
|
|
||||||
{ new Version(2, 1), "HTTP/2.1" }
|
|
||||||
};
|
|
||||||
|
|
||||||
[Theory]
|
|
||||||
[MemberData(nameof(s_data))]
|
|
||||||
public void GetHttpProtocolVersion_CorrectIETFVersion(Version version, string expected)
|
|
||||||
{
|
|
||||||
var actual = version.GetHttpProtocolVersion();
|
|
||||||
|
|
||||||
Assert.Equal(expected, actual);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Loading…
Reference in New Issue