提问人:IMSsam 提问时间:11/15/2023 更新时间:11/16/2023 访问量:90
如何查看传入 API 请求的 TLS 版本 - ASP.NET
How can I see the TLS version of an incoming API request - ASP.NET
问:
我在 Microsoft Azure 上托管了一个包含 Web API 的 Web 应用。我的目标是 .NET Framework 4.5。
我正在完成所有必需的步骤,以使TLS 1.2成为传入请求所需的最低版本。
在我正式切换到传入请求的 TLS 1.2 最低版本之前,我想知道是否有人当前正在使用较旧的 TLS 版本,因为我们有第三方使用我们的 API。
有没有办法检测在特定 API 请求中协商的 TLS 版本?
例如,我在下面有这个 API 调用。我可以使用 .NET Framework 4.5 编写哪些代码来获取协商的 TLS 版本?
[HttpGet]
[Authorize(Roles = "User")]
public HttpResponseMessage GetFirstName()
{
// I would like to add code here to get TLS version negotiated so I can log it
var email = User.Identity.GetUserName();
ApplicationUser userFound = GetUserByEmail(email);
if (userFound == null)
{
return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Error: No such user.");
}
var firstName = new { FirstName = userFound.FirstName };
return Request.CreateResponse(HttpStatusCode.OK, firstName);
}
我知道我最终需要完全升级 .NET Framework,但我需要在 4.5 上快速解决该问题。
答:
0赞
Suresh Chikkam
11/15/2023
#1
当然,Panagiotis Kanavos 的观点是有效的。升级到受支持的 .NET Framework 版本(如 4.6.2 或更高版本)可能会有更多帮助。
正如您可以在 MS 文档中查看的那样,如果您使用的是 4.5v,则需要升级到最新版本。
我已经尝试了较新版本的 .NET Framework 4.6.1。我可以直接从类中访问 TLS 版本信息。SslStream
using System;
using System.Net.Http;
using System.Net.Http.Formatting;
using System.Net.Http.Headers;
using System.Threading.Tasks;
using System.Web.Http;
namespace YourNamespace.Controllers
{
public class YourController : ApiController
{
[HttpGet]
public async Task<HttpResponseMessage> Get()
{
await LogNegotiatedTLSVersion(Request);
// Your existing code here
return new HttpResponseMessage()
{
Content = new ObjectContent<string>("Hello, World!", new JsonMediaTypeFormatter()),
};
}
private async Task LogNegotiatedTLSVersion(HttpRequestMessage request)
{
object property;
if (request.Properties.TryGetValue("MS_HttpContext", out property))
{
var context = (System.Web.HttpContextWrapper)property;
var stream = context.Response.Filter as System.Web.HttpBufferedOutputStream;
if (stream != null)
{
var sslStreamField = stream.GetType().GetField("_sslStream", System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic);
var sslStream = sslStreamField?.GetValue(stream) as System.Net.Security.SslStream;
if (sslStream != null)
{
// Log the negotiated TLS version
Console.WriteLine($"Negotiated TLS version: {sslStream.SslProtocol}");
}
}
}
}
}
}
- 该属性用于获取协商的 TLS 版本。调用该方法对连接的服务器端进行身份验证。
SslStream.SslProtocol
AuthenticateAsServer
评论
0赞
IMSsam
11/16/2023
我尝试了您的解决方案,但我被卡住了,因为我的 Request 对象是 HttpRequestMessage,而不是 HttpRequest。您知道利用 HttpRequestMessage 获得相同结果的方法吗?
0赞
Suresh Chikkam
11/16/2023
@IMSsam 您仍然可以提取 TLS 信息,但需要使用 HttpRequestMessage.Properties 字典来访问基础 SslStream 并检索 TLS 版本。请查看我更新的答案。
评论
System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;