Dajbych.net


Jak správně přesměrovat na HTTPS v aplikaci MVC ASP.NET

, 3 minuty čtení

http logo

Upgrade prohlížečů navštěvujících váš web na zabezpečené připojení je osvědčeným postupem a lze jej snadno provést. Rozhodl jsem se podělit o svou implementaci, protože jsem viděl mnoho částečných nebo nezabezpečených implementací. Správná implementace splňuje jak požadavky na zpětnou kompatibilitu, tak požadavky na bezpečnost různých webových prohlížečů. Tento článek popisuje, co potřebujete vědět, než začnete přesměrovávat uživatele na protokol HTTPS.

Co útočníci dělají

Někteří naivní weboví vývojáři používají připojení HTTPS pouze v případě, že prohlížeč odešle formulář s citlivými daty na server. Pokud je šifrování bezdrátové sítě slabé (což je případ většiny veřejných bezdrátových sítí nebo mobilních datových sítí), může útočník upravit odpověď serveru tak, aby byl formulář HTML odeslán na web útočníka. Proto je nezbytné nešifrovaná připojení zcela obejít.

Hlavička HTTP Upgrade-Insecure-Requests

Prohlížeč může v požadavku odeslat hlavičku Upgrade-Insecure-Requests: 1. Použitím této hlavičky dává serveru pokyn, že klient preferuje šifrované připojení. Kdo chce nešifrované připojení? Webové prohledávače mohou například ušetřit čas procesoru, protože optické spojení mezi datovými centry je obtížnější zachytit (je alespoň mnohem znatelnější). Webové prohledávače se většinou zajímají pouze o veřejná data.

Bylo by špatným zvykem automaticky přesměrovávat každý požadavek na protokol HTTPS. Webová rozhraní API mohou přijímat velké požadavky prostřednictvím požadavků POST. Když je požadavek POST přesměrován (povoleno RFC7231, který je zastaralý RFC2316), klient musí opakovaně přenášet celou datovou část. Může být lepší vrátit stavový kód chyby klienta HTTP, který přinutí klienta odeslat požadavek přímo do koncového bodu HTTPS.

Strict-Transport-Security hlavička HTTP

Server může v odpovědi odeslat hlavičku Strict-Transport-Security: max-age=<expire-time>. Použitím tohoto záhlaví dáte prohlížeči pokyn, aby automaticky převedl všechny pokusy o otevření webu na připojení HTTPS. Prohlížeče přijímají toto záhlaví pouze v případě, že je již navázáno zabezpečené připojení, protože útočník může toto záhlaví odstranit, pokud váš web používá prostý protokol HTTP.

Přesměrování webu z protokolu HTTP na HTTPS není bezpečné, protože útočník může nahradit umístění, do kterého je prohlížeč přesměrován. Hlavička Strict-Transport-Security (HSTS) byla určena k obejití této příležitosti pro útok typu man-in-the-middle. Je velká šance, že uživatel navštíví váš web z nekompromitované sítě. Když poté navštíví váš web, prohlížeč bude vždy používat HTTPS a útočník promešká příležitost k útoku typu man-in-the-middle i v napadené síti.

Filtr akcí ASP.NET MVC pro protokol HTTPS

Filtr akce je atribut, který můžete použít na akci nebo celý kontroler. Mění způsob, jakým je požadavek proveden. Ustanovení TlsAttribute přesměruje uživatele na zabezpečené připojení, pokud prohlížeč odešle hlavičku Upgrade-Insecure-Requests a požadavek není z localhost. Pokud je připojení zabezpečené, přidá se do odpovědi serveru hlavička HSTS.

public class TlsAttribute : ActionFilterAttribute {
    public override void OnActionExecuting(ActionExecutingContext filterContext) {
        var request = filterContext.HttpContext.Request;
        if (request.IsSecureConnection) {
            filterContext.HttpContext.Response.AddHeader("Strict-Transport-Security", "max-age=15552000");
        } else if (!request.IsLocal && request.Headers["Upgrade-Insecure-Requests"] == "1") {
            var url = new Uri("https://" + request.Url.GetComponents(UriComponents.Host | UriComponents.PathAndQuery, UriFormat.Unescaped), UriKind.Absolute);
            filterContext.Result = new RedirectResult(url.AbsoluteUri);
        }
    }
}

Poté lze filtr akcí snadno použít.

[HttpGet, Tls]
public ActionResult BlogPost(int id) {
    ...
}