Antwortkomprimierung in ASP.NET Core

Die Netzwerkbandbreite ist eine begrenzte Ressource. Eine Reduzierung der Antwortgröße steigert in der Regel die Reaktionsfähigkeit einer App, häufig sogar erheblich. Eine Möglichkeit zum Verringern der Nutzdatengrößen besteht darin, die Antworten einer App zu komprimieren.

Komprimierung mit HTTPS

Komprimierte Antworten über sichere Verbindungen können mithilfe der Option EnableForHttps gesteuert werden, die aus Sicherheitsgründen standardmäßig deaktiviert ist. Die Verwendung der Komprimierung bei dynamisch generierten Seiten kann die App für CRIME- und BREACH-Angriffe anfällig machen. CRIME- und BREACH-Angriffe können in ASP.NET Core durch fälschungssichere Token entschärft werden. Weitere Informationen finden Sie unter Prevent Cross-Site Request Forgery (XSRF/CSRF) Attacks in ASP.NET Core (Verhindern von websiteübergreifenden Anforderungsfälschungen (XSRF/CSRF) in ASP.NET Core). Informationen zur Entschärfung von BREACH-Angriffen finden Sie unter Entschärfungen unter http://www.breachattack.com/.

Selbst wenn EnableForHttps in der App deaktiviert ist, können IIS, IIS Express und Azure App Service Gzip auf dem IIS-Webserver verwenden. Achten Sie beim Überprüfen der Antwortheader auf den Wert Server. Ein unerwarteter content-encoding-Wert im Antwortheader ist möglicherweise auf den Webserver zurückzuführen und nicht auf die Konfiguration der ASP.NET Core-App.

Wann sollte Middleware zur Antwortkomprimierung verwendet werden?

Verwenden Sie serverbasierte Technologien für die Antwortkomprimierung in IIS, Apache oder Nginx. Die Leistung der Middleware für die Antwortkomprimierung entspricht wahrscheinlich nicht der Leistung der Servermodule. HTTP.sys-Server und Kestrel-Server bieten derzeit keine integrierte Komprimierungsunterstützung.

Verwenden Sie Middleware für die Antwortkomprimierung, wenn Folgendes auf die App zutrifft:

Antwortkomprimierung

Normalerweise ist eine Komprimierung für jede Antwort von Vorteil, die nicht nativ komprimiert wird. Nicht nativ komprimiert sind in der Regel CSS-, JavaScript-, HTML-, XML- und JSON-Antworten. Komprimieren Sie keine nativ komprimierten Inhalte, wie z. B. PNG-Dateien. Bei dem Versuch, eine nativ komprimierte Antwort weiter zu komprimieren, wird jede noch so kleine zusätzliche Verringerung in Bezug auf Größe und Übertragungszeit wahrscheinlich durch die Zeit aufgehoben, die zur Verarbeitung der Komprimierung benötigt wird. Komprimieren Sie keine Dateien, die kleiner als etwa 150–1.000 Byte sind, je nach Inhalt der Datei und Effizienz der Komprimierung. Der Mehraufwand bei der Komprimierung kleiner Dateien kann dazu führen, dass die komprimierte Datei größer ist als die nicht komprimierte Datei.

Wenn ein Client komprimierte Inhalte verarbeiten kann, muss er den Server hierüber informieren, indem er den Accept-Encoding-Header mit der Anforderung sendet. Wenn ein Server komprimierte Inhalte sendet, muss er im Content-Encoding-Header angeben, wie die komprimierte Antwort codiert ist. Die von der Middleware für die Antwortkomprimierung unterstützten Inhaltscodierungsbezeichnungen sind in der folgenden Tabelle aufgeführt.

Accept-Encoding-Headerwerte Middleware unterstützt Beschreibung
br Ja (Standard) Mit Brotli komprimiertes Datenformat
deflate Nein Mit DEFLATE komprimiertes Datenformat
exi Nein W3C Efficient XML Interchange
gzip Ja Gzip-Dateiformat
identity Ja Bezeichner „Keine Codierung“: Die Antwort darf nicht codiert werden.
pack200-gzip Nein Netzwerkübertragungsformat für Java-Archive
* Ja Alle verfügbaren Inhaltscodierungen, die nicht explizit angefordert wurden

Weitere Informationen finden Sie in der offiziellen Inhaltscodierungsliste der IANA.

Die Middleware für die Antwortkomprimierung ermöglicht das Hinzufügen zusätzlicher Komprimierungsanbieter für benutzerdefinierte Accept-Encoding-Headerwerte. Weitere Informationen finden Sie unter Benutzerdefinierte Anbieter in diesem Artikel.

Die Middleware für die Antwortkomprimierung ist in der Lage, auf die Gewichtung des Qualitätswerts (qvalue, q) zu reagieren, wenn dieser vom Client gesendet wird, um Komprimierungsverfahren zu priorisieren. Weitere Informationen finden Sie unter RFC 9110: Accept-Encoding.

Bei Komprimierungsalgorithmen muss ein Kompromiss zwischen der Komprimierungsgeschwindigkeit und der Effektivität der Komprimierung gefunden werden. Effektivität bezieht sich in diesem Zusammenhang auf die Größe der Ausgabe nach der Komprimierung. Die kleinste Größe wird durch die optimale Komprimierung erreicht.

Die Header, die beim Anfordern, Senden, Zwischenspeichern und Empfangen von komprimierten Inhalten verwendet werden, werden in der folgenden Tabelle beschrieben.

Header Role
Accept-Encoding Wird vom Client an den Server gesendet, um die für den Client akzeptablen Inhaltscodierungsverfahren anzugeben.
Content-Encoding Wird vom Server an den Client gesendet, um die Inhaltscodierung der Nutzdaten anzugeben.
Content-Length Bei der Komprimierung wird der Content-Length-Header entfernt, da sich der Textinhalt ändert, wenn die Antwort komprimiert wird.
Content-MD5 Wenn eine Komprimierung stattfindet, wird der Content-MD5-Header entfernt, da sich der Textinhalt geändert hat und der Hash nicht länger gültig ist.
Content-Type Gibt den MIME-Typ des Inhalts an. In jeder Antwort sollte der Content-Type angegeben werden. Die Middleware für die Antwortkomprimierung überprüft anhand dieses Werts, ob die Antwort komprimiert werden soll. Die Middleware für die Antwortkomprimierung gibt einen Satz von Standard-MIME-Typen an, die sie codieren kann. Diese können ersetzt oder um weitere MIME-Typen ergänzt werden.
Vary Wenn der Server den Wert Accept-Encoding an Clients und Proxys sendet, zeigt der Vary-Header dem Client oder Proxy an, dass er Antworten basierend auf dem Accept-Encoding-Headerwert der Anforderung zwischenspeichern (variieren) soll. Die Rückgabe von Inhalten mit dem Vary: Accept-Encoding-Header hat zur Folge, dass sowohl komprimierte als auch nicht komprimierte Antworten separat zwischengespeichert werden.

Erkunden Sie die Features der Middleware für die Antwortkomprimierung mit der Beispiel-App. Das Beispiel veranschaulicht Folgendes:

  • Komprimierung von App-Antworten mithilfe von Gzip und benutzerdefinierten Komprimierungsanbietern
  • Vorgehensweise zum Hinzufügen eines MIME-Typs zur Standardliste der MIME-Typen für die Komprimierung
  • Vorgehensweise zum Hinzufügen eines benutzerdefinierten Anbieters für die Antwortkomprimierung

Konfiguration

Der folgende Code zeigt, wie die Middleware zur Antwortkomprimierung für die standardmäßigen MIME-Typen und Komprimierungsanbieter (Brotli und Gzip) aktiviert werden kann:

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddResponseCompression(options =>
{
    options.EnableForHttps = true;
});

var app = builder.Build();

app.UseResponseCompression();

app.MapGet("/", () => "Hello World!");

app.Run();

Hinweise:

Senden Sie eine Anforderung ohne Accept-Encoding-Header an die Beispiel-App, und beachten Sie, dass die Antwort nicht komprimiert wird. Der Content-Encoding-Header ist nicht in der Sammlung der Antwortheader enthalten.

Gehen Sie z. B. in Firefox für Entwickler*innen so vor:

  • Wählen Sie die Registerkarte „Netzwerk“ aus.
  • Klicken Sie in der Liste der Netzwerkanforderungen mit der rechten Maustaste auf die Anforderung, und wählen Sie Bearbeiten und erneut senden aus.
  • Ändern Sie Accept-Encoding: von gzip, deflate, br in none.
  • Wählen Sie Senden aus.

Senden Sie über einen Browser mit Verwendung der Entwicklertools eine Anforderung an die Beispiel-App, und beachten Sie, dass die Antwort komprimiert wird. Die Content-Encoding- und Vary-Header sind in der Antwort enthalten.

Anbieter

Komprimierungsanbieter Brotli und Gzip

Verwenden Sie den BrotliCompressionProvider, um Antworten mit dem komprimierten Brotli-Datenformat zu komprimieren.

Wenn der CompressionProviderCollectionnicht explizit Komprimierungsanbieter hinzugefügt werden:

  • Der Brotli-Komprimierungsanbieter und der Gzip-Komprimierungsanbieter werden standardmäßig dem Array der Komprimierungsanbieter hinzugefügt.
  • Die Komprimierung wird standardmäßig auf die Brotli-Komprimierung festgelegt, wenn das komprimierte Brotli-Datenformat vom Client unterstützt wird. Wenn Brotli vom Client nicht unterstützt wird, erfolgt die Komprimierung standardmäßig mit Gzip, sofern der Client die Gzip-Komprimierung unterstützt.

Hinweis

Dokumentationslinks zur .NET-Referenzquelle laden in der Regel den Standardbranch des Repositorys, der die aktuelle Entwicklung für das nächste Release von .NET darstellt. Um ein Tag für ein bestimmtes Release auszuwählen, wählen Sie diesen mit der Dropdownliste Switch branches or tags (Branches oder Tags wechseln) aus. Weitere Informationen finden Sie unter How to select a version tag of ASP.NET Core source code (dotnet/AspNetCore.Docs #26205) (Auswählen eines Versionstags von ASP.NET Core-Quellcode (dotnet/AspNetCore.Docs #26205)).

Wird ein Komprimierungsanbieter hinzugefügt, werden keine anderen Anbieter hinzugefügt. Wenn beispielsweise der Gzip-Komprimierungsanbieter der einzige explizit hinzugefügte Anbieter ist, werden keine weiteren Komprimierungsanbieter hinzugefügt.

Der folgende Code führt folgende Aktionen aus:

  • Aktiviert die Antwortkomprimierung für HTTPS-Anforderungen.
  • Fügt die Antwortkomprimierungsanbieter Brotli und Gzip hinzu.
using System.IO.Compression;
using Microsoft.AspNetCore.ResponseCompression;

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddResponseCompression(options =>
{
    options.EnableForHttps = true;
    options.Providers.Add<BrotliCompressionProvider>();
    options.Providers.Add<GzipCompressionProvider>();
});

builder.Services.Configure<BrotliCompressionProviderOptions>(options =>
{
    options.Level = CompressionLevel.Fastest;
});

builder.Services.Configure<GzipCompressionProviderOptions>(options =>
{
    options.Level = CompressionLevel.SmallestSize;
});

var app = builder.Build();

app.UseResponseCompression();

app.MapGet("/", () => "Hello World!");

app.Run();

Legen Sie den Komprimierungsgrad mit BrotliCompressionProviderOptions und GzipCompressionProviderOptions fest. Die Komprimierungsanbieter Brotli und Gzip verwenden standardmäßig den schnellsten Komprimierungsgrad, CompressionLevel.Fastest, der möglicherweise nicht die effizienteste Komprimierung liefert. Wenn eine möglichst effiziente Komprimierung gewünscht wird, konfigurieren Sie die Middleware zur Antwortkomprimierung für eine optimale Komprimierung.

Werte, die angeben, ob bei einem Komprimierungsvorgang die Geschwindigkeit oder die Komprimierungsgröße im Vordergrund steht, finden Sie in der CompressionLevel-Enumeration.

using System.IO.Compression;
using Microsoft.AspNetCore.ResponseCompression;

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddResponseCompression(options =>
{
    options.EnableForHttps = true;
    options.Providers.Add<BrotliCompressionProvider>();
    options.Providers.Add<GzipCompressionProvider>();
});

builder.Services.Configure<BrotliCompressionProviderOptions>(options =>
{
    options.Level = CompressionLevel.Fastest;
});

builder.Services.Configure<GzipCompressionProviderOptions>(options =>
{
    options.Level = CompressionLevel.SmallestSize;
});

var app = builder.Build();

app.UseResponseCompression();

app.MapGet("/", () => "Hello World!");

app.Run();

Benutzerdefinierte Anbieter

Erstellen Sie mit ICompressionProvider benutzerdefinierte Implementierungen für die Komprimierung. EncodingName steht für die Inhaltscodierung, die dieser ICompressionProvider erzeugt. Die Middleware für die Antwortkomprimierung verwendet diese Informationen, um den Anbieter anhand der in der im Accept-Encoding-Header der Anforderung angegebenen Liste auszuwählen.

Anforderungen an die Beispiel-App mit dem Accept-Encoding: mycustomcompression-Header geben eine Antwort mit einem Content-Encoding: mycustomcompression-Header zurück. Der Client muss in der Lage sein, die benutzerdefinierte Codierung zu dekomprimieren, damit eine benutzerdefinierte Komprimierungsimplementierung funktionieren kann.

using Microsoft.AspNetCore.ResponseCompression;

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddResponseCompression(options =>
{
    options.Providers.Add<BrotliCompressionProvider>();
    options.Providers.Add<GzipCompressionProvider>();
    options.Providers.Add<CustomCompressionProvider>();
});

var app = builder.Build();

app.UseResponseCompression();

app.MapGet("/", () => "Hello World!");

app.Run();
using Microsoft.AspNetCore.ResponseCompression;

public class CustomCompressionProvider : ICompressionProvider
{
    public string EncodingName => "mycustomcompression";
    public bool SupportsFlush => true;

    public Stream CreateStream(Stream outputStream)
    {
        // Replace with a custom compression stream wrapper.
        return outputStream;
    }
}

Mit dem vorangehenden Code wird der Antworttext nicht durch das Beispiel komprimiert. Das Beispiel zeigt jedoch, wo ein benutzerdefinierter Komprimierungsalgorithmus implementiert werden kann.

MIME-Typen

Die Middleware für die Antwortkomprimierung gibt einen Standardsatz von MIME-Typen für die Komprimierung an. Eine vollständige Liste der unterstützten MIME-Typen finden Sie im Quellcode.

Hinweis

Dokumentationslinks zur .NET-Referenzquelle laden in der Regel den Standardbranch des Repositorys, der die aktuelle Entwicklung für das nächste Release von .NET darstellt. Um ein Tag für ein bestimmtes Release auszuwählen, wählen Sie diesen mit der Dropdownliste Switch branches or tags (Branches oder Tags wechseln) aus. Weitere Informationen finden Sie unter How to select a version tag of ASP.NET Core source code (dotnet/AspNetCore.Docs #26205) (Auswählen eines Versionstags von ASP.NET Core-Quellcode (dotnet/AspNetCore.Docs #26205)).

Mit ResponseCompressionOptions.MimeTypes können Sie MIME-Typen ersetzen oder anfügen. Beachten Sie, dass MIME-Typen mit Platzhaltern (wie z. B. text/*) nicht unterstützt werden. Die Beispiel-App fügt einen MIME-Typ für image/svg+xml hinzu und komprimiert und verarbeitet das ASP.NET Core-Bannerbild banner.svg.

using Microsoft.AspNetCore.ResponseCompression;
using ResponseCompressionSample;

var builder = WebApplication.CreateBuilder(args);

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

var app = builder.Build();

app.UseResponseCompression();

Hinzufügen des Vary-Headers

Beim Komprimieren von Antworten auf Grundlage des Accept-Encoding-Anforderungsheaders kann es nicht komprimierte und mehrere komprimierte Versionen der Antwort geben. Um den Client- und Proxycaches mitzuteilen, dass mehrere Versionen vorhanden sind und gespeichert werden sollen, wird der Vary-Header mit einem Accept-Encoding-Wert ergänzt. Die Middleware für die Antwort fügt den Vary-Header automatisch hinzu, wenn die Antwort komprimiert wird.

Hinweis

Dokumentationslinks zur .NET-Referenzquelle laden in der Regel den Standardbranch des Repositorys, der die aktuelle Entwicklung für das nächste Release von .NET darstellt. Um ein Tag für ein bestimmtes Release auszuwählen, wählen Sie diesen mit der Dropdownliste Switch branches or tags (Branches oder Tags wechseln) aus. Weitere Informationen finden Sie unter How to select a version tag of ASP.NET Core source code (dotnet/AspNetCore.Docs #26205) (Auswählen eines Versionstags von ASP.NET Core-Quellcode (dotnet/AspNetCore.Docs #26205)).

Issue für Middleware bei Einsatz hinter einem Nginx-Reverseproxy

Wird eine Anforderung durch einen Nginx-Proxy verarbeitet, wird der Accept-Encoding-Header entfernt. Das Entfernen des Accept-Encoding-Headers verhindert, dass die Middleware für die Antwortkomprimierung die Antwort komprimiert. Weitere Informationen finden Sie unter NGINX: Komprimierung und Dekomprimierung. Dieses Issue wird unter Ermitteln der Passthrough-Komprimierung für Nginx (dotnet/aspnetcore#5989) nachverfolgt.

Deaktivieren der dynamischen IIS-Komprimierung

Informationen zum Deaktivieren des auf Serverebene konfigurierten IIS-Moduls für die dynamische Komprimierung finden Sie unter Deaktivieren von IIS-Modulen.

Problembehandlung bei der Antwortkomprimierung

Verwenden Sie z. B. die Firefox-Browser-Entwicklungstools, mit denen Sie den Accept-Encoding-Anforderungsheader festlegen sowie Antwortheader, Größe und Text untersuchen können. Standardmäßig komprimiert die Middleware für die Antwortkomprimierung Antworten, die die folgenden Bedingungen erfüllen:

  • Der Accept-Encoding-Header weist den Wert br, gzip, * oder eine benutzerdefinierte Codierung auf, die einem benutzerdefinierten Komprimierungsanbieter entspricht. Der Wert darf nicht identity lauten oder einen Qualitätswert (qvalue, q) von 0 (Null) aufweisen.
  • Der MIME-Typ (Content-Type) muss festgelegt werden und mit einem der in ResponseCompressionOptions konfigurierten MIME-Typen übereinstimmen.
  • Die Anforderung darf nicht den Header Content-Range enthalten.
  • Die Anforderung muss ein unsicheres Protokoll (HTTP) verwenden – es sei denn, in den Optionen der Middleware für die Antwortkomprimierung ist ein sicheres Protokoll (HTTPS) konfiguriert. Beachten Sie die oben beschriebenen Risiken, wenn Sie die sichere Inhaltskomprimierung aktivieren.

Von Azure bereitgestelltes Beispiel

Die in Azure bereitgestellte Beispiel-App umfasst die folgende Datei Program.cs:

using Microsoft.AspNetCore.ResponseCompression;
using ResponseCompressionSample;

var builder = WebApplication.CreateBuilder(args);

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

var app = builder.Build();

app.UseResponseCompression();

app.Map("/trickle", async (HttpResponse httpResponse) =>
{
    httpResponse.ContentType = "text/plain;charset=utf-8";

    for (int i = 0; i < 20; i++)
    {
        await httpResponse.WriteAsync("a");
        await httpResponse.Body.FlushAsync();
        await Task.Delay(TimeSpan.FromMilliseconds(50));
    }
});

app.Map("/testfile1kb.txt", () => Results.File(
    app.Environment.ContentRootFileProvider.GetFileInfo("testfile1kb.txt").PhysicalPath,
    "text/plain;charset=utf-8"));

app.Map("/banner.svg", () => Results.File(
    app.Environment.ContentRootFileProvider.GetFileInfo("banner.svg").PhysicalPath,
    "image/svg+xml;charset=utf-8"));

app.MapFallback(() => LoremIpsum.Text);

app.Run();

Zusätzliche Ressourcen

Hinweis

Dokumentationslinks zur .NET-Referenzquelle laden in der Regel den Standardbranch des Repositorys, der die aktuelle Entwicklung für das nächste Release von .NET darstellt. Um ein Tag für ein bestimmtes Release auszuwählen, wählen Sie diesen mit der Dropdownliste Switch branches or tags (Branches oder Tags wechseln) aus. Weitere Informationen finden Sie unter How to select a version tag of ASP.NET Core source code (dotnet/AspNetCore.Docs #26205) (Auswählen eines Versionstags von ASP.NET Core-Quellcode (dotnet/AspNetCore.Docs #26205)).

Die Netzwerkbandbreite ist eine begrenzte Ressource. Eine Reduzierung der Antwortgröße steigert in der Regel die Reaktionsfähigkeit einer App, häufig sogar erheblich. Eine Möglichkeit zum Verringern der Nutzdatengrößen besteht darin, die Antworten einer App zu komprimieren.

Anzeigen oder Herunterladen von Beispielcode (Vorgehensweise zum Herunterladen)

Wann sollte Middleware zur Antwortkomprimierung verwendet werden?

Verwenden Sie serverbasierte Technologien für die Antwortkomprimierung in IIS, Apache oder Nginx. Die Leistung der Middleware entspricht wahrscheinlich nicht der Leistung der Servermodule. HTTP.sys-Server und Kestrel-Server bieten derzeit keine integrierte Komprimierungsunterstützung.

Verwenden Sie Middleware für die Antwortkomprimierung, wenn Folgendes zutrifft:

Antwortkomprimierung

Normalerweise ist eine Komprimierung für jede Antwort von Vorteil, die nicht nativ komprimiert wird. Nicht nativ komprimiert sind in der Regel CSS-, JavaScript-, HTML-, XML- und JSON-Antworten. Sie sollten keine nativ komprimierten Inhalte komprimieren, wie z. B. PNG-Dateien. Wenn Sie versuchen, eine nativ komprimierte Antwort weiter zu komprimieren, wird jede noch so kleine zusätzliche Verringerung in Bezug auf Größe und Übertragungszeit wahrscheinlich durch die Zeit aufgehoben, die zur Verarbeitung der Komprimierung benötigt wird. Komprimieren Sie keine Dateien, die kleiner als etwa 150–1.000 Byte sind (je nach Inhalt der Datei und Effizienz der Komprimierung). Der Mehraufwand bei der Komprimierung kleiner Dateien kann dazu führen, dass die komprimierte Datei größer ist als die nicht komprimierte Datei.

Wenn ein Client komprimierte Inhalte verarbeiten kann, muss er den Server hierüber informieren, indem er den Accept-Encoding-Header mit der Anforderung sendet. Wenn ein Server komprimierte Inhalte sendet, muss er im Content-Encoding-Header angeben, wie die komprimierte Antwort codiert ist. Die von der Middleware unterstützten Inhaltscodierungsbezeichnungen sind in der folgenden Tabelle aufgeführt.

Accept-Encoding-Headerwerte Middleware unterstützt Beschreibung
br Ja (Standard) Mit Brotli komprimiertes Datenformat
deflate Nein Mit DEFLATE komprimiertes Datenformat
exi Nein W3C Efficient XML Interchange
gzip Ja Gzip-Dateiformat
identity Ja Bezeichner „Keine Codierung“: Die Antwort darf nicht codiert werden.
pack200-gzip Nein Netzwerkübertragungsformat für Java-Archive
* Ja Alle verfügbaren Inhaltscodierungen, die nicht explizit angefordert wurden

Weitere Informationen finden Sie in der offiziellen Inhaltscodierungsliste der IANA.

Die Middleware ermöglicht es Ihnen, zusätzliche Komprimierungsanbieter für benutzerdefinierte Accept-Encoding-Headerwerte hinzuzufügen. Weitere Informationen finden Sie unter Benutzerdefinierte Anbieter weiter unten.

Die Middleware ist in der Lage, auf die Gewichtung des Qualitätswerts (qvalue, q) zu reagieren, wenn dieser vom Client gesendet wird, um Komprimierungsverfahren zu priorisieren. Weitere Informationen finden Sie unter RFC 9110: Accept-Encoding.

Bei Komprimierungsalgorithmen muss ein Kompromiss zwischen der Komprimierungsgeschwindigkeit und der Effektivität der Komprimierung gefunden werden. Effektivität bezieht sich in diesem Zusammenhang auf die Größe der Ausgabe nach der Komprimierung. Die kleinste Größe wird durch die optimale Komprimierung erreicht.

Die Header, die beim Anfordern, Senden, Zwischenspeichern und Empfangen von komprimierten Inhalten verwendet werden, werden in der Tabelle unten beschrieben.

Header Role
Accept-Encoding Wird vom Client an den Server gesendet, um die für den Client akzeptablen Inhaltscodierungsverfahren anzugeben.
Content-Encoding Wird vom Server an den Client gesendet, um die Inhaltscodierung der Nutzdaten anzugeben.
Content-Length Bei der Komprimierung wird der Content-Length-Header entfernt, da sich der Textinhalt ändert, wenn die Antwort komprimiert wird.
Content-MD5 Wenn eine Komprimierung stattfindet, wird der Content-MD5-Header entfernt, da sich der Textinhalt geändert hat und der Hash nicht länger gültig ist.
Content-Type Gibt den MIME-Typ des Inhalts an. In jeder Antwort sollte der Content-Type angegeben werden. Die Middleware überprüft anhand dieses Werts, ob die Antwort komprimiert werden soll. Die Middleware gibt einen Satz von Standard-MIME-Typen an, die sie codieren kann. Diese können jedoch ersetzt oder um weitere MIME-Typen ergänzt werden.
Vary Wenn der Server den Wert Accept-Encoding an Clients und Proxys sendet, zeigt der Vary-Header dem Client oder Proxy an, dass er Antworten basierend auf dem Accept-Encoding-Headerwert der Anforderung zwischenspeichern (variieren) soll. Die Rückgabe von Inhalten mit dem Vary: Accept-Encoding-Header hat zur Folge, dass sowohl komprimierte als auch nicht komprimierte Antworten separat zwischengespeichert werden.

Erkunden Sie die Features der Middleware für die Antwortkomprimierung mit der Beispiel-App. Das Beispiel veranschaulicht Folgendes:

  • Komprimierung von App-Antworten mithilfe von Gzip und benutzerdefinierten Komprimierungsanbietern
  • Vorgehensweise zum Hinzufügen eines MIME-Typs zur Standardliste der MIME-Typen für die Komprimierung

Konfiguration

Der folgende Code zeigt, wie die Middleware zur Antwortkomprimierung für die standardmäßigen MIME-Typen und Komprimierungsanbieter (Brotli und Gzip) aktiviert werden kann:

public class Startup
{
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddResponseCompression();
    }

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

Hinweise:

  • app.UseResponseCompression muss vor jeglicher Middleware für die Antwortkomprimierung aufgerufen werden. Weitere Informationen finden Sie unter ASP.NET Core-Middleware.
  • Verwenden Sie ein Tool wie Fiddler oder Firefox-Browser-Entwicklungstools, um den Accept-Encoding-Anforderungsheader festzulegen sowie Antwortheader, Größe und Text zu untersuchen.

Senden Sie eine Anforderung ohne Accept-Encoding-Header an die Beispiel-App, und beachten Sie, dass die Antwort nicht komprimiert wird. Die Content-Encoding- und Vary-Header sind nicht in der Antwort enthalten.

Fiddler window showing result of a request without the Accept-Encoding header. The response isn't compressed.

Übermitteln Sie eine Anforderung mit Accept-Encoding: br-Header (Brotli-Komprimierung) an die Beispiel-App, und beachten Sie, dass die Antwort komprimiert wird. Die Content-Encoding- und Vary-Header sind in der Antwort enthalten.

Fiddler window showing result of a request with the Accept-Encoding header and a value of br. The Vary and Content-Encoding headers are added to the response. The response is compressed.

Anbieter

Brotli-Komprimierungsanbieter

Verwenden Sie den BrotliCompressionProvider, um Antworten mit dem komprimierten Brotli-Datenformat zu komprimieren.

Wenn CompressionProviderCollection nicht explizit Komprimierungsanbieter hinzugefügt werden:

  • Der Brotli-Komprimierungsanbieter wird standardmäßig zusammen mit dem Gzip-Komprimierungsanbieter dem Array der Komprimierungsanbieter hinzugefügt.
  • Die Komprimierung wird standardmäßig auf die Brotli-Komprimierung festgelegt, wenn das komprimierte Brotli-Datenformat vom Client unterstützt wird. Wenn Brotli vom Client nicht unterstützt wird, erfolgt die Komprimierung standardmäßig mit Gzip, sofern der Client die Gzip-Komprimierung unterstützt.
public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression();
}

Der Brotli-Komprimierungsanbieter muss hinzugefügt werden, wenn Komprimierungsanbieter explizit hinzugefügt werden:

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

Legen Sie den Komprimierungsgrad mit BrotliCompressionProviderOptions fest. Der Brotli-Komprimierungsanbieter verwendet standardmäßig den schnellsten Komprimierungsgrad (CompressionLevel.Fastest), der möglicherweise nicht die effizienteste Komprimierung liefert. Wenn eine möglichst effiziente Komprimierung gewünscht wird, konfigurieren Sie die Middleware für eine optimale Komprimierung.

Compression Level Beschreibung
CompressionLevel.Fastest Die Komprimierung soll so schnell wie möglich abgeschlossen werden, auch wenn die resultierende Ausgabe nicht optimal komprimiert ist.
CompressionLevel.NoCompression Es soll keine Komprimierung durchgeführt werden.
CompressionLevel.Optimal Die Antworten sollen optimal komprimiert werden, auch wenn die Komprimierung mehr Zeit in Anspruch nimmt.
public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression();

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

Gzip-Komprimierungsanbieter

Verwenden Sie den GzipCompressionProvider, um Antworten mit dem Gzip-Dateiformat zu komprimieren.

Wenn CompressionProviderCollection nicht explizit Komprimierungsanbieter hinzugefügt werden:

  • Der Gzip-Komprimierungsanbieter wird standardmäßig zusammen mit dem Brotli-Komprimierungsanbieter dem Array der Komprimierungsanbieter hinzugefügt.
  • Die Komprimierung wird standardmäßig auf die Brotli-Komprimierung festgelegt, wenn das komprimierte Brotli-Datenformat vom Client unterstützt wird. Wenn Brotli vom Client nicht unterstützt wird, erfolgt die Komprimierung standardmäßig mit Gzip, sofern der Client die Gzip-Komprimierung unterstützt.
public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression();
}

Der Gzip-Komprimierungsanbieter muss hinzugefügt werden, wenn Komprimierungsanbieter explizit hinzugefügt werden:

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

Legen Sie den Komprimierungsgrad mit GzipCompressionProviderOptions fest. Der Gzip-Komprimierungsanbieter verwendet standardmäßig den schnellsten Komprimierungsgrad (CompressionLevel.Fastest), der möglicherweise nicht die effizienteste Komprimierung liefert. Wenn eine möglichst effiziente Komprimierung gewünscht wird, konfigurieren Sie die Middleware für eine optimale Komprimierung.

Compression Level Beschreibung
CompressionLevel.Fastest Die Komprimierung soll so schnell wie möglich abgeschlossen werden, auch wenn die resultierende Ausgabe nicht optimal komprimiert ist.
CompressionLevel.NoCompression Es soll keine Komprimierung durchgeführt werden.
CompressionLevel.Optimal Die Antworten sollen optimal komprimiert werden, auch wenn die Komprimierung mehr Zeit in Anspruch nimmt.
public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression();

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

Benutzerdefinierte Anbieter

Erstellen Sie mit ICompressionProvider benutzerdefinierte Implementierungen für die Komprimierung. EncodingName steht für die Inhaltscodierung, die dieser ICompressionProvider erzeugt. Die Middleware verwendet diese Informationen, um den Anbieter anhand der in der im Accept-Encoding-Header der Anforderung angegebenen Liste auszuwählen.

Bei Verwendung der Beispiel-App sendet der Client eine Anforderung mit dem Accept-Encoding: mycustomcompression-Header. Die Middleware verwendet die benutzerdefinierte Komprimierungsimplementierung und gibt die Antwort mit einem Content-Encoding: mycustomcompression-Header zurück. Der Client muss in der Lage sein, die benutzerdefinierte Codierung zu dekomprimieren, damit eine benutzerdefinierte Komprimierungsimplementierung funktionieren kann.

public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression(options =>
    {
        options.Providers.Add<BrotliCompressionProvider>();
        options.Providers.Add<GzipCompressionProvider>();
        options.Providers.Add<CustomCompressionProvider>();
        options.MimeTypes = 
            ResponseCompressionDefaults.MimeTypes.Concat(
                new[] { "image/svg+xml" });
    });
}
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;
    }
}

Senden Sie eine Anforderung mit Accept-Encoding: mycustomcompression-Header an die Beispiel-App, und überprüfen Sie die Antwortheader. Die Vary- und Content-Encoding-Header sind in der Antwort enthalten. Der Antworttext (nicht dargestellt) wird im Beispiel nicht komprimiert. Die Klasse CustomCompressionProvider des Beispiels enthält keine Komprimierungsimplementierung. Das Beispiel zeigt jedoch, wo Sie einen solchen Komprimierungsalgorithmus implementieren würden.

Fiddler window showing result of a request with the Accept-Encoding header and a value of mycustomcompression. The Vary and Content-Encoding headers are added to the response.

MIME-Typen

Die Middleware gibt einen Standardsatz von MIME-Typen für die Komprimierung an:

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

Anhand der Optionen für die Middleware zur Antwortkomprimierung können Sie MIME-Typen ersetzen oder anfügen. Beachten Sie, dass MIME-Typen mit Platzhaltern (wie z. B. text/*) nicht unterstützt werden. Die Beispiel-App fügt einen MIME-Typ für image/svg+xml hinzu und komprimiert und verarbeitet das ASP.NET Core-Bannerbild (banner.svg).

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

Komprimierung mit sicherem Protokoll

Komprimierte Antworten über sichere Verbindungen können mithilfe der Option EnableForHttps gesteuert werden, die standardmäßig deaktiviert ist. Die Verwendung der Komprimierung bei dynamisch generierten Seiten kann zu Sicherheitsproblemen führen und die App z. B. für CRIME- und BREACH-Angriffe anfällig machen.

Hinzufügen des Vary-Headers

Beim Komprimieren von Antworten auf Grundlage des Accept-Encoding-Headers kann es nicht komprimierte und mehrere komprimierte Versionen der Antwort geben. Um den Client- und Proxycaches mitzuteilen, dass mehrere Versionen vorhanden sind und gespeichert werden sollen, wird der Vary-Header mit einem Accept-Encoding-Wert ergänzt. In ASP.NET Core 2.0 oder höher fügt die Middleware den Vary-Header automatisch hinzu, wenn die Antwort komprimiert wird.

Issue für Middleware bei Einsatz hinter einem Nginx-Reverseproxy

Wird eine Anforderung durch einen Nginx-Proxy verarbeitet, wird der Accept-Encoding-Header entfernt. Das Entfernen des Accept-Encoding-Headers verhindert, dass die Middleware die Antwort komprimiert. Weitere Informationen finden Sie unter NGINX: Komprimierung und Dekomprimierung. Dieses Issue wird unter Ermitteln der Passthrough-Komprimierung für Nginx (dotnet/aspnetcore#5989) nachverfolgt.

Arbeiten mit der dynamischen IIS-Komprimierung

Wenn ein aktives Modul für die dynamische IIS-Komprimierung auf Serverebene konfiguriert wurde und Sie dieses für eine App deaktivieren möchten, deaktivieren Sie das Modul mit einem Zusatz in der Datei web.config. Weitere Informationen finden Sie unter Disabling IIS modules (Deaktivieren von IIS-Modulen).

Problembehandlung

Verwenden Sie ein Tool wie Fiddler oder die Firefox-Browser-Entwicklungstools, mit denen Sie den Accept-Encoding-Anforderungsheader festlegen sowie Antwortheader, Größe und Text untersuchen können. Standardmäßig komprimiert die Middleware für die Antwortkomprimierung Antworten, die die folgenden Bedingungen erfüllen:

  • Der Header Accept-Encoding weist einen Wert br, gzip, * oder eine benutzerdefinierte Codierung auf, die einem von Ihnen festgelegten benutzerdefinierten Komprimierungsanbieter entspricht. Der Wert darf nicht identity lauten oder einen Qualitätswert (qvalue, q) von 0 (Null) aufweisen.
  • Der MIME-Typ (Content-Type) muss festgelegt werden und mit einem der in ResponseCompressionOptions konfigurierten MIME-Typen übereinstimmen.
  • Die Anforderung darf nicht den Header Content-Range enthalten.
  • Die Anforderung muss ein unsicheres Protokoll (HTTP) verwenden – es sei denn, in den Optionen der Middleware für die Antwortkomprimierung ist ein sicheres Protokoll (HTTPS) konfiguriert. Beachten Sie die oben beschriebenen Risiken, wenn Sie die sichere Inhaltskomprimierung aktivieren.

Zusätzliche Ressourcen