ERR_SSL_PROTOCOL_ERROR генерируется с использованием сертификата X509 с хостингом Kestrel в .NET 8 в Linux

В настоящее время я работаю над обновлением приложения C#/.NET с .NET 6.0 до .NET 8.0 на виртуальной машине Linux (я работаю на ПК), и у меня возникли некоторые проблемы с работой конечных точек HTTPS. Я наткнулся на эту статью, когда искал решения, но я не на 100% уверен, что это действительно проблема, а если это так, то я не знаю, как ее исправить :). Я извлекаю пару X509Certificate2 crt/ключ из локальной файловой системы и использую ее для создания IHostBuilder объекта, использующего HTTPS. Ниже приведен текущий код, с которым я работаю:

var certContents = File.ReadAllText(<local filepath>);
var certKeyContents = File.ReadAllText(<local key filepath>);
var cert = X509Certificate2.CreateFromPem(certContents, certKeyContents);

return Host.CreateDefaultBuilder(args)
    .UseServiceProviderFactory(new AutofacServiceProviderFactory())
    .ConfigureWebHostDefaults(webBuilder =>
    {
        webBuilder
            .UseContentRoot(Directory.GetCurrentDirectory())
            .UseKestrel(options =>
            {
                options.AddServerHeader = false;
                options.Listen(IPAddress.Any, port, ops =>
                {
                    ops.UseHttps(cert);
                }); 
            }
        })
        .UseStartup<Startup>();
    })
    .ConfigureLogging(logging => 
    {
    })
    .UseNLog();

Результатом этого обычно является страница с ошибкой, на которой просто отображается сообщение «Этот сайт не может обеспечить безопасное соединение». Для тестирования этих вызовов я в основном использовал Google Chrome v122.0 и Postman v9.31. Я установил точки останова в коде, и кажется, что я даже не могу добраться до серверной части с этими ошибками, поскольку эти точки останова никогда не срабатывают. Интересно, что я обнаружил, что могу продвинуться немного дальше, используя FireFox (например, он, кажется, может получить доступ к серверной части); он не выдает ошибок SSL, а вместо этого пытается получить доступ к экземпляру Keycloak нашего приложения (не размещенному локально), чтобы проверить наш токен SSO, и выдает ошибку IDX20803. Ниже приведен дополнительный код исключения из этого:

System.InvalidOperationException: IDX20803: Unable to obtain configuration from: '<Keycloak URL>'.
   at Microsoft.IdentityModel.Protocols.ConfigurationManager`1.GetConfigurationAsync(CancellationToken cancel)
   at Microsoft.AspNetCore.Authentication.JwtBearer.JwtBearerHandler.HandleAuthenticateAsync()
   at Microsoft.AspNetCore.Authentication.JwtBearer.JwtBearerHandler.HandleAuthenticateAsync()
   at Microsoft.AspNetCore.Authentication.AuthenticationHandler`1.AuthenticateAsync()
   at Microsoft.AspNetCore.Authentication.AuthenticationService.AuthenticateAsync(HttpContext context, String scheme)
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddlewareImpl.Invoke(HttpContext context)

Я также заметил несколько ошибок IDX20803, которые больше соответствуют этому шаблону. Этот код отлично работает в .NET 6, но, должно быть, мне что-то не хватает в обновленных версиях .NET — любые рекомендации приветствуются!

То, что я уже пробовал

  • В обратном вызове options.Listen() попыталась добавить приведенный ниже блок кода.
    • Результат: никаких изменений в ошибке
opt.AllowAnyClientCertificate();
opt.ClientCertificateValidation = (certif, chain, policyErrors) => true;
opt.ClientCertificateMode = Microsoft.AspNetCore.Server.Kestrel.Https.ClientCertificateMode.AllowCertificate;
opt.ServerCertificate = cert;
opt.SslProtocols = System.Security.Authentication.SslProtocols.Tls12
    | System.Security.Authentication.SslProtocols.Ssl3
    | System.Security.Authentication.SslProtocols.Tls
    | System.Security.Authentication.SslProtocols.None
    | System.Security.Authentication.SslProtocols.Tls11
    | System.Security.Authentication.SslProtocols.Tls13
    | System.Security.Authentication.SslProtocols.Default;
  • В обратном вызове options.Listen() попробовал удалить вызов ops.UseHttps(cert).

    • Результат: удалось выполнить вызовы API к URL-адресу HTTP, но HTTPS остался недоступен.
  • В начале моих файлов Program.cs и Startup.cs я попытался добавить эту строку: ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.SystemDefault | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls | SecurityProtocolType.Tls13;

    • Результат: никаких изменений в ошибке
  • В методе Настройка файла Startup.cs добавьте app.UseHttpsRedirection();

    • Результат: никаких изменений в ошибке
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
0
109
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Возможно, это связано с этим: https://github.com/dotnet/aspnetcore/issues/54366

Посмотрите, поможет ли это:

options =>
{
    options.Listen(System.Net.IPAddress.Loopback, your-port, httpnOptions =>
    {
        httpOptions.UseHttps(new HttpsConnectionAdapterOptions { SslProtocols = SslProtocols.Tls12 });
    }
}))

если это поможет, есть проблема с TLS 1.3. Судя по всему, патч выпустят в мае.

https://github.com/dotnet/runtime/pull/99670

Другие вопросы по теме

ОШИБКА: не удалось найти версию, удовлетворяющую требованию pip (из версий: нет)
SSL-сокет принудительно закрыт — Python и IoT
Проблема с проверкой сертификата сервера при подключении к кластеру Kafka
Ошибка SSL при попытке настроить запросы сертификата Puppet Server
Проверка сертификата не удалась: невозможно получить сертификат локального эмитента, кажется, все в порядке
Grafana под управлением AWS не может подключить базу данных RDS Postgres в качестве источника данных с включенным SSL
«прерывание из-за небезопасной конфигурации» при настройке TLS на сервере Rust Rocket
Не удалось установить соединение TLS на основе TPM 2.0 с ключами сервера RSA-4k (вне диапазона)
Зачем мне использовать NODE_TLS_REJECT_UNAUTHORIZED="0", если это небезопасно
SSL-квитирование с сервером KMS занимает время (50 секунд) для нескольких событий запросов, хотя время ожидания соединения сокета составляет 2000 согласно журналам