LAB02-Research / HASS.Agent

Windows-based client for Home Assistant. Provides notifications, quick actions, commands, sensors and more.
https://hassagent.lab02-research.org
MIT License
1.6k stars 74 forks source link

Feature: Add support for TLS 1.3 #283

Open Gunni opened 1 year ago

Gunni commented 1 year ago

Is your feature request related to a problem? Please describe. I have a reverse proxy in front of my Home Assistant server. It only allows TLS 1.3.

This applications fails with this error when connecting: Authentication failed because the remote party sent a TLS alert: 'ProtocolVersion'.

Note that the error in the UI is plainly incorrect...

image

Describe the solution you'd like Follow the Transport Layer Security (TLS) best practices with the .NET Framework. Especially: For TLS 1.3, target .NET Framework 4.8 or later.

Describe alternatives you've considered Connecting insecurely? No thanks.

Additional context Fix the error to be a better error.

Full exception from log

2023-02-28 20:10:05.445 +00:00 [FTL] [HASS_API] Error while checking config: The SSL connection could not be established, see inner exception.
System.Net.Http.HttpRequestException: The SSL connection could not be established, see inner exception.
 ---> System.Security.Authentication.AuthenticationException: Authentication failed because the remote party sent a TLS alert: 'ProtocolVersion'.
 ---> System.ComponentModel.Win32Exception (0x80090326): The message received was unexpected or badly formatted.
   --- End of inner exception stack trace ---
   at System.Net.Security.SslStream.ForceAuthenticationAsync[TIOAdapter](TIOAdapter adapter, Boolean receiveFirst, Byte[] reAuthenticationData, Boolean isApm)
   at System.Net.Http.ConnectHelper.EstablishSslConnectionAsync(SslClientAuthenticationOptions sslOptions, HttpRequestMessage request, Boolean async, Stream stream, CancellationToken cancellationToken)
   --- End of inner exception stack trace ---
   at System.Net.Http.ConnectHelper.EstablishSslConnectionAsync(SslClientAuthenticationOptions sslOptions, HttpRequestMessage request, Boolean async, Stream stream, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.ConnectAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.CreateHttp11ConnectionAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.AddHttp11ConnectionAsync(HttpRequestMessage request)
   at System.Threading.Tasks.TaskCompletionSourceWithCancellation`1.WaitWithCancellationAsync(CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.GetHttp11ConnectionAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.SendWithVersionDetectionAndRetryAsync(HttpRequestMessage request, Boolean async, Boolean doRequestAuth, CancellationToken cancellationToken)
   at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
   at System.Net.Http.HttpClient.<SendAsync>g__Core|83_0(HttpRequestMessage request, HttpCompletionOption completionOption, CancellationTokenSource cts, Boolean disposeCts, CancellationTokenSource pendingRequestsCts, CancellationToken originalCancellationToken)
   at HADotNet.Core.BaseClient.Get[T](String path)
   at HADotNet.Core.Clients.ConfigClient.GetConfiguration()
   at HASS.Agent.HomeAssistant.HassApiManager.CheckHassConfigAsync(String uri, String apiKey, Boolean automaticClientCertificate, Boolean allowUntrustedCertificates, String clientCertificate)
Flightkick commented 1 year ago

What could be solved in this project

The error message doesn't give too many details as to why the connection is actually failing, this could be improved.

What is happening

The underlying issue seems to be caused by limited support for TLS1.3 in Microsoft Windows. Looking at the docs you linked^1:

For TLS 1.3, target .NET Framework 4.8 or later.

This project seems to target a much higher .NET version. https://github.com/LAB02-Research/HASS.Agent/blob/08310c474780107f63053cf02ce52f80e49408cb/src/HASS.Agent/HASS.Agent.csproj#L5C15-L5C15

However, it seems that the TLS1.3 configuration is only supported from Windows 11 and Windows Server 2022^2. Other languages and frameworks do support TLS1.3 on earlier platforms as they're not dependent on Schannel SSP.

Alternatives to consider

Instead of connecting insecurely you could lax the minimum supported TLS version on your reverse proxy to TLS1.2. Just to quote a source on this, the IT Security Guidelines for Transport Layer Security from the Dutch National Cyber Security Centre (NCSC) currently state that the use of TLS1.2 is sufficient^3. Make sure to validate that only secure algorithms are allowed.