Konfigurace ASP.NET Core pro práci se servery proxy a nástroji pro vyrovnávání zatíženíConfigure ASP.NET Core to work with proxy servers and load balancers

Od Luke Latham a Chris RossůvBy Luke Latham and Chris Ross

V Doporučené konfiguraci pro ASP.NET Core se aplikace hostuje pomocí IIS/ASP. Modul NET Core, Nginx nebo Apache.In the recommended configuration for ASP.NET Core, the app is hosted using IIS/ASP.NET Core Module, Nginx, or Apache. Proxy servery, nástroje pro vyrovnávání zatížení a další síťová zařízení často překrývají informace o žádosti předtím, než dosáhnou aplikace:Proxy servers, load balancers, and other network appliances often obscure information about the request before it reaches the app:

  • Pokud jsou požadavky HTTPS proxy serverem přes HTTP, původní schéma (HTTPS) se ztratí a musí se přenášet v hlavičce.When HTTPS requests are proxied over HTTP, the original scheme (HTTPS) is lost and must be forwarded in a header.
  • Vzhledem k tomu, že aplikace obdrží požadavek od proxy serveru a ne jeho skutečný zdroj v Internetu nebo podnikové síti, musí být zdrojová adresa IP klienta předána také v hlavičce.Because an app receives a request from the proxy and not its true source on the Internet or corporate network, the originating client IP address must also be forwarded in a header.

Tyto informace můžou být důležité ve zpracování žádostí, například v přesměrování, ověřování, generování odkazů, vyhodnocení zásad a geografická poloha klienta.This information may be important in request processing, for example in redirects, authentication, link generation, policy evaluation, and client geolocation.

Předávaná záhlavíForwarded headers

Podle konvence proxy předávají informace v hlavičkách protokolu HTTP.By convention, proxies forward information in HTTP headers.

ZáhlavíHeader PopisDescription
X-předané – proX-Forwarded-For Uchovává informace o klientovi, který inicioval požadavek a následné proxy servery v řetězci proxy serverů.Holds information about the client that initiated the request and subsequent proxies in a chain of proxies. Tento parametr může obsahovat IP adresy (a volitelně také čísla portů).This parameter may contain IP addresses (and, optionally, port numbers). V řetězci proxy serverů označuje první parametr klienta, ve kterém se žádost poprvé nastavila.In a chain of proxy servers, the first parameter indicates the client where the request was first made. Následující identifikátory proxy následují.Subsequent proxy identifiers follow. Poslední proxy server v řetězci není uveden v seznamu parametrů.The last proxy in the chain isn't in the list of parameters. Poslední IP adresa proxy serveru a volitelně je číslo portu, které je k dispozici jako Vzdálená IP adresa v transportní vrstvě.The last proxy's IP address, and optionally a port number, are available as the remote IP address at the transport layer.
X-Forwarded-ProtoX-Forwarded-Proto Hodnota původního schématu (HTTP/HTTPS).The value of the originating scheme (HTTP/HTTPS). Hodnota může být také seznamem schémat, pokud je požadavek procházen více proxy.The value may also be a list of schemes if the request has traversed multiple proxies.
X-Forwarded-HostX-Forwarded-Host Původní hodnota pole hlavičky hostiteleThe original value of the Host header field. Servery proxy většinou nemění hlavičku hostitele.Usually, proxies don't modify the Host header. Viz informační zpravodaj zabezpečení společnosti Microsoft CVE-2018-0787 pro informace o chybě zabezpečení zvýšení oprávnění, která má vliv na systémy, ve kterých server proxy neověřuje nebo omezuje hlavičky hostitele na známé správné hodnoty.See Microsoft Security Advisory CVE-2018-0787 for information on an elevation-of-privileges vulnerability that affects systems where the proxy doesn't validate or restrict Host headers to known good values.

Middleware předávaných hlaviček z balíčku Microsoft. AspNetCore. HttpOverrides přečte tato záhlaví a vyplní přidružené pole na HttpContext.The Forwarded Headers Middleware, from the Microsoft.AspNetCore.HttpOverrides package, reads these headers and fills in the associated fields on HttpContext.

Aktualizace middlewaru:The middleware updates:

Je možné nakonfigurovat výchozí nastavení middlewaru u předávaných hlaviček.Forwarded Headers Middleware default settings can be configured. Výchozí nastavení:The default settings are:

  • Mezi aplikací a zdrojem požadavků je jenom jeden proxy server .There is only one proxy between the app and the source of the requests.
  • Pro známé proxy servery a známé sítě jsou nakonfigurovány pouze adresy zpětné smyčky.Only loopback addresses are configured for known proxies and known networks.
  • Předané hlavičky jsou pojmenovány X-Forwarded-For a X-Forwarded-Proto.The forwarded headers are named X-Forwarded-For and X-Forwarded-Proto.

Ne všechna síťová zařízení přidávají hlavičky X-Forwarded-For a X-Forwarded-Proto bez další konfigurace.Not all network appliances add the X-Forwarded-For and X-Forwarded-Proto headers without additional configuration. Zeptejte se na pokyny výrobce zařízení, jestli proxy požadavky při přístupu do aplikace tyto hlavičky neobsahují.Consult your appliance manufacturer's guidance if proxied requests don't contain these headers when they reach the app. Pokud zařízení používá jiné názvy hlaviček než X-Forwarded-For a X-Forwarded-Proto, nastavte ForwardedForHeaderName a ForwardedProtoHeaderName možnosti tak, aby odpovídaly názvům hlaviček používaným zařízením.If the appliance uses different header names than X-Forwarded-For and X-Forwarded-Proto, set the ForwardedForHeaderName and ForwardedProtoHeaderName options to match the header names used by the appliance. Další informace najdete v tématu předané možnosti a konfigurace middlewarových hlaviček pro proxy server, který používá jiné názvy hlaviček.For more information, see Forwarded Headers Middleware options and Configuration for a proxy that uses different header names.

Modul IIS/IIS Express a ASP.NET CoreIIS/IIS Express and ASP.NET Core Module

Middleware předávaných hlaviček je ve výchozím nastavení povolená službou IIS Integration middleware , když je aplikace hostovaná mimo službu IIS a modul ASP.NET Core.Forwarded Headers Middleware is enabled by default by IIS Integration Middleware when the app is hosted out-of-process behind IIS and the ASP.NET Core Module. Middleware předávaných hlaviček se aktivují, aby se nejdříve spouštěl v kanálu middleware s omezenou konfigurací určenou pro modul ASP.NET Core, protože se jedná o obavy týkající se důvěryhodnosti se předanými hlavičkami (například falšování IP adres).Forwarded Headers Middleware is activated to run first in the middleware pipeline with a restricted configuration specific to the ASP.NET Core Module due to trust concerns with forwarded headers (for example, IP spoofing). Middleware je nakonfigurované pro přeposílání X-Forwarded-For a X-Forwarded-Proto hlaviček a je omezený na jeden localhost proxy.The middleware is configured to forward the X-Forwarded-For and X-Forwarded-Proto headers and is restricted to a single localhost proxy. Pokud se vyžaduje další konfigurace, přečtěte si téma Možnosti middlewaru předávaných hlaviček.If additional configuration is required, see the Forwarded Headers Middleware options.

Další scénáře proxy server a nástroje pro vyrovnávání zatíženíOther proxy server and load balancer scenarios

Bez použití integrace služby IIS při hostování mimo procesynení middleware předávaných hlaviček ve výchozím nastavení povolená.Outside of using IIS Integration when hosting out-of-process, Forwarded Headers Middleware isn't enabled by default. Middleware předaných hlaviček musí být povolená pro aplikaci, která zpracovává předávaná záhlaví s UseForwardedHeaders.Forwarded Headers Middleware must be enabled for an app to process forwarded headers with UseForwardedHeaders. Po povolení middlewaru v případě, že middleware není zadána žádná ForwardedHeadersOptions, výchozí hodnota ForwardedHeadersOptions. ForwardedHeaders je ForwardedHeaders. None.After enabling the middleware if no ForwardedHeadersOptions are specified to the middleware, the default ForwardedHeadersOptions.ForwardedHeaders are ForwardedHeaders.None.

Nakonfigurujte middleware pomocí ForwardedHeadersOptions pro přeposílání X-Forwarded-For a X-Forwarded-Proto hlaviček v Startup.ConfigureServices.Configure the middleware with ForwardedHeadersOptions to forward the X-Forwarded-For and X-Forwarded-Proto headers in Startup.ConfigureServices. Vyvolejte metodu UseForwardedHeaders v Startup.Configure před voláním jiného middleware:Invoke the UseForwardedHeaders method in Startup.Configure before calling other middleware:

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvc();

    services.Configure<ForwardedHeadersOptions>(options =>
    {
        options.ForwardedHeaders = 
            ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
    });
}

public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
    app.UseForwardedHeaders();

    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }
    else
    {
        app.UseExceptionHandler("/Home/Error");
    }

    app.UseStaticFiles();
    // In ASP.NET Core 1.x, replace the following line with: app.UseIdentity();
    app.UseAuthentication();
    app.UseMvc();
}

Poznámka

Pokud nejsou zadány žádné ForwardedHeadersOptions v Startup.ConfigureServices nebo přímo k metodě rozšíření UseForwardedHeaders, výchozí hlavičky pro přeposílání jsou ForwardedHeaders. None.If no ForwardedHeadersOptions are specified in Startup.ConfigureServices or directly to the extension method with UseForwardedHeaders, the default headers to forward are ForwardedHeaders.None. Vlastnost ForwardedHeaders musí být nakonfigurována s hlavičkou, aby byla předána.The ForwardedHeaders property must be configured with the headers to forward.

Konfigurace nginxNginx configuration

Pro přeposílání hlaviček X-Forwarded-For a X-Forwarded-Proto naleznete v tématu Hostování ASP.NET Core v systému Linux pomocí Nginx.To forward the X-Forwarded-For and X-Forwarded-Proto headers, see Hostování ASP.NET Core v systému Linux pomocí Nginx. Další informace najdete v tématu Nginx: použití předané hlavičky.For more information, see NGINX: Using the Forwarded header.

Konfigurace ApacheApache configuration

X-Forwarded-For se přidá automaticky (viz Mod_proxy modulu Apache: hlavičky reverzních požadavků na proxy server).X-Forwarded-For is added automatically (see Apache Module mod_proxy: Reverse Proxy Request Headers). Informace o tom, jak přeslat hlavičku X-Forwarded-Proto, najdete v tématu Hostování ASP.NET Core v systému Linux pomocí Apache.For information on how to forward the X-Forwarded-Proto header, see Hostování ASP.NET Core v systému Linux pomocí Apache.

Možnosti middlewaru předávaných hlavičekForwarded Headers Middleware options

ForwardedHeadersOptions řízení chování middlewaru předávaných hlaviček.ForwardedHeadersOptions control the behavior of the Forwarded Headers Middleware. Následující příklad změní výchozí hodnoty:The following example changes the default values:

  • Omezte počet záznamů v předaných hlavičkách na 2.Limit the number of entries in the forwarded headers to 2.
  • Přidejte známou adresu proxy serveru 127.0.10.1.Add a known proxy address of 127.0.10.1.
  • Změňte název předané hlavičky z výchozí X-Forwarded-For na X-Forwarded-For-My-Custom-Header-Name.Change the forwarded header name from the default X-Forwarded-For to X-Forwarded-For-My-Custom-Header-Name.
services.Configure<ForwardedHeadersOptions>(options =>
{
    options.ForwardLimit = 2;
    options.KnownProxies.Add(IPAddress.Parse("127.0.10.1"));
    options.ForwardedForHeaderName = "X-Forwarded-For-My-Custom-Header-Name";
});
MožnostOption PopisDescription
AllowedHosts Omezuje hostitele v hlavičce X-Forwarded-Host na zadané hodnoty.Restricts hosts by the X-Forwarded-Host header to the values provided.
  • Hodnoty se porovnávají pomocí pořadí – ignorovat – případ.Values are compared using ordinal-ignore-case.
  • Čísla portů musí být vyloučena.Port numbers must be excluded.
  • Pokud je seznam prázdný, jsou povoleny všichni hostitelé.If the list is empty, all hosts are allowed.
  • Zástupný znak nejvyšší úrovně * umožňuje všem neprázdným hostitelům.A top-level wildcard * allows all non-empty hosts.
  • Zástupné znaky subdomény jsou povolené, ale neodpovídají kořenové doméně.Subdomain wildcards are permitted but don't match the root domain. *.contoso.com například odpovídá subdoméně foo.contoso.com ale nikoli ke kořenové doméně contoso.com.For example, *.contoso.com matches the subdomain foo.contoso.com but not the root domain contoso.com.
  • Názvy hostitelů Unicode jsou povoleny, ale jsou převedeny na Punycode pro porovnání.Unicode host names are allowed but are converted to Punycode for matching.
  • Adresy IPv6 musí zahrnovat ohraničující závorky a musí být v konvenčním formátu (například [ABCD:EF01:2345:6789:ABCD:EF01:2345:6789]).IPv6 addresses must include bounding brackets and be in conventional form (for example, [ABCD:EF01:2345:6789:ABCD:EF01:2345:6789]). IPv6 adresy nejsou speciální – použita pro kontrolu logické rovnosti mezi různými formáty a neprovádí se žádné kanonikalizace.IPv6 addresses aren't special-cased to check for logical equality between different formats, and no canonicalization is performed.
  • Nepodaří-li se omezit povolené hostitele, může útočníkovi umožnit přístup k falešným odkazům generovanými službou.Failure to restrict the allowed hosts may allow an attacker to spoof links generated by the service.
Výchozí hodnota je prázdná IList<string>.The default value is an empty IList<string>.
ForwardedForHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XForwardedForHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XForwardedForHeaderName. Tato možnost se používá, když proxy nebo předávací server nepoužívá hlavičku X-Forwarded-For, ale k přeposílání informací používá jiné záhlaví.This option is used when the proxy/forwarder doesn't use the X-Forwarded-For header but uses some other header to forward the information.

Výchozí hodnota je X-Forwarded-For.The default is X-Forwarded-For.
ForwardedHeaders Určuje, které předávacíci by se měly zpracovat.Identifies which forwarders should be processed. Seznam polí, která platí, najdete v tématu ForwardedHeaders enum .See the ForwardedHeaders Enum for the list of fields that apply. Typické hodnoty přiřazené k této vlastnosti jsou ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto.Typical values assigned to this property are ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto.

Výchozí hodnota je ForwardedHeaders. None.The default value is ForwardedHeaders.None.
ForwardedHostHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XForwardedHostHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XForwardedHostHeaderName. Tato možnost se používá, když proxy nebo předávací server nepoužívá hlavičku X-Forwarded-Host, ale k přeposílání informací používá jiné záhlaví.This option is used when the proxy/forwarder doesn't use the X-Forwarded-Host header but uses some other header to forward the information.

Výchozí hodnota je X-Forwarded-Host.The default is X-Forwarded-Host.
ForwardedProtoHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XForwardedProtoHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XForwardedProtoHeaderName. Tato možnost se používá, když proxy nebo předávací server nepoužívá hlavičku X-Forwarded-Proto, ale k přeposílání informací používá jiné záhlaví.This option is used when the proxy/forwarder doesn't use the X-Forwarded-Proto header but uses some other header to forward the information.

Výchozí hodnota je X-Forwarded-Proto.The default is X-Forwarded-Proto.
ForwardLimit Omezuje počet položek v záhlavích, které jsou zpracovávány.Limits the number of entries in the headers that are processed. Nastavte na null pro zákaz tohoto limitu, ale to byste měli udělat jenom v případě, že jsou nakonfigurované KnownProxies nebo KnownNetworks.Set to null to disable the limit, but this should only be done if KnownProxies or KnownNetworks are configured. Nastavení nenull hodnoty je preventivní opatrnost (ale ne záruka) pro ochranu proti nesprávně konfigurovaným proxy a škodlivým požadavkům přicházejících ze dvoustranných kanálů v síti.Setting a non-null value is a precaution (but not a guarantee) to guard against misconfigured proxies and malicious requests arriving from side-channels on the network.

Middleware předávaných hlaviček zpracovává hlavičky v obráceném pořadí zprava doleva.Forwarded Headers Middleware processes headers in reverse order from right to left. Pokud se použije výchozí hodnota (1), zpracuje se jenom hodnota zprava z hlaviček, pokud se nezvýší hodnota ForwardLimit.If the default value (1) is used, only the rightmost value from the headers is processed unless the value of ForwardLimit is increased.

Výchozí hodnota je 1.The default is 1.
KnownNetworks Rozsahy adres známých sítí, ze kterých se mají přijímat předávací hlavičky.Address ranges of known networks to accept forwarded headers from. Zadejte rozsahy IP adres pomocí zápisu CIDR (Classless prosměrování mezi doménami).Provide IP ranges using Classless Interdomain Routing (CIDR) notation.

Pokud server používá sokety s duálním režimem, adresy IPv4 se dodávají ve formátu IPv6 (například 10.0.0.1 ve službě IPv4 reprezentované protokolem IPv6 jako ::ffff:10.0.0.1).If the server is using dual-mode sockets, IPv4 addresses are supplied in an IPv6 format (for example, 10.0.0.1 in IPv4 represented in IPv6 as ::ffff:10.0.0.1). See IPAddress.MapToIPv6.See IPAddress.MapToIPv6. V části HttpContext. Connection. RemoteIpAddressZjistěte, jestli je tento formát vyžadován.Determine if this format is required by looking at the HttpContext.Connection.RemoteIpAddress. Další informace najdete v části konfigurace pro adresu IPv4 reprezentovanou jako oddíl IPv6 adresa .For more information, see the Configuration for an IPv4 address represented as an IPv6 address section.

Výchozí hodnota je IList<IPNetwork> obsahujícím jednu položku pro IPAddress.Loopback.The default is an IList<IPNetwork> containing a single entry for IPAddress.Loopback.
KnownProxies Adresy známých proxy adres, ze kterých se mají přijímat předávací hlavičky.Addresses of known proxies to accept forwarded headers from. Pomocí KnownProxies můžete zadat přesné shody IP adres.Use KnownProxies to specify exact IP address matches.

Pokud server používá sokety s duálním režimem, adresy IPv4 se dodávají ve formátu IPv6 (například 10.0.0.1 ve službě IPv4 reprezentované protokolem IPv6 jako ::ffff:10.0.0.1).If the server is using dual-mode sockets, IPv4 addresses are supplied in an IPv6 format (for example, 10.0.0.1 in IPv4 represented in IPv6 as ::ffff:10.0.0.1). See IPAddress.MapToIPv6.See IPAddress.MapToIPv6. V části HttpContext. Connection. RemoteIpAddressZjistěte, jestli je tento formát vyžadován.Determine if this format is required by looking at the HttpContext.Connection.RemoteIpAddress. Další informace najdete v části konfigurace pro adresu IPv4 reprezentovanou jako oddíl IPv6 adresa .For more information, see the Configuration for an IPv4 address represented as an IPv6 address section.

Výchozí hodnota je IList<IPAddress> obsahujícím jednu položku pro IPAddress.IPv6Loopback.The default is an IList<IPAddress> containing a single entry for IPAddress.IPv6Loopback.
OriginalForHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XOriginalForHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XOriginalForHeaderName.

Výchozí hodnota je X-Original-For.The default is X-Original-For.
OriginalHostHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XOriginalHostHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XOriginalHostHeaderName.

Výchozí hodnota je X-Original-Host.The default is X-Original-Host.
OriginalProtoHeaderName Použijte hlavičku určenou touto vlastností místo od ta, kterou Určuje ForwardedHeadersDefaults. XOriginalProtoHeaderName.Use the header specified by this property instead of the one specified by ForwardedHeadersDefaults.XOriginalProtoHeaderName.

Výchozí hodnota je X-Original-Proto.The default is X-Original-Proto.
RequireHeaderSymmetry Vyžaduje, aby byl počet synchronizovaných hodnot hlaviček mezi zpracovávaným ForwardedHeadersOptions. ForwardedHeaders .Require the number of header values to be in sync between the ForwardedHeadersOptions.ForwardedHeaders being processed.

Výchozí hodnota v ASP.NET Core 1. x je true.The default in ASP.NET Core 1.x is true. Výchozí hodnota v ASP.NET Core 2,0 nebo novější je false.The default in ASP.NET Core 2.0 or later is false.

Scénáře a případy použitíScenarios and use cases

Pokud není možné přidat předávané hlavičky a všechny požadavky jsou zabezpečenéWhen it isn't possible to add forwarded headers and all requests are secure

V některých případech nemusí být možné přidat předávaná záhlaví do požadavků, které jsou proxy k aplikaci.In some cases, it might not be possible to add forwarded headers to the requests proxied to the app. Pokud proxy vynucuje, že všechny veřejné externí požadavky jsou HTTPS, můžete schéma ručně nastavit v Startup.Configure před použitím libovolného typu middlewaru:If the proxy is enforcing that all public external requests are HTTPS, the scheme can be manually set in Startup.Configure before using any type of middleware:

app.Use((context, next) =>
{
    context.Request.Scheme = "https";
    return next();
});

Tento kód může být zakázán pomocí proměnné prostředí nebo jiného nastavení konfigurace ve vývojovém nebo přípravném prostředí.This code can be disabled with an environment variable or other configuration setting in a development or staging environment.

Práce se základními a proxy servery, které mění cestu požadavkuDeal with path base and proxies that change the request path

Některé proxy servery předávají cestu beze změny, ale se základní cestou aplikace, která by se měla odebrat, aby směrování fungovalo správně.Some proxies pass the path intact but with an app base path that should be removed so that routing works properly. Middleware UsePathBaseExtensions. UsePathBase middleware rozdělí cestu do HttpRequest. cesta a základní cestu aplikace do HttpRequest. PathBase.UsePathBaseExtensions.UsePathBase middleware splits the path into HttpRequest.Path and the app base path into HttpRequest.PathBase.

Pokud je /foo základní cestu aplikace pro cestu k proxy serveru předanou jako /foo/api/1, Request.PathBase sady middlewaru /foo a Request.Path /api/1 pomocí následujícího příkazu:If /foo is the app base path for a proxy path passed as /foo/api/1, the middleware sets Request.PathBase to /foo and Request.Path to /api/1 with the following command:

app.UsePathBase("/foo");

Původní cesta a základ cesty se znovu aplikují, když se middleware znovu zavolá v opačném případě.The original path and path base are reapplied when the middleware is called again in reverse. Další informace o zpracování pořadí middlewaru najdete v tématu Middleware ASP.NET Core.For more information on middleware order processing, see Middleware ASP.NET Core.

Pokud proxy ořízne cestu (například předávání /foo/api/1 do /api/1), opravte přesměrování a odkazy nastavením vlastnosti PathBase žádosti:If the proxy trims the path (for example, forwarding /foo/api/1 to /api/1), fix redirects and links by setting the request's PathBase property:

app.Use((context, next) =>
{
    context.Request.PathBase = new PathString("/foo");
    return next();
});

Pokud proxy přidává data cest, zahodí část cesty pro opravu přesměrování a odkazy pomocí StartsWithSegments a přiřazení k vlastnosti Path:If the proxy is adding path data, discard part of the path to fix redirects and links by using StartsWithSegments and assigning to the Path property:

app.Use((context, next) =>
{
    if (context.Request.Path.StartsWithSegments("/foo", out var remainder))
    {
        context.Request.Path = remainder;
    }

    return next();
});

Konfigurace proxy serveru, který používá jiné názvy hlavičekConfiguration for a proxy that uses different header names

Pokud proxy nepoužívá hlavičky s názvem X-Forwarded-For a X-Forwarded-Proto přesměrovat informace o adrese a portu proxy serveru a informace o původním schématu, nastavte ForwardedForHeaderName a ForwardedProtoHeaderName možnosti tak, aby odpovídaly názvům hlaviček používaných proxy serverem:If the proxy doesn't use headers named X-Forwarded-For and X-Forwarded-Proto to forward the proxy address/port and originating scheme information, set the ForwardedForHeaderName and ForwardedProtoHeaderName options to match the header names used by the proxy:

services.Configure<ForwardedHeadersOptions>(options =>
{
    options.ForwardedForHeaderName = "Header_Name_Used_By_Proxy_For_X-Forwarded-For_Header";
    options.ForwardedProtoHeaderName = "Header_Name_Used_By_Proxy_For_X-Forwarded-Proto_Header";
});

Konfigurace pro adresu IPv4 reprezentovanou jako IPv6 adresaConfiguration for an IPv4 address represented as an IPv6 address

Pokud server používá sokety s duálním režimem, adresy IPv4 jsou zadány ve formátu protokolu IPv6 (například 10.0.0.1 ve službě IPv4 reprezentované protokolem IPv6 jako ::ffff:10.0.0.1 nebo ::ffff:a00:1).If the server is using dual-mode sockets, IPv4 addresses are supplied in an IPv6 format (for example, 10.0.0.1 in IPv4 represented in IPv6 as ::ffff:10.0.0.1 or ::ffff:a00:1). See IPAddress.MapToIPv6.See IPAddress.MapToIPv6. V části HttpContext. Connection. RemoteIpAddressZjistěte, jestli je tento formát vyžadován.Determine if this format is required by looking at the HttpContext.Connection.RemoteIpAddress.

V následujícím příkladu se do seznamu KnownNetworks ve formátu protokolu IPv6 přidají síťová adresa, která poskytuje předávaná záhlaví.In the following example, a network address that supplies forwarded headers is added to the KnownNetworks list in IPv6 format.

Adresa IPv4: 10.11.12.1/8IPv4 address: 10.11.12.1/8

Převedená adresa IPv6: ::ffff:10.11.12.1Converted IPv6 address: ::ffff:10.11.12.1
Délka převedené předpony: 104Converted prefix length: 104

Adresu můžete také uvést v šestnáctkovém formátu (10.11.12.1 představovali v protokolu IPv6 jako ::ffff:0a0b:0c01).You can also supply the address in hexadecimal format (10.11.12.1 represented in IPv6 as ::ffff:0a0b:0c01). Při převodu adresy IPv4 na IPv6 přidejte 96 k délce předpony CIDR (8 v příkladu), aby se zohlednila další předpona IPv6 ::ffff: (8 + 96 = 104).When converting an IPv4 address to IPv6, add 96 to the CIDR Prefix Length (8 in the example) to account for the additional ::ffff: IPv6 prefix (8 + 96 = 104).

// To access IPNetwork and IPAddress, add the following namespaces:
// using using System.Net;
// using Microsoft.AspNetCore.HttpOverrides;
services.Configure<ForwardedHeadersOptions>(options =>
{
    options.ForwardedHeaders =
        ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
    options.KnownNetworks.Add(new IPNetwork(
        IPAddress.Parse("::ffff:10.11.12.1"), 104));
});

Předejte schéma pro reverzní proxy servery se systémy Linux a non-IIS.Forward the scheme for Linux and non-IIS reverse proxies

Aplikace, které volají UseHttpsRedirection a UseHsts umístí lokalitu do nekonečné smyčky, pokud je nasazená na App Service Azure Linux, virtuální počítač se systémem Azure Linux nebo za jakýkoli jiný reverzní proxy server, kromě služby IIS.Apps that call UseHttpsRedirection and UseHsts put a site into an infinite loop if deployed to an Azure Linux App Service, Azure Linux virtual machine (VM), or behind any other reverse proxy besides IIS. Protokol TLS je ukončen reverzním proxy serverem a Kestrel není informován o správném schématu požadavků.TLS is terminated by the reverse proxy, and Kestrel isn't made aware of the correct request scheme. OAuth a OIDC v této konfiguraci selže, protože generují nesprávná přesměrování.OAuth and OIDC also fail in this configuration because they generate incorrect redirects. UseIISIntegration přidává a konfiguruje middleware předávaných hlaviček při spuštění za IIS, ale neexistuje žádná vyhovující Automatická konfigurace pro Linux (integrace Apache nebo Nginx).UseIISIntegration adds and configures Forwarded Headers Middleware when running behind IIS, but there's no matching automatic configuration for Linux (Apache or Nginx integration).

Pro přeposílání schématu od proxy serveru ve scénářích mimo službu IIS přidejte a nakonfigurujte middleware s předanými hlavičkami.To forward the scheme from the proxy in non-IIS scenarios, add and configure Forwarded Headers Middleware. V Startup.ConfigureServicespoužijte následující kód:In Startup.ConfigureServices, use the following code:

// using Microsoft.AspNetCore.HttpOverrides;

if (string.Equals(
    Environment.GetEnvironmentVariable("ASPNETCORE_FORWARDEDHEADERS_ENABLED"), 
    "true", StringComparison.OrdinalIgnoreCase))
{
    services.Configure<ForwardedHeadersOptions>(options =>
    {
        options.ForwardedHeaders = ForwardedHeaders.XForwardedFor | 
            ForwardedHeaders.XForwardedProto;
        // Only loopback proxies are allowed by default.
        // Clear that restriction because forwarders are enabled by explicit 
        // configuration.
        options.KnownNetworks.Clear();
        options.KnownProxies.Clear();
    });
}

Předávání certifikátůCertificate forwarding

AzureAzure

Pokud chcete nakonfigurovat Azure App Service pro předávání certifikátů, přečtěte si téma Konfigurace vzájemného ověřování TLS pro Azure App Service.To configure Azure App Service for certificate forwarding, see Configure TLS mutual authentication for Azure App Service. Následující pokyny se týkají konfigurace aplikace ASP.NET Core.The following guidance pertains to configuring the ASP.NET Core app.

V Startup.Configurepřed voláním app.UseAuthentication();přidejte následující kód:In Startup.Configure, add the following code before the call to app.UseAuthentication();:

app.UseCertificateForwarding();

Nakonfigurujte middleware předávání certifikátů a určete název hlavičky, kterou používá Azure.Configure Certificate Forwarding Middleware to specify the header name that Azure uses. V Startup.ConfigureServicespřidejte následující kód pro konfiguraci hlavičky, ze které middleware vytváří certifikát:In Startup.ConfigureServices, add the following code to configure the header from which the middleware builds a certificate:

services.AddCertificateForwarding(options =>
    options.CertificateHeader = "X-ARR-ClientCert");

Další webové proxy serveryOther web proxies

Pokud se používá proxy server, který není službou IIS nebo Azure App Service směrování žádostí na aplikace (ARR), nakonfigurujte proxy server tak, aby předal certifikát, který přijal v hlavičce protokolu HTTP.If a proxy is used that isn't IIS or Azure App Service's Application Request Routing (ARR), configure the proxy to forward the certificate that it received in an HTTP header. V Startup.Configurepřed voláním app.UseAuthentication();přidejte následující kód:In Startup.Configure, add the following code before the call to app.UseAuthentication();:

app.UseCertificateForwarding();

Nakonfigurujte middleware předávání certifikátů a zadejte název záhlaví.Configure the Certificate Forwarding Middleware to specify the header name. V Startup.ConfigureServicespřidejte následující kód pro konfiguraci hlavičky, ze které middleware vytváří certifikát:In Startup.ConfigureServices, add the following code to configure the header from which the middleware builds a certificate:

services.AddCertificateForwarding(options =>
    options.CertificateHeader = "YOUR_CERTIFICATE_HEADER_NAME");

Pokud proxy server nepodporuje kódování Base64 (jako je případ s Nginx), nastavte možnost HeaderConverter.If the proxy isn't base64-encoding the certificate (as is the case with Nginx), set the HeaderConverter option. Vezměte v úvahu následující příklad Startup.ConfigureServices:Consider the following example in Startup.ConfigureServices:

services.AddCertificateForwarding(options =>
{
    options.CertificateHeader = "YOUR_CUSTOM_HEADER_NAME";
    options.HeaderConverter = (headerValue) => 
    {
        var clientCertificate = 
           /* some conversion logic to create an X509Certificate2 */
        return clientCertificate;
    }
});

Řešení potížíTroubleshoot

Když hlavičky nejsou předávány podle očekávání, povolte protokolování.When headers aren't forwarded as expected, enable logging. Pokud protokoly neposkytují dostatek informací pro řešení tohoto problému, vytvořte výčet hlaviček požadavků přijatých serverem.If the logs don't provide sufficient information to troubleshoot the problem, enumerate the request headers received by the server. K zápisu hlaviček požadavků do odpovědi aplikace nebo k protokolování hlaviček použijte vložený middlewarový middleware.Use inline middleware to write request headers to an app response or log the headers.

Pokud chcete zapsat hlavičky do odpovědi aplikace, umístěte následující vložený middleware terminálu hned po volání UseForwardedHeaders v Startup.Configure:To write the headers to the app's response, place the following terminal inline middleware immediately after the call to UseForwardedHeaders in Startup.Configure:

app.Run(async (context) =>
{
    context.Response.ContentType = "text/plain";

    // Request method, scheme, and path
    await context.Response.WriteAsync(
        $"Request Method: {context.Request.Method}{Environment.NewLine}");
    await context.Response.WriteAsync(
        $"Request Scheme: {context.Request.Scheme}{Environment.NewLine}");
    await context.Response.WriteAsync(
        $"Request Path: {context.Request.Path}{Environment.NewLine}");

    // Headers
    await context.Response.WriteAsync($"Request Headers:{Environment.NewLine}");

    foreach (var header in context.Request.Headers)
    {
        await context.Response.WriteAsync($"{header.Key}: " +
            $"{header.Value}{Environment.NewLine}");
    }

    await context.Response.WriteAsync(Environment.NewLine);

    // Connection: RemoteIp
    await context.Response.WriteAsync(
        $"Request RemoteIp: {context.Connection.RemoteIpAddress}");
});

Do protokolů můžete zapisovat místo těla odpovědi.You can write to logs instead of the response body. Zápis do protokolů umožňuje, aby lokalita fungovala normálně během ladění.Writing to logs allows the site to function normally while debugging.

Zápis protokolů místo textu odpovědi:To write logs rather than to the response body:

app.Use(async (context, next) =>
{
    // Request method, scheme, and path
    _logger.LogDebug("Request Method: {Method}", context.Request.Method);
    _logger.LogDebug("Request Scheme: {Scheme}", context.Request.Scheme);
    _logger.LogDebug("Request Path: {Path}", context.Request.Path);

    // Headers
    foreach (var header in context.Request.Headers)
    {
        _logger.LogDebug("Header: {Key}: {Value}", header.Key, header.Value);
    }

    // Connection: RemoteIp
    _logger.LogDebug("Request RemoteIp: {RemoteIpAddress}", 
        context.Connection.RemoteIpAddress);

    await next();
});

Při zpracování X-Forwarded-{For|Proto|Host} hodnoty přesunuty do X-Original-{For|Proto|Host}.When processed, X-Forwarded-{For|Proto|Host} values are moved to X-Original-{For|Proto|Host}. Pokud existuje více hodnot v dané hlavičce, middleware pro přesměrované hlavičky zpracovává záhlaví v opačném pořadí zprava doleva.If there are multiple values in a given header, Forwarded Headers Middleware processes headers in reverse order from right to left. Výchozí ForwardLimit je 1 (jedna), takže se zpracovává jenom hodnota nejvíce vpravo od hlaviček, pokud se hodnota ForwardLimit nezvýší.The default ForwardLimit is 1 (one), so only the rightmost value from the headers is processed unless the value of ForwardLimit is increased.

Původní Vzdálená IP adresa žádosti se musí shodovat s položkou v KnownProxies nebo v seznamech KnownNetworks před zpracováním předávaných hlaviček.The request's original remote IP must match an entry in the KnownProxies or KnownNetworks lists before forwarded headers are processed. To omezuje falšování hlaviček tím, že nepřijímá předávací servery od nedůvěryhodných proxy serverů.This limits header spoofing by not accepting forwarders from untrusted proxies. Při zjištění neznámého proxy serveru se zobrazí zpráva s informacemi o adrese proxy serveru:When an unknown proxy is detected, logging indicates the address of the proxy:

September 20th 2018, 15:49:44.168 Unknown proxy: 10.0.0.100:54321

V předchozím příkladu je 10.0.0.100 proxy server.In the preceding example, 10.0.0.100 is a proxy server. Pokud je server důvěryhodným proxy serverem, přidejte IP adresu serveru do KnownProxies (nebo přidejte důvěryhodnou síť do KnownNetworks) v Startup.ConfigureServices.If the server is a trusted proxy, add the server's IP address to KnownProxies (or add a trusted network to KnownNetworks) in Startup.ConfigureServices. Další informace najdete v části Možnosti middlewaru předávaných hlaviček .For more information, see the Forwarded Headers Middleware options section.

services.Configure<ForwardedHeadersOptions>(options =>
{
    options.KnownProxies.Add(IPAddress.Parse("10.0.0.100"));
});

Důležité

Povoluje pouze důvěryhodné proxy servery a sítě pro přeposílání hlaviček.Only allow trusted proxies and networks to forward headers. V opačném případě jsou možné útoky s falešnou IP adresou .Otherwise, IP spoofing attacks are possible.

Další materiály a zdroje informacíAdditional resources