Oprogramowanie pośredniczące kompresji odpowiedzi dla platformy ASP.NET CoreResponse Compression Middleware for ASP.NET Core

Przez Luke LathamBy Luke Latham

Wyświetlić lub pobrać przykładowy kod (sposobu pobierania)View or download sample code (how to download)

Przepustowość sieci jest ograniczona zasobów.Network bandwidth is a limited resource. Zmniejszenie rozmiaru odpowiedzi, zazwyczaj często gwałtowny wzrost czas odpowiedzi aplikacji.Reducing the size of the response usually increases the responsiveness of an app, often dramatically. Jednym ze sposobów zmniejszyć rozmiar ładunku jest kompresji odpowiedzi aplikacji.One way to reduce payload sizes is to compress an app's responses.

Kiedy należy używać oprogramowania pośredniczącego kompresji odpowiedziWhen to use Response Compression Middleware

Użyj technologii kompresji odpowiedzi na serwerze usług IIS, Apache lub Nginx.Use server-based response compression technologies in IIS, Apache, or Nginx. Wydajność oprogramowania pośredniczącego prawdopodobnie nie będzie zgodne z modułami serwera.The performance of the middleware probably won't match that of the server modules. Serwer HTTP.sys i Kestrel aktualnie nie oferują obsługę wbudowanych kompresji.HTTP.sys server and Kestrel don't currently offer built-in compression support.

Użyj oprogramowania pośredniczącego kompresji odpowiedzi, gdy jesteś:Use Response Compression Middleware when you're:

Kompresja odpowiedziResponse compression

Zazwyczaj nie natywnie skompresowane odpowiedzi mogą korzystać z kompresji odpowiedzi.Usually, any response not natively compressed can benefit from response compression. Odpowiedzi nie natywnie skompresowane zwykle obejmują: CSS, JavaScript, HTML, XML i JSON.Responses not natively compressed typically include: CSS, JavaScript, HTML, XML, and JSON. Nie Kompresuj natywnie skompresowany zasobów, takich jak pliki PNG.You shouldn't compress natively compressed assets, such as PNG files. Próba dalsze Kompresuj natywnie skompresowane odpowiedzi żadnych dodatkowych małych skrócenie czasu rozmiaru i transmisji prawdopodobnie będzie overshadowed przez czas przetwarzania kompresji.If you attempt to further compress a natively compressed response, any small additional reduction in size and transmission time will likely be overshadowed by the time it took to process the compression. Nie Kompresuj pliki mniejsze niż około 150 – 1000 bajtów (w zależności od zawartości pliku i wydajności kompresji).Don't compress files smaller than about 150-1000 bytes (depending on the file's content and the efficiency of compression). Koszty kompresowania małych plików może powodować większe niż nieskompresowanego pliku skompresowanego pliku.The overhead of compressing small files may produce a compressed file larger than the uncompressed file.

W przypadku klienta może przetwarzać skompresowanej zawartości, klient musi powiadomić serwera jej możliwości, wysyłając Accept-Encoding nagłówek z żądania.When a client can process compressed content, the client must inform the server of its capabilities by sending the Accept-Encoding header with the request. Gdy serwer wysyła skompresowanej treści, musi on zawierać informacje w Content-Encoding nagłówka w sposób jest zakodowany skompresowanych odpowiedzi.When a server sends compressed content, it must include information in the Content-Encoding header on how the compressed response is encoded. W poniższej tabeli przedstawiono zawartości kodowania nazw obsługiwanych przez oprogramowanie pośredniczące.Content encoding designations supported by the middleware are shown in the following table.

Accept-Encodingwartości nagłówkaAccept-Encoding header values Obsługiwane oprogramowanie pośrednicząceMiddleware Supported OpisDescription
br NieNo Format skompresowanych danych BrotliBrotli Compressed Data Format
compress NieNo Format danych "Kompresuj" systemu UNIXUNIX "compress" data format
deflate NieNo "deflate" skompresowane dane w formacie danych "zlib""deflate" compressed data inside the "zlib" data format
exi NieNo W3C XML wydajne wymianyW3C Efficient XML Interchange
gzip Tak (ustawienie domyślne)Yes (default) format pliku gzipgzip file format
identity TakYes Identyfikator "Bez kodowania": nie musi być zakodowany odpowiedzi."No encoding" identifier: The response must not be encoded.
pack200-gzip NieNo Format transferu sieciowego archiwów JavaNetwork Transfer Format for Java Archives
* TakYes Dostępne kodowanie nie jest jawnie żądanej zawartościAny available content encoding not explicitly requested

Aby uzyskać więcej informacji, zobacz przez organizację IANA oficjalnego zawartości listy kodowania.For more information, see the IANA Official Content Coding List.

Oprogramowanie pośredniczące pozwala dodać kompresji dodatkowych dostawców na potrzeby niestandardowe Accept-Encoding wartości nagłówka.The middleware allows you to add additional compression providers for custom Accept-Encoding header values. Aby uzyskać więcej informacji, zobacz dostawców niestandardowych poniżej.For more information, see Custom Providers below.

Oprogramowanie pośredniczące jest w stanie reagowanie na wartość jakości (qvalue, q) wagi po wysłaniu przez klienta priorytety schematów kompresji.The middleware is capable of reacting to quality value (qvalue, q) weighting when sent by the client to prioritize compression schemes. Aby uzyskać więcej informacji, zobacz RFC 7231: Zaakceptuj kodowanie.For more information, see RFC 7231: Accept-Encoding.

Algorytmy kompresji podlegają zależności między szybkość kompresji i skuteczności kompresji.Compression algorithms are subject to a tradeoff between compression speed and the effectiveness of the compression. Skuteczność w tym kontekście odnosi się do rozmiaru dane wyjściowe po kompresji.Effectiveness in this context refers to the size of the output after compression. Jest to osiągane przez maksymalnie najmniejszy rozmiar optymalną kompresji.The smallest size is achieved by the most optimal compression.

Nagłówki zaangażowane w żądanie wysyłania, buforowanie i odbieranie skompresowanej zawartości są opisane w poniższej tabeli.The headers involved in requesting, sending, caching, and receiving compressed content are described in the table below.

nagłówekHeader RolaRole
Accept-Encoding Wysłanych z klienta na serwerze wskazuje zawartość, kodowanie schematy dopuszczalne do klienta.Sent from the client to the server to indicate the content encoding schemes acceptable to the client.
Content-Encoding Wysyłane z serwera do klienta w celu wskazania kodowania zawartości w ładunku.Sent from the server to the client to indicate the encoding of the content in the payload.
Content-Length W przypadku kompresji Content-Length nagłówka zostanie usunięty, ponieważ zmiany zawartości treści podczas kompresowania odpowiedzi.When compression occurs, the Content-Length header is removed, since the body content changes when the response is compressed.
Content-MD5 W przypadku kompresji Content-MD5 nagłówka zostanie usunięty, ponieważ zmieniono zawartość treści i skrót nie jest już prawidłowy.When compression occurs, the Content-MD5 header is removed, since the body content has changed and the hash is no longer valid.
Content-Type Określa typ MIME zawartości.Specifies the MIME type of the content. Należy określić co odpowiedzi jego Content-Type.Every response should specify its Content-Type. Oprogramowanie pośredniczące sprawdza tę wartość, aby określić, jeśli odpowiedź powinna być kompresowana.The middleware checks this value to determine if the response should be compressed. Oprogramowanie pośredniczące określa zbiór domyślne typy MIME go może zakodować, ale można zastąpić, lub dodać typy MIME.The middleware specifies a set of default MIME types that it can encode, but you can replace or add MIME types.
Vary Po wysłaniu przez serwer z wartością Accept-Encoding do klientów i serwerów proxy, Vary nagłówka wskazuje do klienta lub serwera proxy, który powinien pamięci podręcznej (różne) odpowiedzi na podstawie wartości z Accept-Encoding nagłówka żądania.When sent by the server with a value of Accept-Encoding to clients and proxies, the Vary header indicates to the client or proxy that it should cache (vary) responses based on the value of the Accept-Encoding header of the request. Wynik zwracania zawartości za pomocą Vary: Accept-Encoding nagłówka jest zarówno skompresowane i nieskompresowanym odpowiedzi są buforowane oddzielnie.The result of returning content with the Vary: Accept-Encoding header is that both compressed and uncompressed responses are cached separately.

Funkcje oprogramowania pośredniczącego kompresji odpowiedzi z można eksplorować Przykładowa aplikacja.You can explore the features of the Response Compression Middleware with the sample app. Przykładową:The sample illustrates:

  • Kompresja odpowiedzi aplikacji przy użyciu dostawców niestandardowych kompresji i gzip.The compression of app responses using gzip and custom compression providers.
  • Jak dodać typ MIME do listy domyślnych typów MIME kompresji.How to add a MIME type to the default list of MIME types for compression.

PackagePackage

Aby dołączyć oprogramowanie pośredniczące w projekcie, należy dodać odwołanie do Microsoft.AspNetCore.ResponseCompression pakietu lub użyj Microsoft.AspNetCore.All pakietu.To include the middleware in your project, add a reference to the Microsoft.AspNetCore.ResponseCompression package or use the Microsoft.AspNetCore.All package. Ta funkcja jest dostępna dla aplikacji przeznaczonych dla platformy ASP.NET Core 1.1 lub nowszej.This feature is available for apps that target ASP.NET Core 1.1 or later.

KonfiguracjaConfiguration

Poniższy kod przedstawia sposób włączania oprogramowania pośredniczącego kompresji odpowiedzi z kompresji gzip domyślne i domyślnych typów MIME.The following code shows how to enable the Response Compression Middleware with the with the default gzip compression and for default MIME types.

WebHost.CreateDefaultBuilder(args)
    .ConfigureServices(services =>
    {
        services.AddResponseCompression();
    })
    .Configure(app =>
    {
        app.UseResponseCompression();

        app.Run(async context =>
        {
            context.Response.ContentType = "text/plain";
            await context.Response.WriteAsync(LoremIpsum.Text);
        });
    })
    .Build();

Uwaga

Użyj narzędzia, takiego jak Fiddler, Firebug, lub Postman można ustawić Accept-Encoding nagłówek żądania i badania nagłówki odpowiedzi, rozmiar i treść.Use a tool like Fiddler, Firebug, or Postman to set the Accept-Encoding request header and study the response headers, size, and body.

Prześlij żądanie do przykładowej aplikacji bez Accept-Encoding nagłówka i sprawdź, czy odpowiedź jest nieskompresowane.Submit a request to the sample app without the Accept-Encoding header and observe that the response is uncompressed. Content-Encoding i Vary nagłówki nie są dostępne w odpowiedzi.The Content-Encoding and Vary headers aren't present on the response.

Wynik żądania bez nagłówka Accept-Encoding przedstawiający okno fiddler.

Prześlij żądanie do aplikacji przykładowej przy Accept-Encoding: gzip nagłówka i sprawdź, czy odpowiedź jest kompresowana.Submit a request to the sample app with the Accept-Encoding: gzip header and observe that the response is compressed. Content-Encoding i Vary nagłówki są obecne w odpowiedzi.The Content-Encoding and Vary headers are present on the response.

Okno narzędzia fiddler przedstawiający wynik żądania z nagłówka Accept-Encoding i wartości gzip.

dostawcówProviders

GzipCompressionProviderGzipCompressionProvider

Użyj GzipCompressionProvider kompresji odpowiedzi z gzip.Use the GzipCompressionProvider to compress responses with gzip. To jest dostawcą domyślnym kompresji, jeśli żaden nie jest określony.This is the default compression provider if none are specified. Można ustawić poziomu z kompresji GzipCompressionProviderOptions.You can set the compression level with the GzipCompressionProviderOptions.

Domyślnie dostawca kompresji gzip najszybszym poziom kompresji (CompressionLevel.Fastest), może nie dawać najbardziej efektywny kompresji.The gzip compression provider defaults to the fastest compression level (CompressionLevel.Fastest), which might not produce the most efficient compression. W razie potrzeby najbardziej efektywny kompresji można skonfigurować oprogramowanie pośredniczące optymalnej kompresji.If the most efficient compression is desired, you can configure the middleware for optimal compression.

Poziom kompresjiCompression Level OpisDescription
CompressionLevel.Fastest Kompresja powinno zakończyć tak szybko, jak to możliwe, nawet jeśli dane wyjściowe nie będzie skompresowany optymalnie.Compression should complete as quickly as possible, even if the resulting output is not optimally compressed.
CompressionLevel.NoCompression Kompresja nie powinny być wykonywane.No compression should be performed.
CompressionLevel.Optimal Odpowiedzi powinna być optymalnie kompresowana, nawet jeśli kompresja trwa dłużej.Responses should be optimally compressed, even if the compression takes more time to complete.
services.AddResponseCompression(options =>
{
    options.Providers.Add<GzipCompressionProvider>();
    options.Providers.Add<CustomCompressionProvider>();
    options.MimeTypes = ResponseCompressionDefaults.MimeTypes.Concat(new[] { "image/svg+xml" });
});

services.Configure<GzipCompressionProviderOptions>(options => 
{
    options.Level = CompressionLevel.Fastest;
});

MIME, typyMIME types

Oprogramowanie pośredniczące Określa domyślny zestaw typy MIME kompresji:The middleware specifies a default set of MIME types for compression:

  • text/plain
  • text/css
  • application/javascript
  • text/html
  • application/xml
  • text/xml
  • application/json
  • text/json

Można zastąpić, lub Dołącz typy MIME opcje oprogramowania pośredniczącego kompresji odpowiedzi.You can replace or append MIME types with the Response Compression Middleware options. Należy pamiętać, że symbol wieloznaczny MIME typy, takich jak text/* nie są obsługiwane.Note that wildcard MIME types, such as text/* aren't supported. Przykładowa aplikacja dodaje typ MIME dla image/svg+xml kompresuje i obsługuje platformy ASP.NET Core obraz transparentu (banner.svg).The sample app adds a MIME type for image/svg+xml and compresses and serves the ASP.NET Core banner image (banner.svg).

services.AddResponseCompression(options =>
{
    options.Providers.Add<GzipCompressionProvider>();
    options.Providers.Add<CustomCompressionProvider>();
    options.MimeTypes = ResponseCompressionDefaults.MimeTypes.Concat(new[] { "image/svg+xml" });
});

services.Configure<GzipCompressionProviderOptions>(options => 
{
    options.Level = CompressionLevel.Fastest;
});

Dostawcy niestandardowiCustom providers

Można tworzyć niestandardowe kompresji implementacje z ICompressionProvider.You can create custom compression implementations with ICompressionProvider. EncodingName Reprezentuje zawartość, kodowanie tego ICompressionProvider tworzy.The EncodingName represents the content encoding that this ICompressionProvider produces. Oprogramowanie pośredniczące używa tych informacji do wybierz dostawcę na podstawie listy określone w Accept-Encoding nagłówka żądania.The middleware uses this information to choose the provider based on the list specified in the Accept-Encoding header of the request.

Przy użyciu aplikacji przykładowej, klient przesyła żądanie z Accept-Encoding: mycustomcompression nagłówka.Using the sample app, the client submits a request with the Accept-Encoding: mycustomcompression header. Oprogramowanie pośredniczące używa implementacji niestandardowych kompresji i zwraca odpowiedź z Content-Encoding: mycustomcompression nagłówka.The middleware uses the custom compression implementation and returns the response with a Content-Encoding: mycustomcompression header. Klient musi mieć możliwość dekompresja niestandardowego kodowania w kolejności stosowania niestandardowego kompresji do pracy.The client must be able to decompress the custom encoding in order for a custom compression implementation to work.

services.AddResponseCompression(options =>
{
    options.Providers.Add<GzipCompressionProvider>();
    options.Providers.Add<CustomCompressionProvider>();
    options.MimeTypes = ResponseCompressionDefaults.MimeTypes.Concat(new[] { "image/svg+xml" });
});

services.Configure<GzipCompressionProviderOptions>(options => 
{
    options.Level = CompressionLevel.Fastest;
});
public class CustomCompressionProvider : ICompressionProvider
{
    public string EncodingName => "mycustomcompression";
    public bool SupportsFlush => true;

    public Stream CreateStream(Stream outputStream)
    {
        // Create a custom compression stream wrapper here
        return outputStream;
    }
}

Prześlij żądanie do aplikacji przykładowej przy Accept-Encoding: mycustomcompression nagłówka i obserwować nagłówków odpowiedzi.Submit a request to the sample app with the Accept-Encoding: mycustomcompression header and observe the response headers. Vary i Content-Encoding nagłówki są obecne w odpowiedzi.The Vary and Content-Encoding headers are present on the response. Treść odpowiedzi (tego nie pokazano) nie jest skompresowane za próbki.The response body (not shown) isn't compressed by the sample. Nie ma implementacja kompresji CustomCompressionProvider klasy próbki.There isn't a compression implementation in the CustomCompressionProvider class of the sample. Jednak pokazano, gdzie czy wdrożenie jest algorytm kompresji.However, the sample shows where you would implement such a compression algorithm.

Wynik żądania z nagłówka Accept-Encoding oraz wartość mycustomcompression okno fiddler.

Kompresja z bezpiecznego protokołuCompression with secure protocol

Skompresowane odpowiedzi za pośrednictwem bezpiecznego połączenia można sterować za pomocą EnableForHttps opcja, która jest domyślnie wyłączona.Compressed responses over secure connections can be controlled with the EnableForHttps option, which is disabled by default. Używanie kompresji na dynamicznie generowanym stronach może prowadzić do problemów z bezpieczeństwem takich jak ataki CRIME i naruszenia ataków.Using compression with dynamically generated pages can lead to security problems such as the CRIME and BREACH attacks.

Dodawanie nagłówka VaryAdding the Vary header

Podczas kompresowania odpowiedzi na podstawie Accept-Encoding nagłówka, istnieją potencjalnie wiele wersji skompresowanych odpowiedzi i nieskompresowanym wersji.When compressing responses based on the Accept-Encoding header, there are potentially multiple compressed versions of the response and an uncompressed version. Aby nakazać klienta i serwera proxy pamięci podręcznej, czy istnieją wiele wersji, a powinien być przechowywany, Vary nagłówka zostanie dodany z Accept-Encoding wartości.In order to instruct client and proxy caches that multiple versions exist and should be stored, the Vary header is added with an Accept-Encoding value. W przypadku platformy ASP.NET Core 1.x, dodawanie Vary nagłówka do odpowiedzi odbywa się ręcznie.In ASP.NET Core 1.x, adding the Vary header to the response is accomplished manually. W przypadku platformy ASP.NET Core dodaje oprogramowanie pośredniczące 2.x, Vary nagłówka automatycznie w przypadku skompresowanych odpowiedzi.In ASP.NET Core 2.x, the middleware adds the Vary header automatically when the response is compressed.

Program ASP.NET Core tylko 1.xASP.NET Core 1.x only

// ONLY REQUIRED FOR ASP.NET CORE 1.x APPS
private void ManageVaryHeader(HttpContext context)
{
    // If the Accept-Encoding header is present, add the Vary header
    var accept = context.Request.Headers[HeaderNames.AcceptEncoding];
    if (!StringValues.IsNullOrEmpty(accept))
    {
        context.Response.Headers.Append(HeaderNames.Vary, HeaderNames.AcceptEncoding);
    }
}

Middlware problem podczas za Nginx wstecznego serwera proxyMiddlware issue when behind an Nginx reverse-proxy

Jeśli żądanie jest przekazywane przez serwer proxy przez Nginx, Accept-Encoding nagłówka zostaną usunięte.When a request is proxied by Nginx, the Accept-Encoding header is removed. Zapobiega to oprogramowanie pośredniczące od kompresji odpowiedzi.This prevents the middleware from compressing the response. Aby uzyskać więcej informacji, zobacz NGINX: kompresji i dekompresji.For more information, see NGINX: Compression and Decompression. Ten problem jest śledzony przez zorientować się przekazujące kompresja nginx (BasicMiddleware #123).This issue is tracked by Figure out pass-through compression for nginx (BasicMiddleware #123).

Praca z kompresji dynamicznej usług IISWorking with IIS dynamic compression

Jeśli masz aktywnego IIS dynamicznej kompresji modułu skonfigurowane na poziomie serwera, który ma zostać wyłączone dla aplikacji, możesz to zrobić z dodatku programu web.config pliku.If you have an active IIS Dynamic Compression Module configured at the server level that you would like to disable for an app, you can do so with an addition to your web.config file. Aby uzyskać więcej informacji, zobacz moduły IIS wyłączenie.For more information, see Disabling IIS modules.

Rozwiązywanie problemówTroubleshooting

Użyj narzędzia, takiego jak Fiddler, Firebug, lub Postman, umożliwiają skonfigurowanie Accept-Encoding nagłówek żądania i badania nagłówki odpowiedzi, rozmiar i treść.Use a tool like Fiddler, Firebug, or Postman, which allow you to set the Accept-Encoding request header and study the response headers, size, and body. Oprogramowanie pośredniczące kompresji odpowiedzi kompresuje odpowiedzi, które spełniają poniższe warunki:The Response Compression Middleware compresses responses that meet the following conditions:

  • Accept-Encoding Nagłówek ma wartość gzip, *, lub niestandardowy kodowania pasujący dostawcy niestandardowego kompresji, który został określony.The Accept-Encoding header is present with a value of gzip, *, or custom encoding that matches a custom compression provider that you've established. Wartość nie może być identity ani mieć wartości jakości (qvalue, q) ustawienie 0 (zero).The value must not be identity or have a quality value (qvalue, q) setting of 0 (zero).
  • Typ MIME (Content-Type) musi być ustawiona i musi być zgodny z typem MIME skonfigurowane na ResponseCompressionOptions.The MIME type (Content-Type) must be set and must match a MIME type configured on the ResponseCompressionOptions.
  • Żądanie nie może zawierać Content-Range nagłówka.The request must not include the Content-Range header.
  • Żądanie musi używać protokołu niezabezpieczonego (http), chyba że bezpiecznego protokołu (https) jest skonfigurowana w opcjach oprogramowanie pośredniczące kompresji odpowiedzi.The request must use insecure protocol (http), unless secure protocol (https) is configured in the Response Compression Middleware options. Należy zwrócić uwagę zagrożenia opisane powyżej po włączaniu bezpiecznych kompresji zawartości.Note the danger described above when enabling secure content compression.

Dodatkowe zasobyAdditional resources