Verwenden von Hostingstartassemblys in ASP.NET Core
Hinweis
Dies ist nicht die neueste Version dieses Artikels. Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.
Warnung
Diese Version von ASP.NET Core wird nicht mehr unterstützt. Weitere Informationen finden Sie in der Supportrichtlinie für .NET und .NET Core. Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.
Wichtig
Diese Informationen beziehen sich auf ein Vorabversionsprodukt, das vor der kommerziellen Freigabe möglicherweise noch wesentlichen Änderungen unterliegt. Microsoft gibt keine Garantie, weder ausdrücklich noch impliziert, hinsichtlich der hier bereitgestellten Informationen.
Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.
Von Pavel Krymets
Mit einer IHostingStartup-Implementierung (Hostingstart) werden Verbesserungen an einer App beim Start von einer externen Assembly aus vorgenommen. Eine externe Bibliothek kann beispielsweise eine Hostingstartimplementierung verwenden, um zusätzliche Konfigurationsanbieter oder -dienste für eine App bereitzustellen.
Anzeigen oder Herunterladen von Beispielcode (Vorgehensweise zum Herunterladen)
Das Attribut HostingStartup
Ein HostingStartup-Attribut gibt an, ob eine Hostingstartassembly vorhanden ist, die zur Laufzeit aktiviert werden kann.
Bei der Einstiegsassembly oder bei der Assembly, die die Klasse Startup
enthält, wird automatisch geprüft, ob sie das Attribut HostingStartup
enthält. Die Liste der Assemblys für die Suche nach HostingStartup
-Attributen wird zur Laufzeit aus der Konfiguration in WebHostDefaults.HostingStartupAssembliesKey geladen. Die Liste der Assemblys, die aus der Ermittlung ausgeschlossen werden sollen, wird aus WebHostDefaults.HostingStartupExcludeAssembliesKey geladen.
Im folgenden Beispiel lautet der Namespace der Hostingstartassembly StartupEnhancement
. StartupEnhancementHostingStartup
ist die Klasse mit dem Hostingstartcode:
[assembly: HostingStartup(typeof(StartupEnhancement.StartupEnhancementHostingStartup))]
Das Attribut HostingStartup
befindet sich in der Regel in der IHostingStartup
-Implementierungsklassendatei der Hostingstartassembly.
Ermitteln geladener Hostingstartassemblys
Zum Ermitteln von geladenen Hostingstartassemblys aktivieren Sie die Protokollierung und überprüfen die Protokolle der App. Fehler, die beim Laden von Assemblys auftreten, werden protokolliert. Geladene Hostingstartassemblys werden auf der Debugebene protokolliert. Außerdem werden alle Fehler protokolliert.
Deaktivieren des automatischen Ladens von Hostingstartassemblys
Um das automatische Laden von Hostingstartassemblys zu deaktivieren, verwenden Sie einen der folgenden Ansätze:
Um zu verhindern, dass alle Hostingstartassemblys geladen werden, legen Sie eine der folgenden Einstellungen auf
true
oder1
fest:Hostkonfigurationseinstellung „Verhindern des Hostingstarts“:
public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseSetting( WebHostDefaults.PreventHostingStartupKey, "true") .UseStartup<Startup>(); });
Die Umgebungsvariable
ASPNETCORE_PREVENTHOSTINGSTARTUP
Um zu verhindern, dass bestimmte Hostingstartassemblys geladen werden, legen Sie eine der folgenden Einstellungen auf eine durch Semikolons getrennte Zeichenfolge mit Hostingstartassemblys fest, die beim Starten ausgeschlossen werden sollen:
Hostkonfigurationseinstellung „Hostingstartausschlussassemblys“:
public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseSetting( WebHostDefaults.HostingStartupExcludeAssembliesKey, "{ASSEMBLY1;ASSEMBLY2; ...}") .UseStartup<Startup>(); });
Der Platzhalter
{ASSEMBLY1;ASSEMBLY2; ...}
stellt die durch Semikolons getrennte Assemblyliste dar.Die Umgebungsvariable
ASPNETCORE_HOSTINGSTARTUPEXCLUDEASSEMBLIES
Wenn sowohl die Konfigurationseinstellung für den Host als auch die Umgebungsvariable festgelegt werden, wird das Verhalten durch die Hosteinstellung gesteuert.
Durch das Deaktivieren von Hostingstartassemblys mithilfe der Hosteinstellung oder der Umgebungsvariable wird die Assembly global deaktiviert. Einige Eigenschaften einer App können ebenfalls deaktiviert werden.
Projekt
Erstellen Sie einen Hostingstart mit einem der folgenden Projekttypen:
Klassenbibliothek
In einer Klassenbibliothek kann eine Hostingstarterweiterung bereitgestellt werden. Die Bibliothek enthält ein HostingStartup
-Attribut.
Der Beispielcode enthält die Razor Pages-App HostingStartupApp und die Klassenbibliothek HostingStartupLibrary. Die Klassenbibliothek:
- Enthält die Hostingstartklasse
ServiceKeyInjection
, dieIHostingStartup
implementiert.ServiceKeyInjection
fügt mithilfe des Anbieters der Konfiguration im Arbeitsspeicher (AddInMemoryCollection) der App-Konfiguration zwei Dienstzeichenfolgen hinzu. - Enthält ein
HostingStartup
-Attribut, das den Namespace und die Klasse des Hostingstarts angibt.
Die Configure-Methode der ServiceKeyInjection
-Klasse verwendet einen IWebHostBuilder, um einer App Erweiterungen hinzuzufügen.
HostingStartupLibrary/ServiceKeyInjection.cs
:
[assembly: HostingStartup(typeof(HostingStartupLibrary.ServiceKeyInjection))]
namespace HostingStartupLibrary
{
public class ServiceKeyInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
builder.ConfigureAppConfiguration(config =>
{
var dict = new Dictionary<string, string>
{
{"DevAccount_FromLibrary", "DEV_1111111-1111"},
{"ProdAccount_FromLibrary", "PROD_2222222-2222"}
};
config.AddInMemoryCollection(dict);
});
}
}
}
Die Indexseite der App liest und rendert die Konfigurationswerte für die beiden Schlüssel, die von der Hostingstartassembly der Klassenbibliothek festgelegt werden:
HostingStartupApp/Pages/Index.cshtml.cs
:
public class IndexModel : PageModel
{
public IndexModel(IConfiguration config)
{
ServiceKey_Development_Library = config["DevAccount_FromLibrary"];
ServiceKey_Production_Library = config["ProdAccount_FromLibrary"];
ServiceKey_Development_Package = config["DevAccount_FromPackage"];
ServiceKey_Production_Package = config["ProdAccount_FromPackage"];
}
public string ServiceKey_Development_Library { get; private set; }
public string ServiceKey_Production_Library { get; private set; }
public string ServiceKey_Development_Package { get; private set; }
public string ServiceKey_Production_Package { get; private set; }
public void OnGet()
{
}
}
Der Beispielcode enthält darüber hinaus auch ein NuGet-Paketprojekt, das den separaten Hostingstart HostingStartupPackage bereitstellt. Das Paket weist dieselben Merkmale wie die bereits beschriebene Klassenbibliothek auf. Das Paket:
- Enthält die Hostingstartklasse
ServiceKeyInjection
, dieIHostingStartup
implementiert.ServiceKeyInjection
fügt der App-Konfiguration zwei Dienstzeichenfolgen hinzu. - Enthält ein
HostingStartup
-Attribut.
HostingStartupPackage/ServiceKeyInjection.cs
:
[assembly: HostingStartup(typeof(HostingStartupPackage.ServiceKeyInjection))]
namespace HostingStartupPackage
{
public class ServiceKeyInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
builder.ConfigureAppConfiguration(config =>
{
var dict = new Dictionary<string, string>
{
{"DevAccount_FromPackage", "DEV_3333333-3333"},
{"ProdAccount_FromPackage", "PROD_4444444-4444"}
};
config.AddInMemoryCollection(dict);
});
}
}
}
Die Indexseite der App liest und rendert die Konfigurationswerte für die beiden Schlüssel, die von der Hostingstartassembly der Bibliothek festgelegt werden:
HostingStartupApp/Pages/Index.cshtml.cs
:
public class IndexModel : PageModel
{
public IndexModel(IConfiguration config)
{
ServiceKey_Development_Library = config["DevAccount_FromLibrary"];
ServiceKey_Production_Library = config["ProdAccount_FromLibrary"];
ServiceKey_Development_Package = config["DevAccount_FromPackage"];
ServiceKey_Production_Package = config["ProdAccount_FromPackage"];
}
public string ServiceKey_Development_Library { get; private set; }
public string ServiceKey_Production_Library { get; private set; }
public string ServiceKey_Development_Package { get; private set; }
public string ServiceKey_Production_Package { get; private set; }
public void OnGet()
{
}
}
Konsolen-App ohne Einstiegspunkt
Dieses Verfahren ist nur für .NET Core-Apps, nicht jedoch für .NET Framework verfügbar.
Eine dynamische Hostingstarterweiterung, die zur Aktivierung keinen Kompilierungszeitverweis erfordert, kann in einer Konsolen-App ohne Einstiegspunkt bereitgestellt werden, die ein HostingStartup
-Attribut enthält. Durch die Veröffentlichung der Konsolen-App wird eine Hostingstartassembly erstellt, die über den Laufzeitspeicher genutzt werden kann.
In diesem Prozess wird aus folgenden Gründen eine Konsolen-App ohne Einstiegspunkt verwendet:
- Eine Abhängigkeitendatei ist erforderlich, um den Hostingstart in der Hostingstartassembly zu nutzen. Eine Abhängigkeitendatei ist eine ausführbare App-Ressource, die durch das Veröffentlichen einer App, nicht einer Bibliothek, erstellt wird.
- Eine Bibliothek kann dem Laufzeitpaketspeicher, der ein ausführbares Projekt benötigt, das die freigegebene Laufzeit als Ziel verwendet, nicht direkt hinzugefügt werden.
Bei der Erstellung eines dynamischen Hostingstarts geschieht Folgendes:
- Eine Hostingstartassembly wird über die Konsolen-App ohne Einstiegspunkt erstellt, für die Folgendes gilt:
- Sie enthält eine Klasse mit der
IHostingStartup
-Implementierung. - Sie enthält ein HostingStartup-Attribut zum Identifizieren der
IHostingStartup
-Implementierungsklasse.
- Sie enthält eine Klasse mit der
- Die Konsolen-App wird veröffentlicht, um die Abhängigkeiten des Hostingstarts abzurufen. Die Veröffentlichung der Konsolen-App hat unter anderem zur Folge, dass nicht verwendete Abhängigkeiten aus der Abhängigkeitendatei entfernt werden.
- Die Abhängigkeitendatei wird so geändert, dass der Laufzeitspeicherort der Hostingstartassembly festgelegt wird.
- Die Hostingstartassembly und die dazu gehörende Abhängigkeitendatei werden im Laufzeitpaketspeicher abgelegt. Damit die Hostingstartassembly und die entsprechende Abhängigkeitendatei erkannt werden, werden sie in einem Paar von Umgebungsvariablen aufgeführt.
Die Konsolen-App verweist auf das Paket Microsoft.AspNetCore.Hosting.Abstractions:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp3.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.Hosting.Abstractions"
Version="3.0.0" />
</ItemGroup>
</Project>
Ein HostingStartup-Attribut identifiziert eine Klasse bei der Erstellung von IWebHost als eine Implementierung von IHostingStartup
zum Laden und Ausführen. Im folgenden Beispiel ist der Namespace StartupEnhancement
und die Klasse ist StartupEnhancementHostingStartup
:
[assembly: HostingStartup(typeof(StartupEnhancement.StartupEnhancementHostingStartup))]
Eine Klasse implementiert IHostingStartup
. Die Configure-Methode der Klasse verwendet einen IWebHostBuilder, um einer App Erweiterungen hinzuzufügen. IHostingStartup.Configure
wird in der Hoststartassembly von der Runtime vor Startup.Configure
im Benutzercode aufgerufen. Dadurch kann Benutzercode jede Konfiguration der Hoststartassembly überschreiben.
namespace StartupEnhancement
{
public class StartupEnhancementHostingStartup : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
// Use the IWebHostBuilder to add app enhancements.
}
}
}
Die Datei für die Abhängigkeiten ( .deps.json
) legt beim Erstellen eine IHostingStartup
-Projekts den runtime
-Speicherort der Assembly auf den bin-Ordner fest:
"targets": {
".NETCoreApp,Version=v3.0": {
"StartupEnhancement/1.0.0": {
"dependencies": {
"Microsoft.AspNetCore.Hosting.Abstractions": "3.0.0"
},
"runtime": {
"StartupEnhancement.dll": {}
}
}
}
}
Nur ein Teil der Datei wird angezeigt. StartupEnhancement
ist der Name der Assembly im Beispiel.
Beim Hostingstart bereitgestellte Konfiguration
Es gibt zwei Ansätze zur Verarbeitung der Konfiguration, je nachdem, ob die Konfiguration des Hostingstarts oder die der App Vorrang haben soll:
- Bereitstellen der Konfiguration für die App mit ConfigureAppConfiguration zum Laden der Konfiguration, nachdem die ConfigureAppConfiguration-Delegaten der App ausgeführt wurden. Bei diesem Ansatz hat die Hostingstartkonfiguration Vorrang vor der Konfiguration der App.
- Bereitstellen der Konfiguration für die App mit UseConfiguration zum Laden der Konfiguration, bevor die ConfigureAppConfiguration-Delegaten der App ausgeführt werden. Die Konfigurationswerte der App haben bei diesem Ansatz Vorrang vor denen des Hostingstarts.
public class ConfigurationInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
Dictionary<string, string> dict;
builder.ConfigureAppConfiguration(config =>
{
dict = new Dictionary<string, string>
{
{"ConfigurationKey1",
"From IHostingStartup: Higher priority " +
"than the app's configuration."},
};
config.AddInMemoryCollection(dict);
});
dict = new Dictionary<string, string>
{
{"ConfigurationKey2",
"From IHostingStartup: Lower priority " +
"than the app's configuration."},
};
var builtConfig = new ConfigurationBuilder()
.AddInMemoryCollection(dict)
.Build();
builder.UseConfiguration(builtConfig);
}
}
Angeben der Hostingstartassembly
Geben Sie für einen von der Klassenbibliothek oder von der Konsolen-App bereitgestellten Hostingstart den Namen der Hostingstartassembly in der Umgebungsvariablen ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
an. Die Umgebungsvariable ist eine durch Semikolons getrennte Liste von Assemblys.
Nur in Hostingstartassemblys wird nach dem HostingStartup
-Attribut gesucht. Damit die Beispiel-App HostingStartupApp die weiter oben beschriebenen Hostingstarts erkennt, wird für die Umgebungsvariable der folgende Wert festgelegt:
HostingStartupLibrary;HostingStartupPackage;StartupDiagnostics
Eine Hostingstartassembly kann auch mithilfe der Hostkonfigurationseinstellung „Hostingstartassemblys“ festgelegt werden:
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseSetting(
WebHostDefaults.HostingStartupAssembliesKey,
"{ASSEMBLY1;ASSEMBLY2; ...}")
.UseStartup<Startup>();
});
Der Platzhalter {ASSEMBLY1;ASSEMBLY2; ...}
stellt die durch Semikolons getrennte Assemblyliste dar.
Wenn mehrere Hoststartassemblys vorhanden sind, werden ihre Configure-Methoden in der Reihenfolge der aufgelisteten Assemblys ausgeführt.
Aktivierung
Optionen für die Hostingstartaktivierung:
- Laufzeitspeicher: Für die Aktivierung ist kein Kompilierzeitverweis erforderlich. Die Beispiel-App legt die Hostingstartassembly und die Abhängigkeitendateien im Ordner deployment ab, um die Bereitstellung des Hostingstarts in einer Umgebung mit mehreren Computern zu erleichtern. Der Ordner deployment enthält darüber hinaus auch ein PowerShell-Skript, das im Bereitstellungssystem Umgebungsvariablen erstellt oder ändert, um den Hostingstart zu ermöglichen.
- Kompilierzeitverweis für die Aktivierung erforderlich
Laufzeitspeicher
Die Hostingstartimplementierung wird im Laufzeitspeicher abgelegt. Ein Kompilierzeitverweis auf die Assembly wird von der erweiterten App nicht benötigt.
Nach der Erstellung des Hostingstarts wird mithilfe der Manifestprojektdatei und des Befehls dotnet store ein Laufzeitspeicher generiert.
dotnet store --manifest {MANIFEST FILE} --runtime {RUNTIME IDENTIFIER} --output {OUTPUT LOCATION} --skip-optimization
In der Beispiel-App (Projekt RuntimeStore) wird der folgende Befehl verwendet:
dotnet store --manifest store.manifest.csproj --runtime win7-x64 --output ./deployment/store --skip-optimization
Damit die Runtime den Laufzeitspeicher ermitteln kann, wird der Speicherort des Laufzeitspeichers der Umgebungsvariablen DOTNET_SHARED_STORE
hinzugefügt.
Ändern und Ablegen der Abhängigkeitendatei des Hostingstarts
Um die Erweiterung ohne einen Paketverweis auf die Erweiterung zu aktivieren, geben Sie mit additionalDeps
zusätzliche Abhängigkeiten zur Laufzeit an. additionalDeps
ermöglicht Ihnen Folgendes:
- Erweitern des App-Bibliotheksdiagramms durch Bereitstellen einer Reihe zusätzlicher
.deps.json
-Dateien, die beim Start mit der App-eigenen.deps.json
-Datei zusammengeführt werden. - Bereitstellen der Hostingstartassembly, sodass sie ermittelt und geladen werden kann
Folgender Ansatz wird zum Generieren der zusätzlichen Abhängigkeitendatei empfohlen:
- Führen Sie
dotnet publish
für die Manifestdatei des Laufzeitspeichers aus, auf die im vorherigen Abschnitt verwiesen wurde. - Entfernen Sie den Manifestverweis aus den Bibliotheken und dem Abschnitt
runtime
der daraus resultierenden.deps.json
-Datei.
Im Beispielprojekt wird die Eigenschaft store.manifest/1.0.0
aus den Abschnitten targets
und libraries
entfernt:
{
"runtimeTarget": {
"name": ".NETCoreApp,Version=v3.0",
"signature": ""
},
"compilationOptions": {},
"targets": {
".NETCoreApp,Version=v3.0": {
"store.manifest/1.0.0": {
"dependencies": {
"StartupDiagnostics": "1.0.0"
},
"runtime": {
"store.manifest.dll": {}
}
},
"StartupDiagnostics/1.0.0": {
"runtime": {
"lib/netcoreapp3.0/StartupDiagnostics.dll": {
"assemblyVersion": "1.0.0.0",
"fileVersion": "1.0.0.0"
}
}
}
}
},
"libraries": {
"store.manifest/1.0.0": {
"type": "project",
"serviceable": false,
"sha512": ""
},
"StartupDiagnostics/1.0.0": {
"type": "package",
"serviceable": true,
"sha512": "sha512-xrhzuNSyM5/f4ZswhooJ9dmIYLP64wMnqUJSyTKVDKDVj5T+qtzypl8JmM/aFJLLpYrf0FYpVWvGujd7/FfMEw==",
"path": "startupdiagnostics/1.0.0",
"hashPath": "startupdiagnostics.1.0.0.nupkg.sha512"
}
}
}
Legen Sie die .deps.json
-Datei an folgendem Speicherort ab:
{ADDITIONAL DEPENDENCIES PATH}/shared/{SHARED FRAMEWORK NAME}/{SHARED FRAMEWORK VERSION}/{ENHANCEMENT ASSEMBLY NAME}.deps.json
{ADDITIONAL DEPENDENCIES PATH}
: Der Speicherort wurde zur UmgebungsvariableDOTNET_ADDITIONAL_DEPS
hinzugefügt.{SHARED FRAMEWORK NAME}
: Dies ist das freigegebene Framework, das für diese zusätzliche Abhängigkeitsdatei erforderlich ist.{SHARED FRAMEWORK VERSION}
: Dies ist die Mindestversion des freigegebenen Frameworks.{ENHANCEMENT ASSEMBLY NAME}
: Dies ist der Name der Erweiterungsassembly.
In der Beispiel-App (Projekt RuntimeStore) wird die zusätzliche Abhängigkeitendatei an folgendem Speicherort abgelegt:
deployment/additionalDeps/shared/Microsoft.AspNetCore.App/3.0.0/StartupDiagnostics.deps.json
Damit die Runtime den Speicherort des Laufzeitspeichers ermitteln kann, wir die zusätzliche Abhängigkeitendatei der Umgebungsvariablen DOTNET_ADDITIONAL_DEPS
hinzugefügt.
In der Beispiel-App (Projekt RuntimeStore) wird das Erstellen des Laufzeitspeichers und das Generieren der zusätzlichen Abhängigkeitendatei durch ein PowerShell-Skript durchgeführt.
Beispiele zum Festlegen von Umgebungsvariablen für verschiedene Betriebssysteme finden Sie unter Use multiple environments (Verwenden mehrerer Umgebungen).
Bereitstellung
Um die Bereitstellung eines Hostingstarts in einer Umgebung mit mehreren Computern zu erleichtern, erstellt die Beispiel-App in der veröffentlichten Ausgabe einen deployment-Ordner, der Folgendes enthält:
- Der Laufzeitspeicher des Hostingstarts.
- Die Abhängigkeitendatei des Hostingstarts.
- Ein PowerShell-Skript, das
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
,DOTNET_SHARED_STORE
undDOTNET_ADDITIONAL_DEPS
erstellt oder ändert, um die Aktivierung des Hostingstarts zu unterstützen. Führen Sie das Skript über eine PowerShell-Administratoreingabeaufforderung auf dem Bereitstellungssystem aus.
NuGet-Paket
In einem NuGet-Paket kann eine Hostingstarterweiterung bereitgestellt werden. Das Paket enthält ein HostingStartup
-Attribut. Die vom Paket bereitgestellten Hostingstarttypen werden für die App mit einem der folgenden Verfahren verfügbar gemacht:
- Die Projektdatei der erweiterten App erstellt einen Paketverweis für den Hostingstart in der Projektdatei der App (Kompilierzeitverweis). Wenn ein Kompilierzeitverweis eingerichtet ist, werden die Hostingstartassembly und alle dazu gehörenden Abhängigkeiten in die Abhängigkeitendatei der App (
.deps.json
) eingebunden. Dieses Verfahren gilt für ein in nuget.org veröffentlichtes Hostingstartassembly-Paket. - Die Abhängigkeitendatei des Hostingstarts wird für die erweiterte App wie im Abschnitt Laufzeitspeicher beschrieben (ohne Kompilierzeitverweis) verfügbar gemacht.
Weitere Informationen zu NuGet-Paketen und den Laufzeitspeicher finden Sie in den folgenden Themen:
- So erstellen Sie ein NuGet-Paket mit plattformübergreifenden Tools
- Veröffentlichen von Paketen
- Laufzeitpaketspeicher
Ordner „Bin“ des Projekts
Eine Hostingstarterweiterung kann durch eine mittels bin bereitgestellte Assembly in der erweiterten App bereitgestellt werden. Die von der Assembly bereitgestellten Hostingstarttypen werden für die App mit einem der folgenden Verfahren verfügbar gemacht:
- Die Projektdatei der erweiterten App enthält einen Assemblyverweis auf den Hostingstart (Kompilierzeitverweis). Wenn ein Kompilierzeitverweis eingerichtet ist, werden die Hostingstartassembly und alle dazu gehörenden Abhängigkeiten in die Abhängigkeitendatei der App (
.deps.json
) eingebunden. Dieser Ansatz gilt, wenn das Bereitstellungsszenario erfordert, dass ein Kompilierzeitverweis auf die Assembly des Hostingstarts (DLL-Datei) erstellt und die Assembly in eine der beiden Dateien verschoben wird:- Das verbrauchende Projekt.
- Einen Speicherort, auf den das verbrauchende Projekt zugreifen kann.
- Die Abhängigkeitendatei des Hostingstarts wird für die erweiterte App wie im Abschnitt Laufzeitspeicher beschrieben (ohne Kompilierzeitverweis) verfügbar gemacht.
- Wenn das Ziel .NET Framework ist, kann die Assembly in den Standardladekontext geladen werden, was bei .NET Framework bedeutet, dass sich die Assembly an einem der folgenden Speicherorte befindet:
- Anwendungsbasispfad: Dabei handelt es sich um den Ordner bin, in dem die ausführbare Datei ( .exe) der App gespeichert wird.
- Globaler Assemblycache (GAC): Der GAC speichert Assemblys, die mehrere .NET Framework-Apps gemeinsam nutzen. Weitere Informationen finden Sie unter Vorgehensweise: Installieren einer Assembly in den globalen Assemblycache in der .NET Framework-Dokumentation.
Beispielcode
Der Beispielcode (Herunterladen) zeigt Szenarios für die Hostingstartimplementierung:
- Zwei Hostingstartassemblys (Klassenbibliotheken) legen zwei Schlüssel-Wert-Paare der Konfiguration im Arbeitsspeicher fest:
- NuGet-Paket (HostingStartupPackage)
- Klassenbibliothek (HostingStartupLibrary)
- Ein Hostingstart wird über eine im Laufzeitspeicher bereitgestellte Assembly (StartupDiagnostics) aktiviert. Die Assembly fügt der App zum Start zwei Middlewares hinzu, die Diagnoseinformationen zu folgenden Komponenten bereitstellen:
- Registrierte Dienste
- Adresse (Schema, Host, Basispfad, Pfad, Abfragezeichenfolge)
- Verbindung (Remote-IP, Remoteport, lokale IP, lokaler Port, Clientzertifikat)
- Anforderungsheader
- Umgebungsvariablen
So führen Sie das Beispiel aus:
Aktivierung über ein NuGet-Paket
Kompilieren Sie das Paket HostingStartupPackage mit dem Befehl dotnet pack.
Fügen Sie den Assemblynamen des Pakets HostingStartupPackage zur Umgebungsvariablen
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
hinzu.Kompilieren Sie die App, und führen Sie diese aus. In der erweiterten App ist ein Paketverweis vorhanden (Kompilierzeitverweis). Eine
<PropertyGroup>
in der Projektdatei der App gibt die Ausgabe des Paketprojekts ( ../HostingStartupPackage/bin/Debug) als Paketquelle an. Dadurch kann die Anwendung das Paket verwenden, ohne das Paket in nuget.org hochzuladen. Weitere Informationen finden Sie in den Hinweisen in der Projektdatei von HostingStartupApp.<PropertyGroup> <RestoreSources>$(RestoreSources);https://api.nuget.org/v3/index.json;../HostingStartupPackage/bin/Debug</RestoreSources> </PropertyGroup>
Die von der Indexseite gerenderten Schlüsselwerte der Dienstkonfiguration entsprechen den durch die
ServiceKeyInjection.Configure
-Methode des Pakets festgelegten Werten.
Wenn Sie am Projekt HostingStartupPackage Änderungen vornehmen und das Projekt erneut kompilieren, bereinigen Sie die lokalen NuGet-Paketcaches, um sicherzustellen, dass die HostingStartupApp das aktualisierte Paket erhält und kein veraltetes Paket aus dem lokalen Cache. Um die lokalen NuGet-Caches zu bereinigen, führen Sie den folgenden dotnet nuget locals-Befehl aus:
dotnet nuget locals all --clear
Aktivierung über eine Klassenbibliothek
Kompilieren Sie die Klassenbibliothek HostingStartupLibrary mit dem Befehl dotnet build.
Fügen Sie der Umgebungsvariablen
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
den Assemblynamen HostingStartupLibrary der Klassenbibliothek hinzu.Stellen Sie die Assembly der Klassenbibliothek mittels bin für die App bereit, indem Sie die Datei HostingStartupLibrary.dll aus der kompilierten Ausgabe der Klassenbibliothek in den Ordner bin/Debug der App kopieren.
Kompilieren Sie die App, und führen Sie diese aus. Eine
<ItemGroup>
in der Projektdatei der App verweist auf die Assembly der Klassenbibliothek ( .\bin\Debug\netcoreapp3.0\HostingStartupLibrary.dll) – Kompilierzeitverweis. Weitere Informationen finden Sie in den Hinweisen in der Projektdatei von HostingStartupApp.<ItemGroup> <Reference Include=".\\bin\\Debug\\netcoreapp3.0\\HostingStartupLibrary.dll"> <HintPath>.\bin\Debug\netcoreapp3.0\HostingStartupLibrary.dll</HintPath> <SpecificVersion>False</SpecificVersion> </Reference> </ItemGroup>
Die von der Indexseite gerenderten Schlüsselwerte der Dienstkonfiguration entsprechen den durch die
ServiceKeyInjection.Configure
-Methode der Klassenbibliothek festgelegten Werten.
Aktivierung über eine mittels Laufzeitspeicher bereitgestellten Assembly
- Im Projekt StartupDiagnostics wird PowerShell verwendet, um die Datei
StartupDiagnostics.deps.json
zu bearbeiten. PowerShell ist standardmäßig auf Windows-Betriebssystemen ab Windows 7 SP1 und Windows Server 2008 R2 SP1 installiert. Im Artikel Installieren verschiedener Versionen von PowerShell erfahren Sie, wie Sie PowerShell auf anderen Plattformen erwerben können. - Führen Sie das Skript build.ps1 im Ordner RuntimeStore aus. Das Skript:
- Generiert das
StartupDiagnostics
-Paket im Ordner obj\packages . - Generiert den Laufzeitspeicher für
StartupDiagnostics
im Ordner store. Derdotnet store
-Befehl im Skript verwendet den Laufzeitbezeichner (RID)win7-x64
für einen für Windows bereitgestellten Hostingstart. Wenn der Hostingstart für eine andere Laufzeit bereitgestellt wird, muss in Zeile 37 die entsprechende RID eingegeben werden. Der Runtimespeicher fürStartupDiagnostics
würde später in den Runtimespeicher des Benutzers oder Systems auf dem Computer verschoben, auf dem die Assembly verwendet wird. Der Installationsspeicherort für den Benutzerruntimespeicher für dieStartupDiagnostics
-Assembly ist .dotnet/store/x64/netcoreapp3.0/startupdiagnostics/1.0.0/lib/netcoreapp3.0/StartupDiagnostics.dll. - Generiert die
additionalDeps
fürStartupDiagnostics
im Ordner additionalDeps . Die zusätzlichen Abhängigkeiten würden später in die zusätzlichen Abhängigkeiten des Benutzers oder Systems verschoben. Der Installationsspeicherort der zusätzlichen Abhängigkeiten des BenutzersStartupDiagnostics
ist.dotnet/x64/additionalDeps/StartupDiagnostics/shared/Microsoft.NETCore.App/3.0.0/StartupDiagnostics.deps.json
. - Legt die Datei deploy.ps1 im Ordner deployment ab.
- Generiert das
- Führen Sie das Skript deploy.ps1 im Ordner deployment aus. Das Skript fügt Folgendes:
StartupDiagnostics
an die UmgebungsvariableASPNETCORE_HOSTINGSTARTUPASSEMBLIES
.- Der Pfad der Hostingstartabhängigkeiten (im Ordner deployment des RuntimeStore-Projekts) zur
DOTNET_ADDITIONAL_DEPS
-Umgebungsvariablen. - Der Pfad des Runtimespeichers (im Ordner deployment des RuntimeStore-Projekts) zur
DOTNET_SHARED_STORE
-Umgebungsvariablen.
- Führen Sie die Beispiel-App aus.
- Fordern Sie den Endpunkt
/services
an, um die registrierten Dienste der App anzuzeigen. Fordern Sie den Endpunkt/diag
an, um Diagnoseinformationen anzuzeigen.
Mit einer IHostingStartup-Implementierung (Hostingstart) werden Verbesserungen an einer App beim Start von einer externen Assembly aus vorgenommen. Eine externe Bibliothek kann beispielsweise eine Hostingstartimplementierung verwenden, um zusätzliche Konfigurationsanbieter oder -dienste für eine App bereitzustellen.
Anzeigen oder Herunterladen von Beispielcode (Vorgehensweise zum Herunterladen)
Das Attribut HostingStartup
Ein HostingStartup-Attribut gibt an, ob eine Hostingstartassembly vorhanden ist, die zur Laufzeit aktiviert werden kann.
Bei der Einstiegsassembly oder bei der Assembly, die die Klasse Startup
enthält, wird automatisch geprüft, ob sie das Attribut HostingStartup
enthält. Die Liste der Assemblys für die Suche nach HostingStartup
-Attributen wird zur Laufzeit aus der Konfiguration in WebHostDefaults.HostingStartupAssembliesKey geladen. Die Liste der Assemblys, die aus der Ermittlung ausgeschlossen werden sollen, wird aus WebHostDefaults.HostingStartupExcludeAssembliesKey geladen. Weitere Informationen finden Sie unter Webhost: HostingstartassemblysWebhost: Auszuschließende Hostingstartassemblys.
Im folgenden Beispiel lautet der Namespace der Hostingstartassembly StartupEnhancement
. StartupEnhancementHostingStartup
ist die Klasse mit dem Hostingstartcode:
[assembly: HostingStartup(typeof(StartupEnhancement.StartupEnhancementHostingStartup))]
Das Attribut HostingStartup
befindet sich in der Regel in der IHostingStartup
-Implementierungsklassendatei der Hostingstartassembly.
Ermitteln geladener Hostingstartassemblys
Zum Ermitteln von geladenen Hostingstartassemblys aktivieren Sie die Protokollierung und überprüfen die Protokolle der App. Fehler, die beim Laden von Assemblys auftreten, werden protokolliert. Geladene Hostingstartassemblys werden auf der Debugebene protokolliert. Außerdem werden alle Fehler protokolliert.
Deaktivieren des automatischen Ladens von Hostingstartassemblys
Um das automatische Laden von Hostingstartassemblys zu deaktivieren, verwenden Sie einen der folgenden Ansätze:
- Um zu verhindern, dass alle Hostingstartassemblys geladen werden, legen Sie eine der folgenden Einstellungen auf
true
oder1
fest:- Hostkonfigurationseinstellung Verhindern des Hostingstarts.
- Die Umgebungsvariable
ASPNETCORE_PREVENTHOSTINGSTARTUP
- Um zu verhindern, dass bestimmte Hostingstartassemblys geladen werden, legen Sie eine der folgenden Einstellungen auf eine durch Semikolons getrennte Zeichenfolge mit Hostingstartassemblys fest, die beim Starten ausgeschlossen werden sollen:
- Hostkonfigurationseinstellung Hostingstartausschlussassemblys.
- Die Umgebungsvariable
ASPNETCORE_HOSTINGSTARTUPEXCLUDEASSEMBLIES
Wenn sowohl die Konfigurationseinstellung für den Host als auch die Umgebungsvariable festgelegt werden, wird das Verhalten durch die Hosteinstellung gesteuert.
Durch das Deaktivieren von Hostingstartassemblys mithilfe der Hosteinstellung oder der Umgebungsvariable wird die Assembly global deaktiviert. Einige Eigenschaften einer App können ebenfalls deaktiviert werden.
Projekt
Erstellen Sie einen Hostingstart mit einem der folgenden Projekttypen:
Klassenbibliothek
In einer Klassenbibliothek kann eine Hostingstarterweiterung bereitgestellt werden. Die Bibliothek enthält ein HostingStartup
-Attribut.
Der Beispielcode enthält die Razor Pages-App HostingStartupApp und die Klassenbibliothek HostingStartupLibrary. Die Klassenbibliothek:
- Enthält die Hostingstartklasse
ServiceKeyInjection
, dieIHostingStartup
implementiert.ServiceKeyInjection
fügt mithilfe des Anbieters der Konfiguration im Arbeitsspeicher (AddInMemoryCollection) der App-Konfiguration zwei Dienstzeichenfolgen hinzu. - Enthält ein
HostingStartup
-Attribut, das den Namespace und die Klasse des Hostingstarts angibt.
Die Configure-Methode der ServiceKeyInjection
-Klasse verwendet einen IWebHostBuilder, um einer App Erweiterungen hinzuzufügen.
HostingStartupLibrary/ServiceKeyInjection.cs
:
[assembly: HostingStartup(typeof(HostingStartupLibrary.ServiceKeyInjection))]
namespace HostingStartupLibrary
{
public class ServiceKeyInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
builder.ConfigureAppConfiguration(config =>
{
var dict = new Dictionary<string, string>
{
{"DevAccount_FromLibrary", "DEV_1111111-1111"},
{"ProdAccount_FromLibrary", "PROD_2222222-2222"}
};
config.AddInMemoryCollection(dict);
});
}
}
}
Die Indexseite der App liest und rendert die Konfigurationswerte für die beiden Schlüssel, die von der Hostingstartassembly der Klassenbibliothek festgelegt werden:
HostingStartupApp/Pages/Index.cshtml.cs
:
public class IndexModel : PageModel
{
public IndexModel(IConfiguration config)
{
ServiceKey_Development_Library = config["DevAccount_FromLibrary"];
ServiceKey_Production_Library = config["ProdAccount_FromLibrary"];
ServiceKey_Development_Package = config["DevAccount_FromPackage"];
ServiceKey_Production_Package = config["ProdAccount_FromPackage"];
}
public string ServiceKey_Development_Library { get; private set; }
public string ServiceKey_Production_Library { get; private set; }
public string ServiceKey_Development_Package { get; private set; }
public string ServiceKey_Production_Package { get; private set; }
public void OnGet()
{
}
}
Der Beispielcode enthält darüber hinaus auch ein NuGet-Paketprojekt, das den separaten Hostingstart HostingStartupPackage bereitstellt. Das Paket weist dieselben Merkmale wie die bereits beschriebene Klassenbibliothek auf. Das Paket:
- Enthält die Hostingstartklasse
ServiceKeyInjection
, dieIHostingStartup
implementiert.ServiceKeyInjection
fügt der App-Konfiguration zwei Dienstzeichenfolgen hinzu. - Enthält ein
HostingStartup
-Attribut.
HostingStartupPackage/ServiceKeyInjection.cs
:
[assembly: HostingStartup(typeof(HostingStartupPackage.ServiceKeyInjection))]
namespace HostingStartupPackage
{
public class ServiceKeyInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
builder.ConfigureAppConfiguration(config =>
{
var dict = new Dictionary<string, string>
{
{"DevAccount_FromPackage", "DEV_3333333-3333"},
{"ProdAccount_FromPackage", "PROD_4444444-4444"}
};
config.AddInMemoryCollection(dict);
});
}
}
}
Die Indexseite der App liest und rendert die Konfigurationswerte für die beiden Schlüssel, die von der Hostingstartassembly der Bibliothek festgelegt werden:
HostingStartupApp/Pages/Index.cshtml.cs
:
public class IndexModel : PageModel
{
public IndexModel(IConfiguration config)
{
ServiceKey_Development_Library = config["DevAccount_FromLibrary"];
ServiceKey_Production_Library = config["ProdAccount_FromLibrary"];
ServiceKey_Development_Package = config["DevAccount_FromPackage"];
ServiceKey_Production_Package = config["ProdAccount_FromPackage"];
}
public string ServiceKey_Development_Library { get; private set; }
public string ServiceKey_Production_Library { get; private set; }
public string ServiceKey_Development_Package { get; private set; }
public string ServiceKey_Production_Package { get; private set; }
public void OnGet()
{
}
}
Konsolen-App ohne Einstiegspunkt
Dieses Verfahren ist nur für .NET Core-Apps, nicht jedoch für .NET Framework verfügbar.
Eine dynamische Hostingstarterweiterung, die zur Aktivierung keinen Kompilierungszeitverweis erfordert, kann in einer Konsolen-App ohne Einstiegspunkt bereitgestellt werden, die ein HostingStartup
-Attribut enthält. Durch die Veröffentlichung der Konsolen-App wird eine Hostingstartassembly erstellt, die über den Laufzeitspeicher genutzt werden kann.
In diesem Prozess wird aus folgenden Gründen eine Konsolen-App ohne Einstiegspunkt verwendet:
- Eine Abhängigkeitendatei ist erforderlich, um den Hostingstart in der Hostingstartassembly zu nutzen. Eine Abhängigkeitendatei ist eine ausführbare App-Ressource, die durch das Veröffentlichen einer App, nicht einer Bibliothek, erstellt wird.
- Eine Bibliothek kann dem Laufzeitpaketspeicher, der ein ausführbares Projekt benötigt, das die freigegebene Laufzeit als Ziel verwendet, nicht direkt hinzugefügt werden.
Bei der Erstellung eines dynamischen Hostingstarts geschieht Folgendes:
- Eine Hostingstartassembly wird über die Konsolen-App ohne Einstiegspunkt erstellt, für die Folgendes gilt:
- Sie enthält eine Klasse mit der
IHostingStartup
-Implementierung. - Sie enthält ein HostingStartup-Attribut zum Identifizieren der
IHostingStartup
-Implementierungsklasse.
- Sie enthält eine Klasse mit der
- Die Konsolen-App wird veröffentlicht, um die Abhängigkeiten des Hostingstarts abzurufen. Die Veröffentlichung der Konsolen-App hat unter anderem zur Folge, dass nicht verwendete Abhängigkeiten aus der Abhängigkeitendatei entfernt werden.
- Die Abhängigkeitendatei wird so geändert, dass der Laufzeitspeicherort der Hostingstartassembly festgelegt wird.
- Die Hostingstartassembly und die dazu gehörende Abhängigkeitendatei werden im Laufzeitpaketspeicher abgelegt. Damit die Hostingstartassembly und die entsprechende Abhängigkeitendatei erkannt werden, werden sie in einem Paar von Umgebungsvariablen aufgeführt.
Die Konsolen-App verweist auf das Paket Microsoft.AspNetCore.Hosting.Abstractions:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp2.1</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.Hosting.Abstractions"
Version="2.1.1" />
</ItemGroup>
</Project>
Ein HostingStartup-Attribut identifiziert eine Klasse bei der Erstellung von IWebHost als eine Implementierung von IHostingStartup
zum Laden und Ausführen. Im folgenden Beispiel ist der Namespace StartupEnhancement
und die Klasse ist StartupEnhancementHostingStartup
:
[assembly: HostingStartup(typeof(StartupEnhancement.StartupEnhancementHostingStartup))]
Eine Klasse implementiert IHostingStartup
. Die Configure-Methode der Klasse verwendet einen IWebHostBuilder, um einer App Erweiterungen hinzuzufügen. IHostingStartup.Configure
wird in der Hoststartassembly von der Runtime vor Startup.Configure
im Benutzercode aufgerufen. Dadurch kann Benutzercode jede Konfiguration der Hoststartassembly überschreiben.
namespace StartupEnhancement
{
public class StartupEnhancementHostingStartup : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
// Use the IWebHostBuilder to add app enhancements.
}
}
}
Die Datei für die Abhängigkeiten ( .deps.json
) legt beim Erstellen eine IHostingStartup
-Projekts den runtime
-Speicherort der Assembly auf den bin-Ordner fest:
"targets": {
".NETCoreApp,Version=v2.1": {
"StartupEnhancement/1.0.0": {
"dependencies": {
"Microsoft.AspNetCore.Hosting.Abstractions": "2.1.1"
},
"runtime": {
"StartupEnhancement.dll": {}
}
}
}
}
Nur ein Teil der Datei wird angezeigt. StartupEnhancement
ist der Name der Assembly im Beispiel.
Beim Hostingstart bereitgestellte Konfiguration
Es gibt zwei Ansätze zur Verarbeitung der Konfiguration, je nachdem, ob die Konfiguration des Hostingstarts oder die der App Vorrang haben soll:
- Bereitstellen der Konfiguration für die App mit ConfigureAppConfiguration zum Laden der Konfiguration, nachdem die ConfigureAppConfiguration-Delegaten der App ausgeführt wurden. Bei diesem Ansatz hat die Hostingstartkonfiguration Vorrang vor der Konfiguration der App.
- Bereitstellen der Konfiguration für die App mit UseConfiguration zum Laden der Konfiguration, bevor die ConfigureAppConfiguration-Delegaten der App ausgeführt werden. Die Konfigurationswerte der App haben bei diesem Ansatz Vorrang vor denen des Hostingstarts.
public class ConfigurationInjection : IHostingStartup
{
public void Configure(IWebHostBuilder builder)
{
Dictionary<string, string> dict;
builder.ConfigureAppConfiguration(config =>
{
dict = new Dictionary<string, string>
{
{"ConfigurationKey1",
"From IHostingStartup: Higher priority " +
"than the app's configuration."},
};
config.AddInMemoryCollection(dict);
});
dict = new Dictionary<string, string>
{
{"ConfigurationKey2",
"From IHostingStartup: Lower priority " +
"than the app's configuration."},
};
var builtConfig = new ConfigurationBuilder()
.AddInMemoryCollection(dict)
.Build();
builder.UseConfiguration(builtConfig);
}
}
Angeben der Hostingstartassembly
Geben Sie für einen von der Klassenbibliothek oder von der Konsolen-App bereitgestellten Hostingstart den Namen der Hostingstartassembly in der Umgebungsvariablen ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
an. Die Umgebungsvariable ist eine durch Semikolons getrennte Liste von Assemblys.
Nur in Hostingstartassemblys wird nach dem HostingStartup
-Attribut gesucht. Damit die Beispiel-App HostingStartupApp die weiter oben beschriebenen Hostingstarts erkennt, wird für die Umgebungsvariable der folgende Wert festgelegt:
HostingStartupLibrary;HostingStartupPackage;StartupDiagnostics
Eine Hostingstartassembly kann auch mithilfe der Hostkonfigurationseinstellung Hostingstartassemblys festgelegt werden.
Wenn mehrere Hoststartassemblys vorhanden sind, werden ihre Configure-Methoden in der Reihenfolge der aufgelisteten Assemblys ausgeführt.
Aktivierung
Optionen für die Hostingstartaktivierung:
- Laufzeitspeicher: Für die Aktivierung ist kein Kompilierzeitverweis erforderlich. Die Beispiel-App legt die Hostingstartassembly und die Abhängigkeitendateien im Ordner deployment ab, um die Bereitstellung des Hostingstarts in einer Umgebung mit mehreren Computern zu erleichtern. Der Ordner deployment enthält darüber hinaus auch ein PowerShell-Skript, das im Bereitstellungssystem Umgebungsvariablen erstellt oder ändert, um den Hostingstart zu ermöglichen.
- Kompilierzeitverweis für die Aktivierung erforderlich
Laufzeitspeicher
Die Hostingstartimplementierung wird im Laufzeitspeicher abgelegt. Ein Kompilierzeitverweis auf die Assembly wird von der erweiterten App nicht benötigt.
Nach der Erstellung des Hostingstarts wird mithilfe der Manifestprojektdatei und des Befehls dotnet store ein Laufzeitspeicher generiert.
dotnet store --manifest {MANIFEST FILE} --runtime {RUNTIME IDENTIFIER} --output {OUTPUT LOCATION} --skip-optimization
In der Beispiel-App (Projekt RuntimeStore) wird der folgende Befehl verwendet:
dotnet store --manifest store.manifest.csproj --runtime win7-x64 --output ./deployment/store --skip-optimization
Damit die Runtime den Laufzeitspeicher ermitteln kann, wird der Speicherort des Laufzeitspeichers der Umgebungsvariablen DOTNET_SHARED_STORE
hinzugefügt.
Ändern und Ablegen der Abhängigkeitendatei des Hostingstarts
Um die Erweiterung ohne einen Paketverweis auf die Erweiterung zu aktivieren, geben Sie mit additionalDeps
zusätzliche Abhängigkeiten zur Laufzeit an. additionalDeps
ermöglicht Ihnen Folgendes:
- Erweitern des App-Bibliotheksdiagramms durch Bereitstellen einer Reihe zusätzlicher
.deps.json
-Dateien, die beim Start mit der App-eigenen.deps.json
-Datei zusammengeführt werden. - Bereitstellen der Hostingstartassembly, sodass sie ermittelt und geladen werden kann
Folgender Ansatz wird zum Generieren der zusätzlichen Abhängigkeitendatei empfohlen:
- Führen Sie
dotnet publish
für die Manifestdatei des Laufzeitspeichers aus, auf die im vorherigen Abschnitt verwiesen wurde. - Entfernen Sie den Manifestverweis aus den Bibliotheken und dem Abschnitt
runtime
der daraus resultierenden.deps.json
-Datei.
Im Beispielprojekt wird die Eigenschaft store.manifest/1.0.0
aus den Abschnitten targets
und libraries
entfernt:
{
"runtimeTarget": {
"name": ".NETCoreApp,Version=v2.1",
"signature": "4ea77c7b75ad1895ae1ea65e6ba2399010514f99"
},
"compilationOptions": {},
"targets": {
".NETCoreApp,Version=v2.1": {
"store.manifest/1.0.0": {
"dependencies": {
"StartupDiagnostics": "1.0.0"
},
"runtime": {
"store.manifest.dll": {}
}
},
"StartupDiagnostics/1.0.0": {
"runtime": {
"lib/netcoreapp2.1/StartupDiagnostics.dll": {
"assemblyVersion": "1.0.0.0",
"fileVersion": "1.0.0.0"
}
}
}
}
},
"libraries": {
"store.manifest/1.0.0": {
"type": "project",
"serviceable": false,
"sha512": ""
},
"StartupDiagnostics/1.0.0": {
"type": "package",
"serviceable": true,
"sha512": "sha512-oiQr60vBQW7+nBTmgKLSldj06WNLRTdhOZpAdEbCuapoZ+M2DJH2uQbRLvFT8EGAAv4TAKzNtcztpx5YOgBXQQ==",
"path": "startupdiagnostics/1.0.0",
"hashPath": "startupdiagnostics.1.0.0.nupkg.sha512"
}
}
}
Legen Sie die .deps.json
-Datei an folgendem Speicherort ab:
{ADDITIONAL DEPENDENCIES PATH}/shared/{SHARED FRAMEWORK NAME}/{SHARED FRAMEWORK VERSION}/{ENHANCEMENT ASSEMBLY NAME}.deps.json
{ADDITIONAL DEPENDENCIES PATH}
: Der Speicherort wurde zur UmgebungsvariableDOTNET_ADDITIONAL_DEPS
hinzugefügt.{SHARED FRAMEWORK NAME}
: Dies ist das freigegebene Framework, das für diese zusätzliche Abhängigkeitsdatei erforderlich ist.{SHARED FRAMEWORK VERSION}
: Dies ist die Mindestversion des freigegebenen Frameworks.{ENHANCEMENT ASSEMBLY NAME}
: Dies ist der Name der Erweiterungsassembly.
In der Beispiel-App (Projekt RuntimeStore) wird die zusätzliche Abhängigkeitendatei an folgendem Speicherort abgelegt:
deployment/additionalDeps/shared/Microsoft.AspNetCore.App/2.1.0/StartupDiagnostics.deps.json
Damit die Runtime den Speicherort des Laufzeitspeichers ermitteln kann, wir die zusätzliche Abhängigkeitendatei der Umgebungsvariablen DOTNET_ADDITIONAL_DEPS
hinzugefügt.
In der Beispiel-App (Projekt RuntimeStore) wird das Erstellen des Laufzeitspeichers und das Generieren der zusätzlichen Abhängigkeitendatei durch ein PowerShell-Skript durchgeführt.
Beispiele zum Festlegen von Umgebungsvariablen für verschiedene Betriebssysteme finden Sie unter Use multiple environments (Verwenden mehrerer Umgebungen).
Bereitstellung
Um die Bereitstellung eines Hostingstarts in einer Umgebung mit mehreren Computern zu erleichtern, erstellt die Beispiel-App in der veröffentlichten Ausgabe einen deployment-Ordner, der Folgendes enthält:
- Der Laufzeitspeicher des Hostingstarts.
- Die Abhängigkeitendatei des Hostingstarts.
- Ein PowerShell-Skript, das
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
,DOTNET_SHARED_STORE
undDOTNET_ADDITIONAL_DEPS
erstellt oder ändert, um die Aktivierung des Hostingstarts zu unterstützen. Führen Sie das Skript über eine PowerShell-Administratoreingabeaufforderung auf dem Bereitstellungssystem aus.
NuGet-Paket
In einem NuGet-Paket kann eine Hostingstarterweiterung bereitgestellt werden. Das Paket enthält ein HostingStartup
-Attribut. Die vom Paket bereitgestellten Hostingstarttypen werden für die App mit einem der folgenden Verfahren verfügbar gemacht:
- Die Projektdatei der erweiterten App erstellt einen Paketverweis für den Hostingstart in der Projektdatei der App (Kompilierzeitverweis). Wenn ein Kompilierzeitverweis eingerichtet ist, werden die Hostingstartassembly und alle dazu gehörenden Abhängigkeiten in die Abhängigkeitendatei der App (
.deps.json
) eingebunden. Dieses Verfahren gilt für ein in nuget.org veröffentlichtes Hostingstartassembly-Paket. - Die Abhängigkeitendatei des Hostingstarts wird für die erweiterte App wie im Abschnitt Laufzeitspeicher beschrieben (ohne Kompilierzeitverweis) verfügbar gemacht.
Weitere Informationen zu NuGet-Paketen und den Laufzeitspeicher finden Sie in den folgenden Themen:
- So erstellen Sie ein NuGet-Paket mit plattformübergreifenden Tools
- Veröffentlichen von Paketen
- Laufzeitpaketspeicher
Ordner „Bin“ des Projekts
Eine Hostingstarterweiterung kann durch eine mittels bin bereitgestellte Assembly in der erweiterten App bereitgestellt werden. Die von der Assembly bereitgestellten Hostingstarttypen werden für die App mit einem der folgenden Verfahren verfügbar gemacht:
- Die Projektdatei der erweiterten App enthält einen Assemblyverweis auf den Hostingstart (Kompilierzeitverweis). Wenn ein Kompilierzeitverweis eingerichtet ist, werden die Hostingstartassembly und alle dazu gehörenden Abhängigkeiten in die Abhängigkeitendatei der App (
.deps.json
) eingebunden. Dieser Ansatz gilt, wenn das Bereitstellungsszenario erfordert, dass ein Kompilierzeitverweis auf die Assembly des Hostingstarts (DLL-Datei) erstellt und die Assembly in eine der beiden Dateien verschoben wird:- Das verbrauchende Projekt.
- Einen Speicherort, auf den das verbrauchende Projekt zugreifen kann.
- Die Abhängigkeitendatei des Hostingstarts wird für die erweiterte App wie im Abschnitt Laufzeitspeicher beschrieben (ohne Kompilierzeitverweis) verfügbar gemacht.
- Wenn das Ziel .NET Framework ist, kann die Assembly in den Standardladekontext geladen werden, was bei .NET Framework bedeutet, dass sich die Assembly an einem der folgenden Speicherorte befindet:
- Anwendungsbasispfad: Dabei handelt es sich um den Ordner bin, in dem die ausführbare Datei ( .exe) der App gespeichert wird.
- Globaler Assemblycache (GAC): Der GAC speichert Assemblys, die mehrere .NET Framework-Apps gemeinsam nutzen. Weitere Informationen finden Sie unter Vorgehensweise: Installieren einer Assembly in den globalen Assemblycache in der .NET Framework-Dokumentation.
Beispielcode
Der Beispielcode (Herunterladen) zeigt Szenarios für die Hostingstartimplementierung:
- Zwei Hostingstartassemblys (Klassenbibliotheken) legen zwei Schlüssel-Wert-Paare der Konfiguration im Arbeitsspeicher fest:
- NuGet-Paket (HostingStartupPackage)
- Klassenbibliothek (HostingStartupLibrary)
- Ein Hostingstart wird über eine im Laufzeitspeicher bereitgestellte Assembly (StartupDiagnostics) aktiviert. Die Assembly fügt der App zum Start zwei Middlewares hinzu, die Diagnoseinformationen zu folgenden Komponenten bereitstellen:
- Registrierte Dienste
- Adresse (Schema, Host, Basispfad, Pfad, Abfragezeichenfolge)
- Verbindung (Remote-IP, Remoteport, lokale IP, lokaler Port, Clientzertifikat)
- Anforderungsheader
- Umgebungsvariablen
So führen Sie das Beispiel aus:
Aktivierung über ein NuGet-Paket
Kompilieren Sie das Paket HostingStartupPackage mit dem Befehl dotnet pack.
Fügen Sie den Assemblynamen des Pakets HostingStartupPackage zur Umgebungsvariablen
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
hinzu.Kompilieren Sie die App, und führen Sie diese aus. In der erweiterten App ist ein Paketverweis vorhanden (Kompilierzeitverweis). Eine
<PropertyGroup>
in der Projektdatei der App gibt die Ausgabe des Paketprojekts ( ../HostingStartupPackage/bin/Debug) als Paketquelle an. Dadurch kann die Anwendung das Paket verwenden, ohne das Paket in nuget.org hochzuladen. Weitere Informationen finden Sie in den Hinweisen in der Projektdatei von HostingStartupApp.<PropertyGroup> <RestoreSources>$(RestoreSources);https://api.nuget.org/v3/index.json;../HostingStartupPackage/bin/Debug</RestoreSources> </PropertyGroup>
Die von der Indexseite gerenderten Schlüsselwerte der Dienstkonfiguration entsprechen den durch die
ServiceKeyInjection.Configure
-Methode des Pakets festgelegten Werten.
Wenn Sie am Projekt HostingStartupPackage Änderungen vornehmen und das Projekt erneut kompilieren, bereinigen Sie die lokalen NuGet-Paketcaches, um sicherzustellen, dass die HostingStartupApp das aktualisierte Paket erhält und kein veraltetes Paket aus dem lokalen Cache. Um die lokalen NuGet-Caches zu bereinigen, führen Sie den folgenden dotnet nuget locals-Befehl aus:
dotnet nuget locals all --clear
Aktivierung über eine Klassenbibliothek
Kompilieren Sie die Klassenbibliothek HostingStartupLibrary mit dem Befehl dotnet build.
Fügen Sie der Umgebungsvariablen
ASPNETCORE_HOSTINGSTARTUPASSEMBLIES
den Assemblynamen HostingStartupLibrary der Klassenbibliothek hinzu.Stellen Sie die Assembly der Klassenbibliothek mittels bin für die App bereit, indem Sie die Datei HostingStartupLibrary.dll aus der kompilierten Ausgabe der Klassenbibliothek in den Ordner bin/Debug der App kopieren.
Kompilieren Sie die App, und führen Sie diese aus. Eine
<ItemGroup>
in der Projektdatei der App verweist auf die Assembly der Klassenbibliothek ( .\bin\Debug\netcoreapp2.1\HostingStartupLibrary.dll) (Kompilierzeitverweis). Weitere Informationen finden Sie in den Hinweisen in der Projektdatei von HostingStartupApp.<ItemGroup> <Reference Include=".\\bin\\Debug\\netcoreapp2.1\\HostingStartupLibrary.dll"> <HintPath>.\bin\Debug\netcoreapp2.1\HostingStartupLibrary.dll</HintPath> <SpecificVersion>False</SpecificVersion> </Reference> </ItemGroup>
Die von der Indexseite gerenderten Schlüsselwerte der Dienstkonfiguration entsprechen den durch die
ServiceKeyInjection.Configure
-Methode der Klassenbibliothek festgelegten Werten.
Aktivierung über eine mittels Laufzeitspeicher bereitgestellten Assembly
- Im Projekt StartupDiagnostics wird PowerShell verwendet, um die Datei
StartupDiagnostics.deps.json
zu bearbeiten. PowerShell ist standardmäßig auf Windows-Betriebssystemen ab Windows 7 SP1 und Windows Server 2008 R2 SP1 installiert. Im Artikel Installieren verschiedener Versionen von PowerShell erfahren Sie, wie Sie PowerShell auf anderen Plattformen erwerben können. - Führen Sie das Skript build.ps1 im Ordner RuntimeStore aus. Das Skript:
- Generiert das
StartupDiagnostics
-Paket im Ordner obj\packages . - Generiert den Laufzeitspeicher für
StartupDiagnostics
im Ordner store. Derdotnet store
-Befehl im Skript verwendet den Laufzeitbezeichner (RID)win7-x64
für einen für Windows bereitgestellten Hostingstart. Wenn der Hostingstart für eine andere Laufzeit bereitgestellt wird, muss in Zeile 37 die entsprechende RID eingegeben werden. Der Runtimespeicher fürStartupDiagnostics
würde später in den Runtimespeicher des Benutzers oder Systems auf dem Computer verschoben, auf dem die Assembly verwendet wird. Der Installationsspeicherort für den Benutzerruntimespeicher für dieStartupDiagnostics
-Assembly ist .dotnet/store/x64/netcoreapp2.2/startupdiagnostics/1.0.0/lib/netcoreapp2.2/StartupDiagnostics.dll. - Generiert die
additionalDeps
fürStartupDiagnostics
im Ordner additionalDeps . Die zusätzlichen Abhängigkeiten würden später in die zusätzlichen Abhängigkeiten des Benutzers oder Systems verschoben. Der Installationsspeicherort der zusätzlichen Abhängigkeiten des BenutzersStartupDiagnostics
ist.dotnet/x64/additionalDeps/StartupDiagnostics/shared/Microsoft.NETCore.App/2.2.0/StartupDiagnostics.deps.json
. - Legt die Datei deploy.ps1 im Ordner deployment ab.
- Generiert das
- Führen Sie das Skript deploy.ps1 im Ordner deployment aus. Das Skript fügt Folgendes:
StartupDiagnostics
an die UmgebungsvariableASPNETCORE_HOSTINGSTARTUPASSEMBLIES
.- Der Pfad der Hostingstartabhängigkeiten (im Ordner deployment des RuntimeStore-Projekts) zur
DOTNET_ADDITIONAL_DEPS
-Umgebungsvariablen. - Der Pfad des Runtimespeichers (im Ordner deployment des RuntimeStore-Projekts) zur
DOTNET_SHARED_STORE
-Umgebungsvariablen.
- Führen Sie die Beispiel-App aus.
- Fordern Sie den Endpunkt
/services
an, um die registrierten Dienste der App anzuzeigen. Fordern Sie den Endpunkt/diag
an, um Diagnoseinformationen anzuzeigen.