Перенаправление HTTPS только для определенного порта (прослушивание на смешанных портах) с помощью Kestrel

#c# #asp.net-core #.net-core #kestrel-http-server #kestrel

#c# #asp.net-core #.net-ядро #kestrel-http-сервер #kestrel

Вопрос:

С использованием .NET Core 2.1, C #, Kestrel.

Это будет странный запрос, но: у меня есть внешний URL, который должен быть HTTPS, и внутренний URL, который является только HTTP.

Мне интересно, как я могу перенаправить любой трафик с HTTP на порт 443 на HTTPS (оставаясь на том же порту, 443); на данный момент он остается на HTTP и умирает ужасной смертью.

(Примечание: порт 888 остается HTTP, и любой трафик, идущий туда, должен оставаться как небезопасный HTTP.)

Я настроил это в Program.cs следующим образом:

 WebHost.CreateDefaultBuilder(args)
        .UseStartup<Startup>()
        .UseKestrel(options =>
        {
            options.Listen(IPAddress.Any, 443, opts=>
            {
                opts.UseHttps("mycert.pfx");
            });

            options.Listen(IPAddress.Any, 888);
        })
    .Build();
  

При запуске я попытался настроить (приложение IApplicationBuilder …)
app.UseHttpsRedirection();

Но это привело к перенаправлению ВСЕГО трафика на обоих портах на HTTPS, что является проблемой для 888, поскольку для него нет SSL-сертификата!

Есть ли какой-либо способ перенаправить с HTTP на HTTPS в зависимости от порта, для которого я его указываю? Спасибо

Ответ №1:

Конвейер промежуточного программного обеспечения по умолчанию выполняется независимо от того, какая конечная точка используется для доступа к вашему приложению. Итак, если вы просто сделаете app.UseHttpsRedirection() , то промежуточное программное обеспечение перенаправления HTTPS будет запущено для всех ваших общедоступных конечных точек.

Используется механизм UseWhen , который позволяет настроить конвейер условного промежуточного программного обеспечения, когда промежуточное программное обеспечение добавляется только в определенных условиях. Это будет выглядеть следующим образом:

 app.UseWhen(context => context.Request.Port == 888, httpApp =>
{
    httpApp.UseHttpsRedirection();
});
  

Однако в вашей ситуации это не поможет: проблема в том, что на одном порту вы можете разместить только одну вещь. Итак, если вы хотите разместить свое приложение с HTTPS на порту 443, тогда оно будет принимать только HTTPS там. Если вы попытаетесь подключиться, используя незащищенный HTTP, то произойдет сбой, поскольку он не может выполнить необходимое подтверждение связи.

Что вы хотели бы сделать здесь, так это разместить HTTP и HTTPS на одном порту, но это просто не работает, поскольку нет механизма, позволяющего выяснить, хочет ли клиент использовать HTTP или HTTPS, прежде чем они фактически уже попытаются установить либо.

Итак, нет, вы не можете перенаправить HTTP с порта 443 на HTTPS с порта 443.

Комментарии:

1. Hero <3 Теперь, когда вы это объяснили, это имеет смысл. Чего я пытаюсь избежать, так это того, что клиент переходит на HTTP (443), когда на самом деле он должен использовать HTTPS (443).