obsługa platformy ASP.NET Core dla natywnej usługi AOT
Autor: Mitch Denny
ASP.NET Core 8.0 wprowadza obsługę natywnej platformy .NET przed czasem (AOT).
Aby zapoznać Blazor WebAssembly się ze wskazówkami dotyczącymi natywnej funkcji AOT, która dodaje lub zastępuje wskazówki zawarte w tym artykule, zobacz ASP.NET Core Blazor WebAssembly build tools and ahead-of-time (AOT) build tools and ahead-of-time (AOT) build tools (Przed czasem kompilacji).
Dlaczego warto używać natywnej AOT z platformą ASP.NET Core
Publikowanie i wdrażanie natywnej aplikacji AOT zapewnia następujące korzyści:
- Zminimalizowane zużycie dysku: podczas publikowania przy użyciu natywnej funkcji AOT jest tworzony pojedynczy plik wykonywalny zawierający tylko kod z zależności zewnętrznych, które są potrzebne do obsługi programu. Zmniejszony rozmiar pliku wykonywalnego może prowadzić do:
- Mniejsze obrazy kontenerów, na przykład w scenariuszach wdrażania konteneryzowanego.
- Skrócony czas wdrażania z mniejszych obrazów.
- Skrócony czas uruchamiania: natywne aplikacje AOT mogą pokazywać skrócone czasy uruchamiania, co oznacza
- Aplikacja jest gotowa do szybszego obsługi żądań.
- Ulepszone wdrożenie, w którym koordynatorzy kontenerów muszą zarządzać przejściem z jednej wersji aplikacji do innej.
- Mniejsze zapotrzebowanie na pamięć: natywne aplikacje AOT mogą mieć mniejsze zapotrzebowanie na pamięć w zależności od pracy wykonywanej przez aplikację. Zmniejszenie zużycia pamięci może prowadzić do większej gęstości wdrożenia i zwiększenia skalowalności.
Aplikacja szablonu została uruchomiona w naszym laboratorium porównawczym, aby porównać wydajność opublikowanej aplikacji AOT, przyciętej aplikacji środowiska uruchomieniowego i nietrimmed aplikacji środowiska uruchomieniowego. Na poniższym wykresie przedstawiono wyniki testów porównawczych:
Na poprzednim wykresie pokazano, że natywna usługa AOT ma mniejszy rozmiar aplikacji, użycie pamięci i czas uruchamiania.
zgodność ASP.NET Core i natywna funkcja AOT
Nie wszystkie funkcje w systemie ASP.NET Core są obecnie zgodne z natywną funkcją AOT. Poniższa tabela zawiera podsumowanie zgodności funkcji ASP.NET Core z natywną funkcją AOT:
Funkcja | W pełni obsługiwane | Częściowo obsługiwane | Nieobsługiwany |
---|---|---|---|
gRPC | W pełni obsługiwane | ||
Minimalne interfejsy API | Częściowo obsługiwane | ||
MVC | Nieobsługiwane | ||
Blazor Server | Nieobsługiwane | ||
SignalR | Częściowo obsługiwane | ||
Uwierzytelnianie JWT | W pełni obsługiwane | ||
Inne uwierzytelnianie | Nieobsługiwane | ||
CORS | W pełni obsługiwane | ||
Kontrole kondycji | W pełni obsługiwane | ||
Rejestrowanie http | W pełni obsługiwane | ||
Lokalizacja | W pełni obsługiwane | ||
OutputCaching | W pełni obsługiwane | ||
RateLimiting | W pełni obsługiwane | ||
RequestDecompression | W pełni obsługiwane | ||
OdpowiedźCaching | W pełni obsługiwane | ||
OdpowiedźKompresja | W pełni obsługiwane | ||
Przepisać | W pełni obsługiwane | ||
Sesja | Nieobsługiwane | ||
Uzdrowisko | Nieobsługiwane | ||
StaticFiles | W pełni obsługiwane | ||
Protokoły WebSocket | W pełni obsługiwane |
Aby uzyskać więcej informacji na temat ograniczeń, zobacz:
- Ograniczenia wdrożenia natywnej usługi AOT
- Wprowadzenie do ostrzeżeń AOT
- Znane przycinanie niezgodności
- Wprowadzenie do ostrzeżeń dotyczących przycinania
- Problem z usługą GitHub dotnet/core #8288
Ważne jest, aby dokładnie przetestować aplikację podczas przechodzenia do natywnego modelu wdrażania AOT. Aplikacja wdrożona przez usługę AOT powinna zostać przetestowana w celu sprawdzenia, czy funkcjonalność nie została zmieniona z niezatrimmed i skompilowanej aplikacji JIT. Podczas kompilowania aplikacji przejrzyj i popraw ostrzeżenia dotyczące AOT. Aplikacja, która wystawia ostrzeżenia AOT podczas publikowania, może nie działać poprawnie. Jeśli w czasie publikowania nie zostaną wydane żadne ostrzeżenia dotyczące funkcji AOT, opublikowana aplikacja AOT powinna działać tak samo jak nietrimmed i skompilowana aplikacja JIT.
Publikowanie natywnej usługi AOT
Natywna funkcja AOT jest włączona z właściwością PublishAot
MSBuild. W poniższym przykładzie pokazano, jak włączyć natywną funkcję AOT w pliku projektu:
<PropertyGroup>
<PublishAot>true</PublishAot>
</PropertyGroup>
To ustawienie umożliwia natywną kompilację AOT podczas publikowania i umożliwia dynamiczną analizę użycia kodu podczas kompilacji i edycji. Projekt korzystający z natywnego publikowania AOT używa kompilacji JIT podczas uruchamiania lokalnego. Aplikacja AOT ma następujące różnice w porównaniu z aplikacją skompilowana w trybie JIT:
- Funkcje, które nie są zgodne z natywną funkcją AOT, są wyłączone i zgłaszają wyjątki w czasie wykonywania.
- Analizator źródła jest włączony, aby wyróżnić kod, który nie jest zgodny z natywną funkcją AOT. W czasie publikowania cała aplikacja, w tym pakiety NuGet, jest ponownie analizowana pod kątem zgodności.
Natywna analiza AOT obejmuje cały kod aplikacji i biblioteki, od których zależy aplikacja. Przejrzyj ostrzeżenia dotyczące natywnej usługi AOT i wykonaj kroki naprawcze. Dobrym pomysłem jest częste publikowanie aplikacji w celu wykrycia problemów na wczesnym etapie cyklu projektowania.
Na platformie .NET 8 natywna funkcja AOT jest obsługiwana przez następujące typy aplikacji ASP.NET Core:
- minimalne interfejsy API — aby uzyskać więcej informacji, zobacz sekcję szablonu interfejsu API sieci Web (natywna funkcja AOT) w dalszej części tego artykułu.
- gRPC — aby uzyskać więcej informacji, zobacz gRPC i Native AOT.
- Usługi robocze — aby uzyskać więcej informacji, zobacz AOT w szablonach usługi roboczej.
Szablon interfejsu API sieci Web (natywna funkcja AOT)
Szablon ASP.NET Core Web API (native AOT) (krótka nazwawebapiaot
) tworzy projekt z włączoną funkcją AOT. Szablon różni się od szablonu projektu internetowego interfejsu API w następujący sposób:
- Używa tylko minimalnych interfejsów API, ponieważ usługa MVC nie jest jeszcze zgodna z natywną funkcją AOT.
- Używa interfejsu CreateSlimBuilder() API, aby upewnić się, że tylko podstawowe funkcje są domyślnie włączone, minimalizując rozmiar wdrożonej aplikacji.
- Jest skonfigurowany do nasłuchiwania tylko w protokole HTTP, ponieważ ruch HTTPS jest często obsługiwany przez usługę ruchu przychodzącego we wdrożeniach natywnych dla chmury.
- Nie zawiera profilu uruchamiania do uruchamiania w usługach IIS lub IIS Express.
.http
Tworzy plik skonfigurowany przy użyciu przykładowych żądań HTTP, które można wysyłać do punktów końcowych aplikacji.- Zawiera przykładowy
Todo
interfejs API zamiast przykładu prognozy pogody. - Dodaje
PublishAot
do pliku projektu, jak pokazano wcześniej w tym artykule. - Włącza generatory źródeł serializatora JSON. Generator źródła służy do generowania kodu serializacji w czasie kompilacji, który jest wymagany do kompilacji natywnej AOT.
Zmiany w zakresie obsługi generowania źródła
W poniższym przykładzie pokazano kod dodany do Program.cs
pliku w celu obsługi generowania źródła serializacji JSON:
using MyFirstAotWebApi;
+using System.Text.Json.Serialization;
-var builder = WebApplication.CreateBuilder();
+var builder = WebApplication.CreateSlimBuilder(args);
+builder.Services.ConfigureHttpJsonOptions(options =>
+{
+ options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
+});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
+[JsonSerializable(typeof(Todo[]))]
+internal partial class AppJsonSerializerContext : JsonSerializerContext
+{
+
+}
Bez tego dodanego kodu System.Text.Json
użyto odbicia w celu serializacji i deserializacji danych JSON. Odbicie nie jest obsługiwane w natywnej AOT.
Aby uzyskać więcej informacji, zobacz:
Zmiany w launchSettings.json
Plik launchSettings.json
utworzony przez szablon interfejsu API sieci Web (natywny AOT) zawiera sekcję iisSettings
i IIS Express
profil został usunięty:
{
"$schema": "http://json.schemastore.org/launchsettings.json",
- "iisSettings": {
- "windowsAuthentication": false,
- "anonymousAuthentication": true,
- "iisExpress": {
- "applicationUrl": "http://localhost:11152",
- "sslPort": 0
- }
- },
"profiles": {
"http": {
"commandName": "Project",
"dotnetRunMessages": true,
"launchBrowser": true,
"launchUrl": "todos",
"applicationUrl": "http://localhost:5102",
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
}
},
- "IIS Express": {
- "commandName": "IISExpress",
- "launchBrowser": true,
- "launchUrl": "todos",
- "environmentVariables": {
- "ASPNETCORE_ENVIRONMENT": "Development"
- }
- }
}
}
Metoda CreateSlimBuilder
Szablon używa CreateSlimBuilder() metody zamiast CreateBuilder() metody .
using System.Text.Json.Serialization;
using MyFirstAotWebApi;
var builder = WebApplication.CreateSlimBuilder(args);
builder.Logging.AddConsole();
builder.Services.ConfigureHttpJsonOptions(options =>
{
options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
[JsonSerializable(typeof(Todo[]))]
internal partial class AppJsonSerializerContext : JsonSerializerContext
{
}
Metoda CreateSlimBuilder
inicjuje WebApplicationBuilder element z minimalnymi funkcjami ASP.NET Core niezbędnymi do uruchomienia aplikacji.
Jak wspomniano wcześniej, CreateSlimBuilder
metoda nie obejmuje obsługi protokołu HTTPS lub HTTP/3. Te protokoły zazwyczaj nie są wymagane w przypadku aplikacji uruchamianych za serwerem proxy zakończenia protokołu TLS. Zobacz na przykład kończenie żądań protokołu TLS i kończenie szyfrowania TLS za pomocą usługi Application Gateway. Protokół HTTPS można włączyć przez wywołanie konstruktora. WebHost.UseKestrelHttpsConfiguration HTTP/3 można włączyć przez wywołanie konstruktora. WebHost.UseQuic.
Klasa CreateSlimBuilder
a klasa CreateBuilder
Metoda CreateSlimBuilder
nie obsługuje następujących funkcji obsługiwanych przez metodę CreateBuilder
:
- Hosting zestawów startowych
- UseStartup
- Następujący dostawcy rejestrowania:
- Funkcje hostingu internetowego:
- Kestrel konfiguracja
- Ograniczenia regex i alfa używane w routingu
Metoda CreateSlimBuilder
zawiera następujące funkcje potrzebne do wydajnego środowiska programistycznego:
- Konfiguracja pliku JSON dla elementów
appsettings.json
iappsettings.{EnvironmentName}.json
. - Konfiguracja wpisów tajnych użytkownika.
- Rejestrowanie konsoli.
- Konfiguracja rejestrowania.
Aby zapoznać się z konstruktorem pomijającym poprzednie funkcje, zobacz CreateEmptyBuilder
Metoda .
Włączenie minimalnych funkcji ma zalety przycinania, a także AOT. Aby uzyskać więcej informacji, zobacz Przycinanie samodzielnych wdrożeń i plików wykonywalnych.
Aby uzyskać bardziej szczegółowe informacje, zobacz Porównanie WebApplication.CreateBuilder
z CreateSlimBuilder
Generatory źródeł
Ponieważ nieużywany kod jest przycinany podczas publikowania dla natywnej AOT, aplikacja nie może używać niezwiązanego odbicia w czasie wykonywania. Generatory źródeł są używane do tworzenia kodu, który pozwala uniknąć konieczności odbicia. W niektórych przypadkach generatory źródłowe generują kod zoptymalizowany pod kątem AOT nawet wtedy, gdy generator nie jest wymagany.
Aby wyświetlić wygenerowany kod źródłowy, dodaj EmitCompilerGeneratedFiles
właściwość do pliku aplikacji .csproj
, jak pokazano w poniższym przykładzie:
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<!-- Other properties omitted for brevity -->
<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
</PropertyGroup>
</Project>
Uruchom polecenie , dotnet build
aby wyświetlić wygenerowany kod. Dane wyjściowe zawierają obj/Debug/net8.0/generated/
katalog zawierający wszystkie wygenerowane pliki dla projektu.
Polecenie dotnet publish
kompiluje również pliki źródłowe i generuje skompilowane pliki. Ponadto dotnet publish
przekazuje wygenerowane zestawy do natywnego kompilatora IL. Kompilator IL tworzy natywny plik wykonywalny. Natywny plik wykonywalny zawiera natywny kod maszyny.
Biblioteki i natywna usługa AOT
Wiele popularnych bibliotek używanych w projektach ASP.NET Core ma obecnie pewne problemy ze zgodnością w przypadku użycia w projekcie przeznaczonym dla natywnej funkcji AOT, takich jak:
- Używanie odbicia do sprawdzania i odnajdywania typów.
- Warunkowe ładowanie bibliotek w czasie wykonywania.
- Generowanie kodu na bieżąco w celu zaimplementowania funkcji.
Biblioteki korzystające z tych funkcji dynamicznych należy zaktualizować w celu pracy z natywną usługą AOT. Można je aktualizować przy użyciu narzędzi, takich jak generatory źródeł Roslyn.
Autorzy bibliotek, którzy mają nadzieję obsługiwać natywną usługę AOT, są zachęcani do:
- Przeczytaj o wymaganiach dotyczących zgodności z natywną usługą AOT.
- Przygotuj bibliotekę do przycinania.
Minimalne interfejsy API i ładunki JSON
Minimalna struktura interfejsu API jest zoptymalizowana pod kątem odbierania i zwracania ładunków JSON przy użyciu polecenia System.Text.Json. System.Text.Json
:
- Nakłada wymagania dotyczące zgodności dla formatu JSON i natywnego AOT.
- Wymaga użycia generatora źródłowego.
System.Text.Json
Wszystkie typy przesyłane jako część treści HTTP lub zwracane z delegatów żądań w aplikacjach minimalnych interfejsów API muszą być skonfigurowane na obiekcie JsonSerializerContext , który jest zarejestrowany za pośrednictwem wstrzykiwania zależności ASP.NET Core:
using System.Text.Json.Serialization;
using MyFirstAotWebApi;
var builder = WebApplication.CreateSlimBuilder(args);
builder.Logging.AddConsole();
builder.Services.ConfigureHttpJsonOptions(options =>
{
options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
[JsonSerializable(typeof(Todo[]))]
internal partial class AppJsonSerializerContext : JsonSerializerContext
{
}
W poprzednim wyróżnionym kodzie:
- Kontekst serializatora JSON jest zarejestrowany w kontenerze DI. Aby uzyskać więcej informacji, zobacz:
- Element niestandardowy
JsonSerializerContext
jest oznaczony adnotacją z atrybutem[JsonSerializable]
umożliwiającym włączenie kodu serializatora JSON wygenerowanegoToDo
przez źródło dla typu.
Parametr delegata, który nie jest powiązany z treścią i nie musi być serializowalny. Na przykład parametr ciągu zapytania, który jest bogatym typem obiektu i implementuje IParsable<T>
element .
public class Todo
{
public int Id { get; set; }
public string? Title { get; set; }
public DateOnly? DueBy { get; set; }
public bool IsComplete { get; set; }
}
static class TodoGenerator
{
private static readonly (string[] Prefixes, string[] Suffixes)[] _parts = new[]
{
(new[] { "Walk the", "Feed the" }, new[] { "dog", "cat", "goat" }),
(new[] { "Do the", "Put away the" }, new[] { "groceries", "dishes", "laundry" }),
(new[] { "Clean the" }, new[] { "bathroom", "pool", "blinds", "car" })
};
// Remaining code omitted for brevity.
Znane problemy
Zobacz ten problem z usługą GitHub, aby zgłosić lub przejrzeć problemy z natywną obsługą usługi AOT w usłudze ASP.NET Core.
Zobacz też
- Samouczek: publikowanie aplikacji ASP.NET Core przy użyciu natywnej usługi AOT
- Wdrożenie natywnej usługi AOT
- Optymalizowanie wdrożeń usługi AOT
- Generator źródła powiązania konfiguracji
- Korzystanie z generatora źródła powiązania konfiguracji
- Minimalny szablon kompilacji AOT interfejsu API
- Porównanie
WebApplication.CreateBuilder
zCreateSlimBuilder
- Eksplorowanie nowego minimalnego generatora źródła interfejsu API
- Zastępowanie wywołań metod przechwytujących
- Za
[LogProperties]
i nowy generator źródeł rejestrowania telemetrii
ASP.NET Core 8.0 wprowadza obsługę natywnej platformy .NET przed czasem (AOT).
Dlaczego warto używać natywnej AOT z platformą ASP.NET Core
Publikowanie i wdrażanie natywnej aplikacji AOT zapewnia następujące korzyści:
- Zminimalizowane zużycie dysku: podczas publikowania przy użyciu natywnej funkcji AOT jest tworzony pojedynczy plik wykonywalny zawierający tylko kod z zależności zewnętrznych, które są potrzebne do obsługi programu. Zmniejszony rozmiar pliku wykonywalnego może prowadzić do:
- Mniejsze obrazy kontenerów, na przykład w scenariuszach wdrażania konteneryzowanego.
- Skrócony czas wdrażania z mniejszych obrazów.
- Skrócony czas uruchamiania: natywne aplikacje AOT mogą pokazywać skrócone czasy uruchamiania, co oznacza
- Aplikacja jest gotowa do szybszego obsługi żądań.
- Ulepszone wdrożenie, w którym koordynatorzy kontenerów muszą zarządzać przejściem z jednej wersji aplikacji do innej.
- Mniejsze zapotrzebowanie na pamięć: natywne aplikacje AOT mogą mieć mniejsze zapotrzebowanie na pamięć w zależności od pracy wykonywanej przez aplikację. Zmniejszenie zużycia pamięci może prowadzić do większej gęstości wdrożenia i zwiększenia skalowalności.
Aplikacja szablonu została uruchomiona w naszym laboratorium porównawczym, aby porównać wydajność opublikowanej aplikacji AOT, przyciętej aplikacji środowiska uruchomieniowego i nietrimmed aplikacji środowiska uruchomieniowego. Na poniższym wykresie przedstawiono wyniki testów porównawczych:
Na poprzednim wykresie pokazano, że natywna usługa AOT ma mniejszy rozmiar aplikacji, użycie pamięci i czas uruchamiania.
zgodność ASP.NET Core i natywna funkcja AOT
Nie wszystkie funkcje w systemie ASP.NET Core są obecnie zgodne z natywną funkcją AOT. Poniższa tabela zawiera podsumowanie zgodności funkcji ASP.NET Core z natywną funkcją AOT:
Funkcja | W pełni obsługiwane | Częściowo obsługiwane | Nieobsługiwany |
---|---|---|---|
gRPC | W pełni obsługiwane | ||
Minimalne interfejsy API | Częściowo obsługiwane | ||
MVC | Nieobsługiwane | ||
Blazor Server | Nieobsługiwane | ||
SignalR | Nieobsługiwane | ||
Uwierzytelnianie JWT | W pełni obsługiwane | ||
Inne uwierzytelnianie | Nieobsługiwane | ||
CORS | W pełni obsługiwane | ||
Kontrole kondycji | W pełni obsługiwane | ||
Rejestrowanie http | W pełni obsługiwane | ||
Lokalizacja | W pełni obsługiwane | ||
OutputCaching | W pełni obsługiwane | ||
RateLimiting | W pełni obsługiwane | ||
RequestDecompression | W pełni obsługiwane | ||
OdpowiedźCaching | W pełni obsługiwane | ||
OdpowiedźKompresja | W pełni obsługiwane | ||
Przepisać | W pełni obsługiwane | ||
Sesja | Nieobsługiwane | ||
Uzdrowisko | Nieobsługiwane | ||
StaticFiles | W pełni obsługiwane | ||
Protokoły WebSocket | W pełni obsługiwane |
Aby uzyskać więcej informacji na temat ograniczeń, zobacz:
- Ograniczenia wdrożenia natywnej usługi AOT
- Wprowadzenie do ostrzeżeń AOT
- Znane przycinanie niezgodności
- Wprowadzenie do ostrzeżeń dotyczących przycinania
- Problem z usługą GitHub dotnet/core #8288
Ważne jest, aby dokładnie przetestować aplikację podczas przechodzenia do natywnego modelu wdrażania AOT. Aplikacja wdrożona przez usługę AOT powinna zostać przetestowana w celu sprawdzenia, czy funkcjonalność nie została zmieniona z niezatrimmed i skompilowanej aplikacji JIT. Podczas kompilowania aplikacji przejrzyj i popraw ostrzeżenia dotyczące AOT. Aplikacja, która wystawia ostrzeżenia AOT podczas publikowania, może nie działać poprawnie. Jeśli w czasie publikowania nie zostaną wydane żadne ostrzeżenia dotyczące funkcji AOT, opublikowana aplikacja AOT powinna działać tak samo jak nietrimmed i skompilowana aplikacja JIT.
Publikowanie natywnej usługi AOT
Natywna funkcja AOT jest włączona z właściwością PublishAot
MSBuild. W poniższym przykładzie pokazano, jak włączyć natywną funkcję AOT w pliku projektu:
<PropertyGroup>
<PublishAot>true</PublishAot>
</PropertyGroup>
To ustawienie umożliwia natywną kompilację AOT podczas publikowania i umożliwia dynamiczną analizę użycia kodu podczas kompilacji i edycji. Projekt korzystający z natywnego publikowania AOT używa kompilacji JIT podczas uruchamiania lokalnego. Aplikacja AOT ma następujące różnice w porównaniu z aplikacją skompilowana w trybie JIT:
- Funkcje, które nie są zgodne z natywną funkcją AOT, są wyłączone i zgłaszają wyjątki w czasie wykonywania.
- Analizator źródła jest włączony, aby wyróżnić kod, który nie jest zgodny z natywną funkcją AOT. W czasie publikowania cała aplikacja, w tym pakiety NuGet, jest ponownie analizowana pod kątem zgodności.
Natywna analiza AOT obejmuje cały kod aplikacji i biblioteki, od których zależy aplikacja. Przejrzyj ostrzeżenia dotyczące natywnej usługi AOT i wykonaj kroki naprawcze. Dobrym pomysłem jest częste publikowanie aplikacji w celu wykrycia problemów na wczesnym etapie cyklu projektowania.
Na platformie .NET 8 natywna funkcja AOT jest obsługiwana przez następujące typy aplikacji ASP.NET Core:
- minimalne interfejsy API — aby uzyskać więcej informacji, zobacz sekcję szablonu interfejsu API sieci Web (natywna funkcja AOT) w dalszej części tego artykułu.
- gRPC — aby uzyskać więcej informacji, zobacz gRPC i Native AOT.
- Usługi robocze — aby uzyskać więcej informacji, zobacz AOT w szablonach usługi roboczej.
Szablon interfejsu API sieci Web (natywna funkcja AOT)
Szablon ASP.NET Core Web API (native AOT) (krótka nazwawebapiaot
) tworzy projekt z włączoną funkcją AOT. Szablon różni się od szablonu projektu internetowego interfejsu API w następujący sposób:
- Używa tylko minimalnych interfejsów API, ponieważ usługa MVC nie jest jeszcze zgodna z natywną funkcją AOT.
- Używa interfejsu CreateSlimBuilder() API, aby upewnić się, że tylko podstawowe funkcje są domyślnie włączone, minimalizując rozmiar wdrożonej aplikacji.
- Jest skonfigurowany do nasłuchiwania tylko w protokole HTTP, ponieważ ruch HTTPS jest często obsługiwany przez usługę ruchu przychodzącego we wdrożeniach natywnych dla chmury.
- Nie zawiera profilu uruchamiania do uruchamiania w usługach IIS lub IIS Express.
.http
Tworzy plik skonfigurowany przy użyciu przykładowych żądań HTTP, które można wysyłać do punktów końcowych aplikacji.- Zawiera przykładowy
Todo
interfejs API zamiast przykładu prognozy pogody. - Dodaje
PublishAot
do pliku projektu, jak pokazano wcześniej w tym artykule. - Włącza generatory źródeł serializatora JSON. Generator źródła służy do generowania kodu serializacji w czasie kompilacji, który jest wymagany do kompilacji natywnej AOT.
Zmiany w zakresie obsługi generowania źródła
W poniższym przykładzie pokazano kod dodany do Program.cs
pliku w celu obsługi generowania źródła serializacji JSON:
using MyFirstAotWebApi;
+using System.Text.Json.Serialization;
-var builder = WebApplication.CreateBuilder();
+var builder = WebApplication.CreateSlimBuilder(args);
+builder.Services.ConfigureHttpJsonOptions(options =>
+{
+ options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
+});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
+[JsonSerializable(typeof(Todo[]))]
+internal partial class AppJsonSerializerContext : JsonSerializerContext
+{
+
+}
Bez tego dodanego kodu System.Text.Json
użyto odbicia w celu serializacji i deserializacji danych JSON. Odbicie nie jest obsługiwane w natywnej AOT.
Aby uzyskać więcej informacji, zobacz:
Zmiany w launchSettings.json
Plik launchSettings.json
utworzony przez szablon interfejsu API sieci Web (natywny AOT) zawiera sekcję iisSettings
i IIS Express
profil został usunięty:
{
"$schema": "http://json.schemastore.org/launchsettings.json",
- "iisSettings": {
- "windowsAuthentication": false,
- "anonymousAuthentication": true,
- "iisExpress": {
- "applicationUrl": "http://localhost:11152",
- "sslPort": 0
- }
- },
"profiles": {
"http": {
"commandName": "Project",
"dotnetRunMessages": true,
"launchBrowser": true,
"launchUrl": "todos",
"applicationUrl": "http://localhost:5102",
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
}
},
- "IIS Express": {
- "commandName": "IISExpress",
- "launchBrowser": true,
- "launchUrl": "todos",
- "environmentVariables": {
- "ASPNETCORE_ENVIRONMENT": "Development"
- }
- }
}
}
Metoda CreateSlimBuilder
Szablon używa CreateSlimBuilder() metody zamiast CreateBuilder() metody .
using System.Text.Json.Serialization;
using MyFirstAotWebApi;
var builder = WebApplication.CreateSlimBuilder(args);
builder.Logging.AddConsole();
builder.Services.ConfigureHttpJsonOptions(options =>
{
options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
[JsonSerializable(typeof(Todo[]))]
internal partial class AppJsonSerializerContext : JsonSerializerContext
{
}
Metoda CreateSlimBuilder
inicjuje WebApplicationBuilder element z minimalnymi funkcjami ASP.NET Core niezbędnymi do uruchomienia aplikacji.
Jak wspomniano wcześniej, CreateSlimBuilder
metoda nie obejmuje obsługi protokołu HTTPS lub HTTP/3. Te protokoły zazwyczaj nie są wymagane w przypadku aplikacji uruchamianych za serwerem proxy zakończenia protokołu TLS. Zobacz na przykład kończenie żądań protokołu TLS i kończenie szyfrowania TLS za pomocą usługi Application Gateway. Protokół HTTPS można włączyć przez wywołanie konstruktora. WebHost.UseKestrelHttpsConfiguration HTTP/3 można włączyć przez wywołanie konstruktora. WebHost.UseQuic.
Klasa CreateSlimBuilder
a klasa CreateBuilder
Metoda CreateSlimBuilder
nie obsługuje następujących funkcji obsługiwanych przez metodę CreateBuilder
:
- Hosting zestawów startowych
- UseStartup
- Następujący dostawcy rejestrowania:
- Funkcje hostingu internetowego:
- Kestrel konfiguracja
- Ograniczenia regex i alfa używane w routingu
Metoda CreateSlimBuilder
zawiera następujące funkcje potrzebne do wydajnego środowiska programistycznego:
- Konfiguracja pliku JSON dla elementów
appsettings.json
iappsettings.{EnvironmentName}.json
. - Konfiguracja wpisów tajnych użytkownika.
- Rejestrowanie konsoli.
- Konfiguracja rejestrowania.
Aby zapoznać się z konstruktorem pomijającym poprzednie funkcje, zobacz CreateEmptyBuilder
Metoda .
Włączenie minimalnych funkcji ma zalety przycinania, a także AOT. Aby uzyskać więcej informacji, zobacz Przycinanie samodzielnych wdrożeń i plików wykonywalnych.
Aby uzyskać bardziej szczegółowe informacje, zobacz Porównanie WebApplication.CreateBuilder
z CreateSlimBuilder
Generatory źródeł
Ponieważ nieużywany kod jest przycinany podczas publikowania dla natywnej AOT, aplikacja nie może używać niezwiązanego odbicia w czasie wykonywania. Generatory źródeł są używane do tworzenia kodu, który pozwala uniknąć konieczności odbicia. W niektórych przypadkach generatory źródłowe generują kod zoptymalizowany pod kątem AOT nawet wtedy, gdy generator nie jest wymagany.
Aby wyświetlić wygenerowany kod źródłowy, dodaj EmitCompilerGeneratedFiles
właściwość do pliku aplikacji .csproj
, jak pokazano w poniższym przykładzie:
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<!-- Other properties omitted for brevity -->
<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
</PropertyGroup>
</Project>
Uruchom polecenie , dotnet build
aby wyświetlić wygenerowany kod. Dane wyjściowe zawierają obj/Debug/net8.0/generated/
katalog zawierający wszystkie wygenerowane pliki dla projektu.
Polecenie dotnet publish
kompiluje również pliki źródłowe i generuje skompilowane pliki. Ponadto dotnet publish
przekazuje wygenerowane zestawy do natywnego kompilatora IL. Kompilator IL tworzy natywny plik wykonywalny. Natywny plik wykonywalny zawiera natywny kod maszyny.
Biblioteki i natywna usługa AOT
Wiele popularnych bibliotek używanych w projektach ASP.NET Core ma obecnie pewne problemy ze zgodnością w przypadku użycia w projekcie przeznaczonym dla natywnej funkcji AOT, takich jak:
- Używanie odbicia do sprawdzania i odnajdywania typów.
- Warunkowe ładowanie bibliotek w czasie wykonywania.
- Generowanie kodu na bieżąco w celu zaimplementowania funkcji.
Biblioteki korzystające z tych funkcji dynamicznych należy zaktualizować w celu pracy z natywną usługą AOT. Można je aktualizować przy użyciu narzędzi, takich jak generatory źródeł Roslyn.
Autorzy bibliotek, którzy mają nadzieję obsługiwać natywną usługę AOT, są zachęcani do:
- Przeczytaj o wymaganiach dotyczących zgodności z natywną usługą AOT.
- Przygotuj bibliotekę do przycinania.
Minimalne interfejsy API i ładunki JSON
Minimalna struktura interfejsu API jest zoptymalizowana pod kątem odbierania i zwracania ładunków JSON przy użyciu polecenia System.Text.Json. System.Text.Json
:
- Nakłada wymagania dotyczące zgodności dla formatu JSON i natywnego AOT.
- Wymaga użycia generatora źródłowego.
System.Text.Json
Wszystkie typy przesyłane jako część treści HTTP lub zwracane z delegatów żądań w aplikacjach minimalnych interfejsów API muszą być skonfigurowane na obiekcie JsonSerializerContext , który jest zarejestrowany za pośrednictwem wstrzykiwania zależności ASP.NET Core:
using System.Text.Json.Serialization;
using MyFirstAotWebApi;
var builder = WebApplication.CreateSlimBuilder(args);
builder.Logging.AddConsole();
builder.Services.ConfigureHttpJsonOptions(options =>
{
options.SerializerOptions.TypeInfoResolverChain.Insert(0, AppJsonSerializerContext.Default);
});
var app = builder.Build();
var sampleTodos = TodoGenerator.GenerateTodos().ToArray();
var todosApi = app.MapGroup("/todos");
todosApi.MapGet("/", () => sampleTodos);
todosApi.MapGet("/{id}", (int id) =>
sampleTodos.FirstOrDefault(a => a.Id == id) is { } todo
? Results.Ok(todo)
: Results.NotFound());
app.Run();
[JsonSerializable(typeof(Todo[]))]
internal partial class AppJsonSerializerContext : JsonSerializerContext
{
}
W poprzednim wyróżnionym kodzie:
- Kontekst serializatora JSON jest zarejestrowany w kontenerze DI. Aby uzyskać więcej informacji, zobacz:
- Element niestandardowy
JsonSerializerContext
jest oznaczony adnotacją z atrybutem[JsonSerializable]
umożliwiającym włączenie kodu serializatora JSON wygenerowanegoToDo
przez źródło dla typu.
Parametr delegata, który nie jest powiązany z treścią i nie musi być serializowalny. Na przykład parametr ciągu zapytania, który jest bogatym typem obiektu i implementuje IParsable<T>
element .
public class Todo
{
public int Id { get; set; }
public string? Title { get; set; }
public DateOnly? DueBy { get; set; }
public bool IsComplete { get; set; }
}
static class TodoGenerator
{
private static readonly (string[] Prefixes, string[] Suffixes)[] _parts = new[]
{
(new[] { "Walk the", "Feed the" }, new[] { "dog", "cat", "goat" }),
(new[] { "Do the", "Put away the" }, new[] { "groceries", "dishes", "laundry" }),
(new[] { "Clean the" }, new[] { "bathroom", "pool", "blinds", "car" })
};
// Remaining code omitted for brevity.
Znane problemy
Zobacz ten problem z usługą GitHub, aby zgłosić lub przejrzeć problemy z natywną obsługą usługi AOT w usłudze ASP.NET Core.
Zobacz też
- Samouczek: publikowanie aplikacji ASP.NET Core przy użyciu natywnej usługi AOT
- Wdrożenie natywnej usługi AOT
- Optymalizowanie wdrożeń usługi AOT
- Generator źródła powiązania konfiguracji
- Korzystanie z generatora źródła powiązania konfiguracji
- Minimalny szablon kompilacji AOT interfejsu API
- Porównanie
WebApplication.CreateBuilder
zCreateSlimBuilder
- Eksplorowanie nowego minimalnego generatora źródła interfejsu API
- Zastępowanie wywołań metod przechwytujących
- Za
[LogProperties]
i nowy generator źródeł rejestrowania telemetrii