Nota
O acesso a esta página requer autorização. Pode tentar iniciar sessão ou alterar os diretórios.
O acesso a esta página requer autorização. Pode tentar alterar os diretórios.
Por Mitch Denny
Para obter Blazor WebAssembly orientação de AOT nativa, que adiciona ou substitui a orientação neste artigo, consulte Blazor WebAssembly.
Por que usar AOT nativo com ASP.NET Core
Publicar e implantar um aplicativo AOT nativo oferece os seguintes benefícios:
-
Minimized disk footprint: Ao publicar usando AOT nativo, é produzido um único executável que contém apenas o código das dependências externas necessário para suportar o programa. O tamanho reduzido do executável pode levar a:
- Imagens de contentor mais pequenas, por exemplo, em cenários de implantação em contentores.
- Tempo de implantação reduzido a partir de imagens menores.
-
Tempo de inicialização reduzido: Os aplicativos AOT nativos podem mostrar tempos de inicialização reduzidos, o que significa
- O aplicativo está pronto para atender solicitações mais rapidamente.
- Implantação aprimorada em que os orquestradores de contêineres precisam gerenciar a transição de uma versão do aplicativo para outra.
- Demanda de memória reduzida: Os aplicativos AOT nativos podem ter demandas de memória reduzidas, dependendo do trabalho feito pelo aplicativo. O consumo reduzido de memória pode levar a uma maior densidade de implantação e melhor escalabilidade.
O aplicativo de modelo foi executado em nosso laboratório de benchmarking para comparar o desempenho de um aplicativo publicado pela AOT, um aplicativo de tempo de execução cortado e um aplicativo de tempo de execução não cortado. O gráfico a seguir mostra os resultados do benchmarking:
O gráfico anterior mostra que a AOT nativa tem menor tamanho de aplicativo, uso de memória e tempo de inicialização.
Compatibilidade do ASP.NET Core com AOT nativo
Nem todos os recursos do ASP.NET Core são atualmente compatíveis com a AOT nativa. A tabela a seguir resume a compatibilidade de recursos do ASP.NET Core com o AOT Nativo:
| Funcionalidade | Totalmente suportado | Parcialmente suportado | Não suportado |
|---|---|---|---|
| gRPC | ✔️ Totalmente suportado | ||
| APIs mínimas | ✔️ Parcialmente suportado | ||
| MVC | Não suportado | ||
| Blazor Server | Não suportado | ||
| SignalR | ✔️ Parcialmente suportado | ||
| Autenticação JWT | ✔️ Totalmente suportado | ||
| Outra autenticação | Não suportado | ||
| CORS | ✔️ Totalmente suportado | ||
| Verificações de saúde | ✔️ Totalmente suportado | ||
| Registo HTTP | ✔️ Totalmente suportado | ||
| Localização | ✔️ Totalmente suportado | ||
| OutputCaching | ✔️ Totalmente suportado | ||
| Limitação de Taxa | ✔️ Totalmente suportado | ||
| PedidoDescompressão | ✔️ Totalmente suportado | ||
| Cache de Respostas | ✔️ Totalmente suportado | ||
| CompressãoDeResposta | ✔️ Totalmente suportado | ||
| Reescrever | ✔️ Totalmente suportado | ||
| Sessão | Não suportado | ||
| Termas | Não suportado | ||
| Arquivos Estáticos | ✔️ Totalmente suportado | ||
| WebSockets | ✔️ Totalmente suportado |
Para obter mais informações sobre limitações, consulte:
- Limitações da implantação de AOT nativo
- Introdução aos avisos AOT
- Incompatibilidades de corte conhecidas
- Introdução aos alertas de corte
- Problema do GitHub dotnet/core #8288
É importante testar um aplicativo completamente ao mudar para um modelo de implantação AOT nativo. O aplicativo compilado pela AOT deve ser testado para garantir que a funcionalidade não sofreu alterações em relação ao aplicativo sem otimização e compilado em JIT. Ao criar o aplicativo, revise e corrija os avisos da AOT. Uma aplicação que emite avisos de AOT durante a publicação pode não funcionar corretamente. Se não forem emitidos avisos de AOT no momento da publicação, a aplicação AOT publicada deverá funcionar da mesma forma que a aplicação não otimizada e compilada em JIT.
Publicação AOT nativa
O Native AOT é habilitado com a propriedade PublishAot MSBuild. O exemplo a seguir mostra como habilitar o AOT nativo em um arquivo de projeto:
<PropertyGroup>
<PublishAot>true</PublishAot>
</PropertyGroup>
Essa configuração permite a compilação AOT nativa durante a publicação e permite a análise dinâmica do uso de código durante a compilação e edição. Um projeto que usa a publicação AOT nativa usa a compilação JIT quando executado localmente. Um aplicativo AOT tem as seguintes diferenças de um aplicativo compilado por JIT:
- Os recursos que não são compatíveis com o AOT nativo são desativados e lançam exceções em tempo de execução.
- Um analisador de código-fonte está habilitado para destacar o código que não é compatível com o AOT nativo. No momento da publicação, todo o aplicativo, incluindo os pacotes NuGet, é analisado quanto à compatibilidade novamente.
A análise AOT nativa inclui todo o código do aplicativo e as bibliotecas das quais o aplicativo depende. Revise os avisos de AOT nativos e tome medidas corretivas. É uma boa ideia publicar aplicativos com frequência para descobrir problemas no início do ciclo de vida do desenvolvimento.
No .NET 8, a AOT nativa é suportada pelos seguintes tipos de aplicativo ASP.NET Core:
- APIs mínimas - Para mais informações, consulte a secção do template "The Web API (Native AOT)" mais adiante neste artigo.
- gRPC - Para mais informações, consulte gRPC e AOT Nativo.
- Serviços de trabalhador - Para obter mais informações, consulte AOT em Modelos de serviço de trabalhador.
O modelo de API da Web (AOT nativa)
O modelo ASP.NET Core Web API (Native AOT) (nome abreviado webapiaot) cria um projeto com AOT ativado. O modelo difere da API Web modelo de projeto das seguintes maneiras:
- Usa apenas APIs mínimas, pois o MVC ainda não é compatível com o AOT nativo.
- Usa a API CreateSlimBuilder() para garantir que apenas os recursos essenciais sejam habilitados por padrão, minimizando o tamanho implantado do aplicativo.
- Está configurado para escutar somente em HTTP, pois o tráfego HTTPS é normalmente tratado por um serviço de entrada em implantações nativas da nuvem.
- Não inclui um perfil de inicialização para execução no IIS ou IIS Express.
- Cria um ficheiro
.httpconfigurado com solicitações HTTP de exemplo que podem ser enviadas para os endpoints da aplicação. - Inclui uma amostra
TodoAPI em vez da amostra de previsão do tempo. - Adiciona
PublishAotao arquivo de projeto, conforme mostrado anteriormente neste artigo. - Habilita os geradores de código-fonte do serializador JSON . O gerador de código-fonte é usado para gerar código de serialização em tempo de compilação, o que é necessário para a compilação AOT nativa.
Alterações para dar suporte à geração de código-fonte
O exemplo a seguir mostra o código adicionado ao arquivo Program.cs para dar suporte à geração de origem de serialização 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
+{
+
+}
Sem esse código adicionado, System.Text.Json usa reflexão para serializar e desserializar JSON. A reflexão não é suportada em Native AOT.
Para mais informações, consulte:
Alterações ao launchSettings.json
O arquivo
{
"$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"
- }
- }
}
}
O método CreateSlimBuilder
O modelo usa o método CreateSlimBuilder() em vez do método CreateBuilder().
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
{
}
O método CreateSlimBuilder inicializa o WebApplicationBuilder com o mínimo de recursos ASP.NET Core necessários para executar um aplicativo.
Como observado anteriormente, o método CreateSlimBuilder não inclui suporte para HTTPS ou HTTP/3. Esses protocolos normalmente não são necessários para aplicativos executados atrás de um proxy de terminação TLS. Por exemplo, consulte terminação de TLS e TLS fim a fim com o Application Gateway. O HTTPS pode ser ativado ao invocar construtor.WebHost.UseKestrelHttpsConfiguration. O HTTP/3 pode ser ativado ao invocar construtor.WebHost.UseQuic.
CreateSlimBuilder vs CreateBuilder
O método CreateSlimBuilder não suporta os seguintes recursos que são suportados pelo método CreateBuilder:
- Hospedagem de assemblies de inicialização
- UseStartup
- Os seguintes provedores de log:
- Recursos de hospedagem na Web:
- Kestrel configuração
- restrições Regex e alfa usadas no roteamento
O método CreateSlimBuilder inclui os seguintes recursos necessários para uma experiência de desenvolvimento eficiente:
- Configuração do arquivo JSON para
appsettings.jsoneappsettings.{EnvironmentName}.json. - Configuração de segredos do usuário.
- Registo de consola.
- Configuração de registo.
Para um construtor que omite as funcionalidades anteriores, consulte o método CreateEmptyBuilder.
A inclusão de características mínimas tem benefícios para a otimização, assim como para o AOT. Para obter mais informações, consulte Reduzir implantações independentes e executáveis.
Para obter informações mais detalhadas, consulte Comparando WebApplication.CreateBuilder com CreateSlimBuilder
Geradores de origem
Como o código não utilizado é cortado durante a publicação para AOT nativo, o aplicativo não pode usar reflexão ilimitada em tempo de execução. Geradores de código-fonte são usados para produzir código que evita a necessidade de reflexão. Em alguns casos, os geradores de código-fonte produzem código otimizado para AOT, mesmo quando um gerador não é necessário.
Para exibir o código-fonte gerado, adicione a propriedade EmitCompilerGeneratedFiles ao arquivo .csproj de um aplicativo, conforme mostrado no exemplo a seguir:
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<!-- Other properties omitted for brevity -->
<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
</PropertyGroup>
</Project>
Execute o comando dotnet build para ver o código gerado. A saída inclui um diretório obj/Debug/net8.0/generated/ que contém todos os arquivos gerados para o projeto.
O comando dotnet publish também compila os arquivos de origem e gera arquivos que são compilados. Além disso, dotnet publish passa os assemblies gerados para um compilador IL nativo. O compilador IL produz o executável nativo. O executável nativo contém o código da máquina nativa.
Bibliotecas e AOT nativo
Muitas das bibliotecas populares usadas em projetos ASP.NET Core atualmente têm alguns problemas de compatibilidade quando usadas em um projeto direcionado à AOT nativa, como:
- Uso da reflexão para inspecionar e descobrir tipos.
- Carregamento condicional de bibliotecas em tempo de execução.
- Geração de código em tempo real para implementar funcionalidades.
As bibliotecas que usam esses recursos dinâmicos precisam ser atualizadas para trabalhar com AOT nativo. Eles podem ser atualizados usando ferramentas como geradores de fontes Roslyn.
Os autores de bibliotecas que desejam apoiar o Native AOT são encorajados a:
- Leia sobre os requisitos de compatibilidade de AOT nativo .
- Preparar a biblioteca para cortar.
APIs mínimas e cargas úteis JSON
A API Mínima é otimizada para receber e retornar dados JSON usando System.Text.Json.
System.Text.Json:
- Impõe requisitos de compatibilidade para JSON e AOT nativo.
- Requer o uso do gerador de fonte
System.Text.Json.
Todos os tipos transmitidos como parte do corpo HTTP ou retornados de delegados de solicitação em aplicativos de APIs mínimas devem ser configurados em um JsonSerializerContext registrado por meio da injeção de dependência do 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
{
}
No código destacado anterior:
- O contexto do serializador JSON é registado com o container DI. Para mais informações, consulte:
- O
JsonSerializerContextpersonalizado é anotado com o atributo[JsonSerializable]para habilitar o código serializador JSON gerado pela fonte para o tipoToDo.
Um parâmetro no delegado que não está vinculado ao corpo e não precisa ser serializável. Por exemplo, um parâmetro de cadeia de caracteres de consulta que é um tipo de objeto avançado e implementa IParsable<T>.
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.
Problemas conhecidos
Consulte este problema do GitHub para relatar ou revisar problemas com o suporte nativo de AOT no ASP.NET Core.
Ver também
- Tutorial: Publicar um aplicativo ASP.NET Core usando o AOT nativo
- Implantação de AOT nativo
- Otimizar implantações de AOT
- Gerador de código-fonte de ligação de configuração
- pt-PT: Usando o gerador de código-fonte do vinculador de configuração
- O modelo de compilação AOT da API Minimal
-
Comparando
WebApplication.CreateBuildercomCreateSlimBuilder - Explorando o novo gerador de código de API Minimal
- Substituindo chamadas de método por Intercetores
-
[LogProperties]
O .NET 8 introduz suporte para AOT (ahead-of-time) nativo do .NET.
Por que usar AOT nativo com ASP.NET Core
Publicar e implantar um aplicativo AOT nativo oferece os seguintes benefícios:
-
Minimized disk footprint: Ao publicar usando AOT nativo, é produzido um único executável que contém apenas o código das dependências externas necessário para suportar o programa. O tamanho reduzido do executável pode levar a:
- Imagens de contentor mais pequenas, por exemplo, em cenários de implantação em contentores.
- Tempo de implantação reduzido a partir de imagens menores.
-
Tempo de inicialização reduzido: Os aplicativos AOT nativos podem mostrar tempos de inicialização reduzidos, o que significa
- O aplicativo está pronto para atender solicitações mais rapidamente.
- Implantação aprimorada em que os orquestradores de contêineres precisam gerenciar a transição de uma versão do aplicativo para outra.
- Demanda de memória reduzida: Os aplicativos AOT nativos podem ter demandas de memória reduzidas, dependendo do trabalho feito pelo aplicativo. O consumo reduzido de memória pode levar a uma maior densidade de implantação e melhor escalabilidade.
O aplicativo de modelo foi executado em nosso laboratório de benchmarking para comparar o desempenho de um aplicativo publicado pela AOT, um aplicativo de tempo de execução cortado e um aplicativo de tempo de execução não cortado. O gráfico a seguir mostra os resultados do benchmarking:
O gráfico anterior mostra que a AOT nativa tem menor tamanho de aplicativo, uso de memória e tempo de inicialização.
Compatibilidade do ASP.NET Core com AOT nativo
Nem todos os recursos do ASP.NET Core são atualmente compatíveis com a AOT nativa. A tabela a seguir resume a compatibilidade de recursos do ASP.NET Core com o AOT Nativo:
| Funcionalidade | Totalmente suportado | Parcialmente suportado | Não suportado |
|---|---|---|---|
| gRPC | ✔️ Totalmente suportado | ||
| APIs mínimas | ✔️ Parcialmente suportado | ||
| MVC | Não suportado | ||
| Blazor Server | Não suportado | ||
| SignalR | Não suportado | ||
| Autenticação JWT | ✔️ Totalmente suportado | ||
| Outra autenticação | Não suportado | ||
| CORS | ✔️ Totalmente suportado | ||
| Verificações de saúde | ✔️ Totalmente suportado | ||
| Registo HTTP | ✔️ Totalmente suportado | ||
| Localização | ✔️ Totalmente suportado | ||
| OutputCaching | ✔️ Totalmente suportado | ||
| Limitação de Taxa | ✔️ Totalmente suportado | ||
| PedidoDescompressão | ✔️ Totalmente suportado | ||
| Cache de Respostas | ✔️ Totalmente suportado | ||
| CompressãoDeResposta | ✔️ Totalmente suportado | ||
| Reescrever | ✔️ Totalmente suportado | ||
| Sessão | Não suportado | ||
| Termas | Não suportado | ||
| Arquivos Estáticos | ✔️ Totalmente suportado | ||
| WebSockets | ✔️ Totalmente suportado |
Para obter mais informações sobre limitações, consulte:
- Limitações da implantação de AOT nativo
- Introdução aos avisos AOT
- Incompatibilidades de corte conhecidas
- Introdução aos alertas de corte
- Problema do GitHub dotnet/core #8288
É importante testar um aplicativo completamente ao mudar para um modelo de implantação AOT nativo. O aplicativo compilado pela AOT deve ser testado para garantir que a funcionalidade não sofreu alterações em relação ao aplicativo sem otimização e compilado em JIT. Ao criar o aplicativo, revise e corrija os avisos da AOT. Uma aplicação que emite avisos de AOT durante a publicação pode não funcionar corretamente. Se não forem emitidos avisos de AOT no momento da publicação, a aplicação AOT publicada deverá funcionar da mesma forma que a aplicação não otimizada e compilada em JIT.
Publicação AOT nativa
O Native AOT é habilitado com a propriedade PublishAot MSBuild. O exemplo a seguir mostra como habilitar o AOT nativo em um arquivo de projeto:
<PropertyGroup>
<PublishAot>true</PublishAot>
</PropertyGroup>
Essa configuração permite a compilação AOT nativa durante a publicação e permite a análise dinâmica do uso de código durante a compilação e edição. Um projeto que usa a publicação AOT nativa usa a compilação JIT quando executado localmente. Um aplicativo AOT tem as seguintes diferenças de um aplicativo compilado por JIT:
- Os recursos que não são compatíveis com o AOT nativo são desativados e lançam exceções em tempo de execução.
- Um analisador de código-fonte está habilitado para destacar o código que não é compatível com o AOT nativo. No momento da publicação, todo o aplicativo, incluindo os pacotes NuGet, é analisado quanto à compatibilidade novamente.
A análise AOT nativa inclui todo o código do aplicativo e as bibliotecas das quais o aplicativo depende. Revise os avisos de AOT nativos e tome medidas corretivas. É uma boa ideia publicar aplicativos com frequência para descobrir problemas no início do ciclo de vida do desenvolvimento.
No .NET 8, a AOT nativa é suportada pelos seguintes tipos de aplicativo ASP.NET Core:
- APIs mínimas - Para mais informações, consulte a secção "Modelo de Web API (Native AOT)" mais adiante neste artigo.
- gRPC - Para mais informações, consulte gRPC e AOT Nativo.
- Serviços de trabalhador - Para obter mais informações, consulte AOT em Modelos de serviço de trabalhador.
O modelo de API da Web (AOT nativa)
O modelo ASP.NET Core Web API (Native AOT) (nome abreviado webapiaot) cria um projeto com AOT ativado. O modelo difere da API Web modelo de projeto das seguintes maneiras:
- Usa apenas APIs mínimas, pois o MVC ainda não é compatível com o AOT nativo.
- Usa a API CreateSlimBuilder() para garantir que apenas os recursos essenciais sejam habilitados por padrão, minimizando o tamanho implantado do aplicativo.
- Está configurado para escutar somente em HTTP, pois o tráfego HTTPS é normalmente tratado por um serviço de entrada em implantações nativas da nuvem.
- Não inclui um perfil de inicialização para execução no IIS ou IIS Express.
- Cria um ficheiro
.httpconfigurado com solicitações HTTP de exemplo que podem ser enviadas para os endpoints da aplicação. - Inclui uma amostra
TodoAPI em vez da amostra de previsão do tempo. - Adiciona
PublishAotao arquivo de projeto, conforme mostrado anteriormente neste artigo. - Habilita os geradores de código-fonte do serializador JSON . O gerador de código-fonte é usado para gerar código de serialização em tempo de compilação, o que é necessário para a compilação AOT nativa.
Alterações para dar suporte à geração de código-fonte
O exemplo a seguir mostra o código adicionado ao arquivo Program.cs para dar suporte à geração de origem de serialização 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
+{
+
+}
Sem esse código adicionado, System.Text.Json usa reflexão para serializar e desserializar JSON. A reflexão não é suportada em Native AOT.
Para mais informações, consulte:
Alterações ao launchSettings.json
O arquivo
{
"$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"
- }
- }
}
}
O método CreateSlimBuilder
O modelo usa o método CreateSlimBuilder() em vez do método CreateBuilder().
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
{
}
O método CreateSlimBuilder inicializa o WebApplicationBuilder com o mínimo de recursos ASP.NET Core necessários para executar um aplicativo.
Como observado anteriormente, o método CreateSlimBuilder não inclui suporte para HTTPS ou HTTP/3. Esses protocolos normalmente não são necessários para aplicativos executados atrás de um proxy de terminação TLS. Por exemplo, consulte terminação de TLS e TLS fim a fim com o Application Gateway. O HTTPS pode ser ativado ao invocar construtor.WebHost.UseKestrelHttpsConfiguration. O HTTP/3 pode ser ativado ao invocar construtor.WebHost.UseQuic.
CreateSlimBuilder vs CreateBuilder
O método CreateSlimBuilder não suporta os seguintes recursos que são suportados pelo método CreateBuilder:
- Hospedagem de assemblies de inicialização
- UseStartup
- Os seguintes provedores de log:
- Recursos de hospedagem na Web:
- Kestrel configuração
- restrições Regex e alfa usadas no roteamento
O método CreateSlimBuilder inclui os seguintes recursos necessários para uma experiência de desenvolvimento eficiente:
- Configuração do arquivo JSON para
appsettings.jsoneappsettings.{EnvironmentName}.json. - Configuração de segredos do usuário.
- Registo de consola.
- Configuração de registo.
Para um construtor que omite as funcionalidades anteriores, consulte o método CreateEmptyBuilder.
A inclusão de características mínimas tem benefícios para a otimização, assim como para o AOT. Para obter mais informações, consulte Reduzir implantações independentes e executáveis.
Para obter informações mais detalhadas, consulte Comparando WebApplication.CreateBuilder com CreateSlimBuilder
Geradores de origem
Como o código não utilizado é cortado durante a publicação para AOT nativo, o aplicativo não pode usar reflexão ilimitada em tempo de execução. Geradores de código-fonte são usados para produzir código que evita a necessidade de reflexão. Em alguns casos, os geradores de código-fonte produzem código otimizado para AOT, mesmo quando um gerador não é necessário.
Para exibir o código-fonte gerado, adicione a propriedade EmitCompilerGeneratedFiles ao arquivo .csproj de um aplicativo, conforme mostrado no exemplo a seguir:
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<!-- Other properties omitted for brevity -->
<EmitCompilerGeneratedFiles>true</EmitCompilerGeneratedFiles>
</PropertyGroup>
</Project>
Execute o comando dotnet build para ver o código gerado. A saída inclui um diretório obj/Debug/net8.0/generated/ que contém todos os arquivos gerados para o projeto.
O comando dotnet publish também compila os arquivos de origem e gera arquivos que são compilados. Além disso, dotnet publish passa os assemblies gerados para um compilador IL nativo. O compilador IL produz o executável nativo. O executável nativo contém o código da máquina nativa.
Bibliotecas e AOT nativo
Muitas das bibliotecas populares usadas em projetos ASP.NET Core atualmente têm alguns problemas de compatibilidade quando usadas em um projeto direcionado à AOT nativa, como:
- Uso da reflexão para inspecionar e descobrir tipos.
- Carregamento condicional de bibliotecas em tempo de execução.
- Geração de código em tempo real para implementar funcionalidades.
As bibliotecas que usam esses recursos dinâmicos precisam ser atualizadas para trabalhar com AOT nativo. Eles podem ser atualizados usando ferramentas como geradores de fontes Roslyn.
Os autores de bibliotecas que desejam apoiar o Native AOT são encorajados a:
- Leia sobre os requisitos de compatibilidade de AOT nativo .
- Preparar a biblioteca para cortar.
APIs mínimas e cargas úteis JSON
A API Mínima é otimizada para receber e retornar dados JSON usando System.Text.Json.
System.Text.Json:
- Impõe requisitos de compatibilidade para JSON e AOT nativo.
- Requer o uso do gerador de fonte
System.Text.Json.
Todos os tipos transmitidos como parte do corpo HTTP ou retornados de delegados de solicitação em aplicativos de APIs mínimas devem ser configurados em um JsonSerializerContext registrado por meio da injeção de dependência do 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
{
}
No código destacado anterior:
- O contexto do serializador JSON é registado com o container DI. Para mais informações, consulte:
- O
JsonSerializerContextpersonalizado é anotado com o atributo[JsonSerializable]para habilitar o código serializador JSON gerado pela fonte para o tipoToDo.
Um parâmetro no delegado que não está vinculado ao corpo e não precisa ser serializável. Por exemplo, um parâmetro de cadeia de caracteres de consulta que é um tipo de objeto avançado e implementa IParsable<T>.
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.
Problemas conhecidos
Consulte este problema do GitHub para relatar ou revisar problemas com o suporte nativo de AOT no ASP.NET Core.
Ver também
- Tutorial: Publicar um aplicativo ASP.NET Core usando o AOT nativo
- Implantação de AOT nativo
- Otimizar implantações de AOT
- Gerador de código-fonte de ligação de configuração
- pt-PT: Usando o gerador de código-fonte do vinculador de configuração
- O modelo de compilação AOT da API Minimal
-
Comparando
WebApplication.CreateBuildercomCreateSlimBuilder - Explorando o novo gerador de código de API Minimal
- Substituindo chamadas de método por Intercetores
-
[LogProperties]