This browser is no longer supported.
Upgrade to Microsoft Edge to take advantage of the latest features, security updates, and technical support.
Note
Access to this page requires authorization. You can trysigning in orchanging directories.
Access to this page requires authorization. You can trychanging directories.
Note
This isn't the latest version of this article. For the current release, see the.NET 10 version of this article.
Warning
This version of ASP.NET Core is no longer supported. For more information, see the.NET and .NET Core Support Policy. For the current release, see the.NET 9 version of this article.
This article provides an overview of the fundamentals for building ASP.NET Core apps, including dependency injection (DI), configuration, middleware, and more.
For Blazor fundamentals guidance, which adds to or supersedes the guidance in this article, seeASP.NET Core Blazor fundamentals.
ASP.NET Core apps created with the web templates contain the application startup code in theProgram.cs file. TheProgram.cs file is where:
The following app startup code supports several app types:
using WebAll.Components;var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorComponents() .AddInteractiveServerComponents();builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.MapRazorComponents<App>() .AddInteractiveServerRenderMode();app.UseAntiforgery();app.Run();ASP.NET Core features built-independency injection (DI) that makes configured services available throughout an app. Services are added to the DI container withWebApplicationBuilder.Services,builder.Services in the preceding code. When theWebApplicationBuilder is instantiated, manyframework-provided services are added automatically.builder is aWebApplicationBuilder in the following code:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();In the preceding code,CreateBuilder adds configuration, logging, andmany other services to the DI container. The DI framework provides an instance of a requested service at run time.
The following code adds a customDbContext and Blazor components to the DI container:
var builder = WebApplication.CreateBuilder(args);builder.Services.AddDbContextFactory<BlazorWebAppMoviesContext>(options => options.UseSqlServer(builder.Configuration.GetConnectionString("MoviesContext") ?? throw new InvalidOperationException("Connection string not found.")));builder.Services.AddQuickGridEntityFrameworkAdapter();builder.Services.AddDatabaseDeveloperPageExceptionFilter();// Add services to the container.builder.Services.AddRazorComponents() .AddInteractiveServerComponents();var app = builder.Build();In Blazor Web Apps, services are often resolved from DI at run time by using the@inject directive in a Razor component, as shown in the following example:
@page "/movies"@rendermode InteractiveServer@using Microsoft.EntityFrameworkCore@using Microsoft.AspNetCore.Components.QuickGrid@using BlazorWebAppMovies.Models@using BlazorWebAppMovies.Data@implements IAsyncDisposable@inject IDbContextFactory<BlazorWebAppMovies.Data.BlazorWebAppMoviesContext> DbFactory<PageTitle>Index</PageTitle><h1>Index</h1><div> <input type="search" @bind="titleFilter" @bind:event="oninput" /></div><p> <a href="movies/create">Create New</a></p><QuickGrid Items="FilteredMovies" Pagination="pagination"> <PropertyColumn Property="movie => movie.Title" Sortable="true" /> <PropertyColumn Property="movie => movie.ReleaseDate" Title="Release Date" /> <PropertyColumn Property="movie => movie.Genre" /> <PropertyColumn Property="movie => movie.Price" /> <PropertyColumn Property="movie => movie.Rating" /> <TemplateColumn Context="movie"> <a href="@($"movies/edit?id={movie.Id}")">Edit</a> | <a href="@($"movies/details?id={movie.Id}")">Details</a> | <a href="@($"movies/delete?id={movie.Id}")">Delete</a> </TemplateColumn></QuickGrid><Paginator State="pagination" />@code { private BlazorWebAppMoviesContext context = default!; private PaginationState pagination = new PaginationState { ItemsPerPage = 10 }; private string titleFilter = string.Empty; private IQueryable<Movie> FilteredMovies => context.Movie.Where(m => m.Title!.Contains(titleFilter)); protected override void OnInitialized() { context = DbFactory.CreateDbContext(); } public async ValueTask DisposeAsync() => await context.DisposeAsync();}In the preceding code:
@inject directive is used.OnInitialized method and assigned to thecontext variable.context service creates theFilteredMovie list.Another way to resolve a service from DI is by using constructor injection. The following Razor Pages code uses constructor injection to resolve the database context and a logger from DI:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; private readonly ILogger<IndexModel> _logger; public IndexModel(RazorPagesMovieContext context, ILogger<IndexModel> logger) { _context = context; _logger = logger; } public IList<Movie> Movie { get;set; } public async Task OnGetAsync() { _logger.LogInformation("IndexModel OnGetAsync."); Movie = await _context.Movie.ToListAsync(); }}In the preceding code, theIndexModel constructor takes a parameter of typeRazorPagesMovieContext, which is resolved at run time into the_context variable. The context object is used to create a list of movies in theOnGetAsync method.
For more information, seeASP.NET Core Blazor dependency injection andDependency injection in ASP.NET Core.
The request handling pipeline is composed as a series of middleware components. Each component performs operations on anHttpContext and either invokes the next middleware in the pipeline or terminates the request.
By convention, a middleware component is added to the pipeline by invoking aUse{Feature} extension method. The use of methods namedUse{Feature} to add middleware to an app is illustrated in the following code:
var builder = WebApplication.CreateBuilder(args);builder.Services.AddDbContextFactory<BlazorWebAppMoviesContext>(options => options.UseSqlServer(builder.Configuration.GetConnectionString("MoviesContext") ?? throw new InvalidOperationException("Connection string not found.")));builder.Services.AddQuickGridEntityFrameworkAdapter();builder.Services.AddDatabaseDeveloperPageExceptionFilter();// Add services to the container.builder.Services.AddRazorComponents() .AddInteractiveServerComponents();var app = builder.Build();using (var scope = app.Services.CreateScope()){ var services = scope.ServiceProvider; SeedData.Initialize(services);}// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error", createScopeForErrors: true); app.UseHsts(); app.UseMigrationsEndPoint();}app.UseHttpsRedirection();app.UseAntiforgery();app.MapStaticAssets();app.MapRazorComponents<App>() .AddInteractiveServerRenderMode();app.Run();For more information, seeASP.NET Core Middleware.
On startup, an ASP.NET Core app builds ahost. The host encapsulates all of the app's resources, such as:
There are three different hosts capable of running an ASP.NET Core app:
The ASP.NET CoreWebApplication andWebApplicationBuilder types are recommended and are used in all the ASP.NET Core templates.WebApplication behaves similarly to the .NET Generic Host and exposes many of the same interfaces but requires fewer callbacks to configure. The ASP.NET CoreWebHost is available only for backward compatibility.
The following example instantiates aWebApplication and assigns it to a variable namedapp:
var builder = WebApplication.CreateBuilder(args);builder.Services.AddDbContextFactory<BlazorWebAppMoviesContext>(options => options.UseSqlServer(builder.Configuration.GetConnectionString("MoviesContext") ?? throw new InvalidOperationException("Connection string not found.")));builder.Services.AddQuickGridEntityFrameworkAdapter();builder.Services.AddDatabaseDeveloperPageExceptionFilter();// Add services to the container.builder.Services.AddRazorComponents() .AddInteractiveServerComponents();var app = builder.Build();TheWebApplicationBuilder.Build method configures a host with a set of default options, such as:
appsettings.json, environment variables, command line arguments, and other configuration sources.The Generic Host enables other types of apps to use cross-cutting framework extensions, such as logging, dependency injection (DI), configuration, and app lifetime management. For more information, see.NET Generic Host in ASP.NET Core andBackground tasks with hosted services in ASP.NET Core.
An ASP.NET Core app uses an HTTP server implementation to listen for HTTP requests. The server surfaces requests to the app as a set ofrequest features composed into anHttpContext.
ASP.NET Core provides the following server implementations:
For more information, seeWeb server implementations in ASP.NET Core.
ASP.NET Core provides aconfiguration framework that gets settings as name-value pairs from an ordered set of configuration providers. Built-in configuration providers are available for a variety of sources, such as.json files,.xml files, environment variables, and command-line arguments. Write custom configuration providers to support other sources.
Bydefault, ASP.NET Core apps are configured to read fromappsettings.json, environment variables, the command line, and more. When the app's configuration is loaded, values from environment variables override values fromappsettings.json.
For managing confidential configuration data such as passwords in the development environment, .NET provides theSecret Manager. For production secrets, we recommendAzure Key Vault.
For more information, seeConfiguration in ASP.NET Core.
Execution environments, such asDevelopment,Staging, andProduction, are available in ASP.NET Core. Specify the environment an app is running in by setting theASPNETCORE_ENVIRONMENT environment variable. ASP.NET Core reads that environment variable at app startup and stores the value in anIWebHostEnvironment implementation. This implementation is available anywhere in an app via dependency injection (DI).
The following example configures the exception handler andHTTP Strict Transport Security Protocol (HSTS) middleware whennot running in theDevelopment environment:
if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error", createScopeForErrors: true); app.UseHsts(); app.UseMigrationsEndPoint();}For more information, seeASP.NET Core runtime environments.
ASP.NET Core supports a logging API that works with a variety of built-in and third-party logging providers. Available providers include:
To create logs, resolve anILogger<TCategoryName> service from dependency injection (DI) and call logging methods such asLogInformation. The following example shows how to get and use a logger in a.razor file for a page in a Blazor Web App. A logger object and a console provider for it are stored in the DI container automatically when theCreateBuilder method is called inProgram.cs.
@page "/weather"@attribute [StreamRendering]@inject ILogger<Weather> Logger<PageTitle>Weather</PageTitle><h1>Weather</h1><p>This component demonstrates showing data and logging.</p>@if (forecasts == null){ <p><em>Loading...</em></p>}else{ <table> <thead> <tr> <th>Date</th> <th aria-label="Temperature in Celsius">Temp. (C)</th> <th aria-label="Temperature in Fahrenheit">Temp. (F)</th> <th>Summary</th> </tr> </thead> <tbody> @foreach (var forecast in forecasts) { <tr> <td>@forecast.Date.ToShortDateString()</td> <td>@forecast.TemperatureC</td> <td>@forecast.TemperatureF</td> <td>@forecast.Summary</td> </tr> } </tbody> </table>}@code { private WeatherForecast[]? forecasts; protected override async Task OnInitializedAsync() { // Simulate asynchronous loading to demonstrate streaming rendering await Task.Delay(500); Logger.LogInformation("This is an information log message."); Logger.LogWarning("This is a warning log message."); Logger.LogError("This is an error log message."); var startDate = DateOnly.FromDateTime(DateTime.Now); var summaries = new[] { "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching" }; forecasts = Enumerable.Range(1, 5).Select(index => new WeatherForecast { Date = startDate.AddDays(index), TemperatureC = Random.Shared.Next(-20, 55), Summary = summaries[Random.Shared.Next(summaries.Length)] }).ToArray(); } private class WeatherForecast { public DateOnly Date { get; set; } public int TemperatureC { get; set; } public string? Summary { get; set; } public int TemperatureF => 32 + (int)(TemperatureC / 0.5556); }}For more information, seeLogging in .NET and ASP.NET Core.
Routing in ASP.NET Core is a mechanism that maps incoming requests to specific endpoints in an application. It enables you to define URL patterns that correspond to different components, such as Blazor components, Razor pages, MVC controller actions, or middleware.
TheUseRouting(IApplicationBuilder) method adds routing middleware to the request pipeline. This middleware processes the routing information and determines the appropriate endpoint for each request. You don't have to explicitly callUseRouting unless you want to change the order in which middleware is processed.
For more information, seeRouting in ASP.NET Core andASP.NET Core Blazor routing and navigation.
ASP.NET Core has built-in features for handling errors, such as:
For more information, seeHandle errors in ASP.NET Core.
An implementation ofIHttpClientFactory is available for creatingHttpClient instances. The factory:
HttpClient instances. For example, register and configure agithub client for accessing GitHub. Register and configure a default client for other purposes.HttpClient lifetimes manually.For more information, seeMake HTTP requests using IHttpClientFactory in ASP.NET Core.
The content root is the base path for:
.cshtml,.razor).json,.xml).db)wwwroot folder.During development, the content root defaults to the project's root directory. This directory is also the base path for both the app's content files and theweb root. Specify a different content root by setting its path whenbuilding the host. For more information, seeContent root.
The web root is the base path for public, static resource files, such as:
.css).js).png,.jpg)By default, static files are served only from the web root directory and its sub-directories. The web root path defaults to{CONTENT ROOT}/wwwroot, where the{CONTENT ROOT} placeholder is the content root. Specify a different web root by setting its path whenbuilding the host. For more information, seeWeb root.
Prevent publishing files inwwwroot with the<Content> project item in the project file. The following example prevents publishing content inwwwroot/local and its sub-directories:
<ItemGroup> <Content Update="wwwroot\local\**\*.*" CopyToPublishDirectory="Never" /></ItemGroup>In Razor.cshtml files,~/ points to the web root. A path beginning with~/ is referred to as avirtual path.
For more information, seeStatic files in ASP.NET Core.
Many of the articles and tutorials include links to sample code.
AspNetCore.Docs-main.zip file.To demonstrate multiple scenarios, sample apps use the#define and#if-#else/#elif-#endif preprocessor directives to selectively compile and run different sections of sample code. For those samples that make use of this approach, set the#define directive at the top of the C# files to define the symbol associated with the scenario that you want to run. Some samples require defining the symbol at the top of multiple files in order to run a scenario.
For example, the following#define symbol list indicates that four scenarios are available (one scenario per symbol). The current sample configuration runs theTemplateCode scenario:
#define TemplateCode // or LogFromMain or ExpandDefault or FilterInCodeTo change the sample to run theExpandDefault scenario, define theExpandDefault symbol and leave the remaining symbols commented-out:
#define ExpandDefault // TemplateCode or LogFromMain or FilterInCodeFor more information on usingC# preprocessor directives to selectively compile sections of code, see#define (C# Reference) and#if (C# Reference).
Some sample apps contain sections of code surrounded by#region and#endregion C# directives. The documentation build system injects these regions into the rendered documentation topics.
Region names usually contain the word "snippet." The following example shows a region namedsnippet_WebHostDefaults:
#region snippet_WebHostDefaultsHost.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>(); });#endregionThe preceding C# code snippet is referenced in the topic's markdown file with the following line:
[!code-csharp[](sample/SampleApp/Program.cs?name=snippet_WebHostDefaults)]You may safely ignore or remove the#region and#endregion directives that surround the code. Don't alter the code within these directives if you plan to run the sample scenarios described in the topic.
For more information, seeContribute to the ASP.NET documentation: Code snippets.
This article provides an overview of the fundamentals for building ASP.NET Core apps, including dependency injection (DI), configuration, middleware, and more.
ASP.NET Core apps created with the web templates contain the application startup code in theProgram.cs file. TheProgram.cs file is where:
The following app startup code supports:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();ASP.NET Core includesdependency injection (DI) that makes configured services available throughout an app. Services are added to the DI container withWebApplicationBuilder.Services,builder.Services in the preceding code. When theWebApplicationBuilder is instantiated, manyframework-provided services are added.builder is aWebApplicationBuilder in the following code:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();In the preceding highlighted code,builder has configuration, logging, andmany other services added to the DI container.
The following code adds Razor Pages, MVC controllers with views, and a customDbContext to the DI container:
using Microsoft.EntityFrameworkCore;using RazorPagesMovie.Data;var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();builder.Services.AddDbContext<RazorPagesMovieContext>(options => options.UseSqlServer(builder.Configuration.GetConnectionString("RPMovieContext")));var app = builder.Build();Services are typically resolved from DI using constructor injection. The DI framework provides an instance of this service at runtime.
The following code uses constructor injection to resolve the database context and logger from DI:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; private readonly ILogger<IndexModel> _logger; public IndexModel(RazorPagesMovieContext context, ILogger<IndexModel> logger) { _context = context; _logger = logger; } public IList<Movie> Movie { get;set; } public async Task OnGetAsync() { _logger.LogInformation("IndexModel OnGetAsync."); Movie = await _context.Movie.ToListAsync(); }}The request handling pipeline is composed as a series of middleware components. Each component performs operations on anHttpContext and either invokes the next middleware in the pipeline or terminates the request.
By convention, a middleware component is added to the pipeline by invoking aUse{Feature} extension method. Middleware added to the app is highlighted in the following code:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();For more information, seeASP.NET Core Middleware.
On startup, an ASP.NET Core app builds ahost. The host encapsulates all of the app's resources, such as:
There are three different hosts capable of running an ASP.NET Core app:
The ASP.NET CoreWebApplication andWebApplicationBuilder types are recommended and used in all the ASP.NET Core templates.WebApplication behaves similarly to the .NET Generic Host and exposes many of the same interfaces but requires less callbacks to configure. The ASP.NET CoreWebHost is available only for backward compatibility.
The following example instantiates aWebApplication:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();TheWebApplicationBuilder.Build method configures a host with a set of default options, such as:
appsettings.json, environment variables, command line arguments, and other configuration sources.The Generic Host allows other types of apps to use cross-cutting framework extensions, such as logging, dependency injection (DI), configuration, and app lifetime management. For more information, see.NET Generic Host in ASP.NET Core andBackground tasks with hosted services in ASP.NET Core.
An ASP.NET Core app uses an HTTP server implementation to listen for HTTP requests. The server surfaces requests to the app as a set ofrequest features composed into anHttpContext.
ASP.NET Core provides the following server implementations:
For more information, seeWeb server implementations in ASP.NET Core.
ASP.NET Core provides aconfiguration framework that gets settings as name-value pairs from an ordered set of configuration providers. Built-in configuration providers are available for a variety of sources, such as.json files,.xml files, environment variables, and command-line arguments. Write custom configuration providers to support other sources.
Bydefault, ASP.NET Core apps are configured to read fromappsettings.json, environment variables, the command line, and more. When the app's configuration is loaded, values from environment variables override values fromappsettings.json.
For managing confidential configuration data such as passwords, .NET provides theSecret Manager. For production secrets, we recommendAzure Key Vault.
For more information, seeConfiguration in ASP.NET Core.
Execution environments, such asDevelopment,Staging, andProduction, are available in ASP.NET Core. Specify the environment an app is running in by setting theASPNETCORE_ENVIRONMENT environment variable. ASP.NET Core reads that environment variable at app startup and stores the value in anIWebHostEnvironment implementation. This implementation is available anywhere in an app via dependency injection (DI).
The following example configures the exception handler andHTTP Strict Transport Security Protocol (HSTS) middleware whennot running in theDevelopment environment:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();For more information, seeASP.NET Core runtime environments.
ASP.NET Core supports a logging API that works with a variety of built-in and third-party logging providers. Available providers include:
To create logs, resolve anILogger<TCategoryName> service from dependency injection (DI) and call logging methods such asLogInformation. For example:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; private readonly ILogger<IndexModel> _logger; public IndexModel(RazorPagesMovieContext context, ILogger<IndexModel> logger) { _context = context; _logger = logger; } public IList<Movie> Movie { get;set; } public async Task OnGetAsync() { _logger.LogInformation("IndexModel OnGetAsync."); Movie = await _context.Movie.ToListAsync(); }}For more information, seeLogging in .NET and ASP.NET Core.
Aroute is a URL pattern that is mapped to a handler. The handler is typically a Razor page, an action method in an MVC controller, or a middleware. ASP.NET Core routing gives you control over the URLs used by your app.
The following code, generated by the ASP.NET Core web application template, callsUseRouting:
var builder = WebApplication.CreateBuilder(args);builder.Services.AddRazorPages();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseRouting();app.UseAuthorization();app.MapRazorPages();app.Run();For more information, seeRouting in ASP.NET Core.
ASP.NET Core has built-in features for handling errors, such as:
For more information, seeHandle errors in ASP.NET Core.
An implementation ofIHttpClientFactory is available for creatingHttpClient instances. The factory:
HttpClient instances. For example, register and configure agithub client for accessing GitHub. Register and configure a default client for other purposes.HttpClientHandler instances to avoid common DNS problems that occur when managingHttpClient lifetimes manually.For more information, seeMake HTTP requests using IHttpClientFactory in ASP.NET Core.
The content root is the base path for:
.cshtml,.razor).json,.xml).db)During development, the content root defaults to the project's root directory. This directory is also the base path for both the app's content files and theWeb root. Specify a different content root by setting its path whenbuilding the host. For more information, seeContent root.
The web root is the base path for public, static resource files, such as:
.css).js).png,.jpg)By default, static files are served only from the web root directory and its sub-directories. The web root path defaults to{content root}/wwwroot. Specify a different web root by setting its path whenbuilding the host. For more information, seeWeb root.
Prevent publishing files inwwwroot with the<Content> project item in the project file. The following example prevents publishing content inwwwroot/local and its sub-directories:
<ItemGroup> <Content Update="wwwroot\local\**\*.*" CopyToPublishDirectory="Never" /></ItemGroup>In Razor.cshtml files,~/ points to the web root. A path beginning with~/ is referred to as avirtual path.
For more information, seeStatic files in ASP.NET Core.
This article provides an overview of the fundamentals for building ASP.NET Core apps, including dependency injection (DI), configuration, middleware, and more.
TheStartup class is where:
Here's a sampleStartup class:
public class Startup{ public void ConfigureServices(IServiceCollection services) { services.AddDbContext<RazorPagesMovieContext>(options => options.UseSqlServer(Configuration.GetConnectionString("RazorPagesMovieContext"))); services.AddControllersWithViews(); services.AddRazorPages(); } public void Configure(IApplicationBuilder app) { app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); app.UseEndpoints(endpoints => { endpoints.MapDefaultControllerRoute(); endpoints.MapRazorPages(); }); }}For more information, seeApp startup in ASP.NET Core.
ASP.NET Core includes a built-in dependency injection (DI) framework that makes configured services available throughout an app. For example, a logging component is a service.
Code to configure (orregister) services is added to theStartup.ConfigureServices method. For example:
public void ConfigureServices(IServiceCollection services){ services.AddDbContext<RazorPagesMovieContext>(options => options.UseSqlServer(Configuration.GetConnectionString("RazorPagesMovieContext"))); services.AddControllersWithViews(); services.AddRazorPages();}Services are typically resolved from DI using constructor injection. With constructor injection, a class declares a constructor parameter of either the required type or an interface. The DI framework provides an instance of this service at runtime.
The following example uses constructor injection to resolve aRazorPagesMovieContext from DI:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; public IndexModel(RazorPagesMovieContext context) { _context = context; } // ... public async Task OnGetAsync() { Movies = await _context.Movies.ToListAsync(); }}If the built-in Inversion of Control (IoC) container doesn't meet all of an app's needs, a third-party IoC container can be used instead.
For more information, seeDependency injection in ASP.NET Core.
The request handling pipeline is composed as a series of middleware components. Each component performs operations on anHttpContext and either invokes the next middleware in the pipeline or terminates the request.
By convention, a middleware component is added to the pipeline by invoking aUse... extension method in theStartup.Configure method. For example, to enable rendering of static files, callUseStaticFiles.
The following example configures a request handling pipeline:
public void Configure(IApplicationBuilder app){ app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); app.UseEndpoints(endpoints => { endpoints.MapDefaultControllerRoute(); endpoints.MapRazorPages(); });}ASP.NET Core includes a rich set of built-in middleware. Custom middleware components can also be written.
For more information, seeASP.NET Core Middleware.
On startup, an ASP.NET Core app builds ahost. The host encapsulates all of the app's resources, such as:
There are two different hosts:
The .NET Generic Host is recommended. The ASP.NET Core Web Host is available only for backwards compatibility.
The following example creates a .NET Generic Host:
public class Program{ public static void Main(string[] args) { CreateHostBuilder(args).Build().Run(); } public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>(); });}TheCreateDefaultBuilder andConfigureWebHostDefaults methods configure a host with a set of default options, such as:
appsettings.json,appsettings.{Environment}.json, environment variables, command line arguments, and other configuration sources.For more information, see.NET Generic Host in ASP.NET Core.
The Generic Host allows other types of apps to use cross-cutting framework extensions, such as logging, dependency injection (DI), configuration, and app lifetime management. For more information, see.NET Generic Host in ASP.NET Core andBackground tasks with hosted services in ASP.NET Core.
An ASP.NET Core app uses an HTTP server implementation to listen for HTTP requests. The server surfaces requests to the app as a set ofrequest features composed into anHttpContext.
ASP.NET Core provides the following server implementations:
For more information, seeWeb server implementations in ASP.NET Core.
ASP.NET Core provides a configuration framework that gets settings as name-value pairs from an ordered set of configuration providers. Built-in configuration providers are available for a variety of sources, such as.json files,.xml files, environment variables, and command-line arguments. Write custom configuration providers to support other sources.
Bydefault, ASP.NET Core apps are configured to read fromappsettings.json, environment variables, the command line, and more. When the app's configuration is loaded, values from environment variables override values fromappsettings.json.
The preferred way to read related configuration values is using theoptions pattern. For more information, seeBind hierarchical configuration data using the options pattern.
For managing confidential configuration data such as passwords, .NET provides theSecret Manager. For production secrets, we recommendAzure Key Vault.
For more information, seeConfiguration in ASP.NET Core.
Execution environments, such asDevelopment,Staging, andProduction, are a first-class notion in ASP.NET Core. Specify the environment an app is running in by setting theASPNETCORE_ENVIRONMENT environment variable. ASP.NET Core reads that environment variable at app startup and stores the value in anIWebHostEnvironment implementation. This implementation is available anywhere in an app via dependency injection (DI).
The following example configures the app to provide detailed error information when running in theDevelopment environment:
public void Configure(IApplicationBuilder app, IWebHostEnvironment env){ if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } else { app.UseExceptionHandler("/Error"); app.UseHsts(); } app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); app.UseEndpoints(endpoints => { endpoints.MapDefaultControllerRoute(); endpoints.MapRazorPages(); });}For more information, seeASP.NET Core runtime environments.
ASP.NET Core supports a logging API that works with a variety of built-in and third-party logging providers. Available providers include:
To create logs, resolve anILogger<TCategoryName> service from dependency injection (DI) and call logging methods such asLogInformation. For example:
public class TodoController : ControllerBase{ private readonly ILogger _logger; public TodoController(ILogger<TodoController> logger) { _logger = logger; } [HttpGet("{id}", Name = "GetTodo")] public ActionResult<TodoItem> GetById(string id) { _logger.LogInformation(LoggingEvents.GetItem, "Getting item {Id}", id); // Item lookup code removed. if (item == null) { _logger.LogWarning(LoggingEvents.GetItemNotFound, "GetById({Id}) NOT FOUND", id); return NotFound(); } return item; }}Logging methods such asLogInformation support any number of fields. These fields are commonly used to construct a messagestring, but some logging providers send these to a data store as separate fields. This feature makes it possible for logging providers to implementsemantic logging, also known as structured logging.
For more information, seeLogging in .NET and ASP.NET Core.
Aroute is a URL pattern that is mapped to a handler. The handler is typically a Razor page, an action method in an MVC controller, or a middleware. ASP.NET Core routing gives you control over the URLs used by your app.
For more information, seeRouting in ASP.NET Core.
ASP.NET Core has built-in features for handling errors, such as:
For more information, seeHandle errors in ASP.NET Core.
An implementation ofIHttpClientFactory is available for creatingHttpClient instances. The factory:
HttpClient instances. For example, register and configure agithub client for accessing GitHub. Register and configure a default client for other purposes.HttpClientHandler instances to avoid common DNS problems that occur when managingHttpClient lifetimes manually.For more information, seeMake HTTP requests using IHttpClientFactory in ASP.NET Core.
The content root is the base path for:
.cshtml,.razor).json,.xml).db)During development, the content root defaults to the project's root directory. This directory is also the base path for both the app's content files and theWeb root. Specify a different content root by setting its path whenbuilding the host. For more information, seeContent root.
The web root is the base path for public, static resource files, such as:
.css).js).png,.jpg)By default, static files are served only from the web root directory and its sub-directories. The web root path defaults to{content root}/wwwroot. Specify a different web root by setting its path whenbuilding the host. For more information, seeWeb root.
Prevent publishing files inwwwroot with the<Content> project item in the project file. The following example prevents publishing content inwwwroot/local and its sub-directories:
<ItemGroup> <Content Update="wwwroot\local\**\*.*" CopyToPublishDirectory="Never" /></ItemGroup>In Razor.cshtml files, tilde-slash (~/) points to the web root. A path beginning with~/ is referred to as avirtual path.
For more information, seeStatic files in ASP.NET Core.
Many of the articles and tutorials include links to sample code.
AspNetCore.Docs-main.zip file.To demonstrate multiple scenarios, sample apps use the#define and#if-#else/#elif-#endif preprocessor directives to selectively compile and run different sections of sample code. For those samples that make use of this approach, set the#define directive at the top of the C# files to define the symbol associated with the scenario that you want to run. Some samples require defining the symbol at the top of multiple files in order to run a scenario.
For example, the following#define symbol list indicates that four scenarios are available (one scenario per symbol). The current sample configuration runs theTemplateCode scenario:
#define TemplateCode // or LogFromMain or ExpandDefault or FilterInCodeTo change the sample to run theExpandDefault scenario, define theExpandDefault symbol and leave the remaining symbols commented-out:
#define ExpandDefault // TemplateCode or LogFromMain or FilterInCodeFor more information on usingC# preprocessor directives to selectively compile sections of code, see#define (C# Reference) and#if (C# Reference).
Some sample apps contain sections of code surrounded by#region and#endregion C# directives. The documentation build system injects these regions into the rendered documentation topics.
Region names usually contain the word "snippet." The following example shows a region namedsnippet_WebHostDefaults:
#region snippet_WebHostDefaultsHost.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>(); });#endregionThe preceding C# code snippet is referenced in the topic's markdown file with the following line:
[!code-csharp[](sample/SampleApp/Program.cs?name=snippet_WebHostDefaults)]You may safely ignore or remove the#region and#endregion directives that surround the code. Don't alter the code within these directives if you plan to run the sample scenarios described in the topic.
For more information, seeContribute to the ASP.NET documentation: Code snippets.
This article provides an overview of the fundamentals for building ASP.NET Core apps, including dependency injection (DI), configuration, middleware, and more.
For Blazor fundamentals guidance, which adds to or supersedes the guidance in this node, seeASP.NET Core Blazor fundamentals.
ASP.NET Core apps created with the web templates contain the application startup code in theProgram.cs file. TheProgram.cs file is where:
The following app startup code supports:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();ASP.NET Core includesdependency injection (DI) that makes configured services available throughout an app. Services are added to the DI container withWebApplicationBuilder.Services,builder.Services in the preceding code. When theWebApplicationBuilder is instantiated, manyframework-provided services are added.builder is aWebApplicationBuilder in the following code:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();In the preceding highlighted code,builder has configuration, logging, andmany other services added to the DI container.
The following code adds Razor Pages, MVC controllers with views, and a customDbContext to the DI container:
using Microsoft.EntityFrameworkCore;using RazorPagesMovie.Data;var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();builder.Services.AddDbContext<RazorPagesMovieContext>(options => options.UseSqlServer(builder.Configuration.GetConnectionString("RPMovieContext")));var app = builder.Build();Services are typically resolved from DI using constructor injection. The DI framework provides an instance of this service at runtime.
The following code uses constructor injection to resolve the database context and logger from DI:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; private readonly ILogger<IndexModel> _logger; public IndexModel(RazorPagesMovieContext context, ILogger<IndexModel> logger) { _context = context; _logger = logger; } public IList<Movie> Movie { get;set; } public async Task OnGetAsync() { _logger.LogInformation("IndexModel OnGetAsync."); Movie = await _context.Movie.ToListAsync(); }}The request handling pipeline is composed as a series of middleware components. Each component performs operations on anHttpContext and either invokes the next middleware in the pipeline or terminates the request.
By convention, a middleware component is added to the pipeline by invoking aUse{Feature} extension method. Middleware added to the app is highlighted in the following code:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();For more information, seeASP.NET Core Middleware.
On startup, an ASP.NET Core app builds ahost. The host encapsulates all of the app's resources, such as:
There are three different hosts capable of running an ASP.NET Core app:
The ASP.NET CoreWebApplication andWebApplicationBuilder types are recommended and used in all the ASP.NET Core templates.WebApplication behaves similarly to the .NET Generic Host and exposes many of the same interfaces but requires less callbacks to configure. The ASP.NET CoreWebHost is available only for backward compatibility.
The following example instantiates aWebApplication:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();TheWebApplicationBuilder.Build method configures a host with a set of default options, such as:
appsettings.json, environment variables, command line arguments, and other configuration sources.The Generic Host allows other types of apps to use cross-cutting framework extensions, such as logging, dependency injection (DI), configuration, and app lifetime management. For more information, see.NET Generic Host in ASP.NET Core andBackground tasks with hosted services in ASP.NET Core.
An ASP.NET Core app uses an HTTP server implementation to listen for HTTP requests. The server surfaces requests to the app as a set ofrequest features composed into anHttpContext.
ASP.NET Core provides the following server implementations:
For more information, seeWeb server implementations in ASP.NET Core.
ASP.NET Core provides aconfiguration framework that gets settings as name-value pairs from an ordered set of configuration providers. Built-in configuration providers are available for a variety of sources, such as.json files,.xml files, environment variables, and command-line arguments. Write custom configuration providers to support other sources.
Bydefault, ASP.NET Core apps are configured to read fromappsettings.json, environment variables, the command line, and more. When the app's configuration is loaded, values from environment variables override values fromappsettings.json.
For managing confidential configuration data such as passwords, .NET provides theSecret Manager. For production secrets, we recommendAzure Key Vault.
For more information, seeConfiguration in ASP.NET Core.
Execution environments, such asDevelopment,Staging, andProduction, are available in ASP.NET Core. Specify the environment an app is running in by setting theASPNETCORE_ENVIRONMENT environment variable. ASP.NET Core reads that environment variable at app startup and stores the value in anIWebHostEnvironment implementation. This implementation is available anywhere in an app via dependency injection (DI).
The following example configures the exception handler andHTTP Strict Transport Security Protocol (HSTS) middleware whennot running in theDevelopment environment:
var builder = WebApplication.CreateBuilder(args);// Add services to the container.builder.Services.AddRazorPages();builder.Services.AddControllersWithViews();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseAuthorization();app.MapGet("/hi", () => "Hello!");app.MapDefaultControllerRoute();app.MapRazorPages();app.Run();For more information, seeASP.NET Core runtime environments.
ASP.NET Core supports a logging API that works with a variety of built-in and third-party logging providers. Available providers include:
To create logs, resolve anILogger<TCategoryName> service from dependency injection (DI) and call logging methods such asLogInformation. For example:
public class IndexModel : PageModel{ private readonly RazorPagesMovieContext _context; private readonly ILogger<IndexModel> _logger; public IndexModel(RazorPagesMovieContext context, ILogger<IndexModel> logger) { _context = context; _logger = logger; } public IList<Movie> Movie { get;set; } public async Task OnGetAsync() { _logger.LogInformation("IndexModel OnGetAsync."); Movie = await _context.Movie.ToListAsync(); }}For more information, seeLogging in .NET and ASP.NET Core.
Aroute is a URL pattern that is mapped to a handler. The handler is typically a Razor page, an action method in an MVC controller, or a middleware. ASP.NET Core routing gives you control over the URLs used by your app.
The following code, generated by the ASP.NET Core web application template, callsUseRouting:
var builder = WebApplication.CreateBuilder(args);builder.Services.AddRazorPages();var app = builder.Build();// Configure the HTTP request pipeline.if (!app.Environment.IsDevelopment()){ app.UseExceptionHandler("/Error"); app.UseHsts();}app.UseHttpsRedirection();app.UseStaticFiles();app.UseRouting();app.UseAuthorization();app.MapRazorPages();app.Run();For more information, seeRouting in ASP.NET Core.
ASP.NET Core has built-in features for handling errors, such as:
For more information, seeHandle errors in ASP.NET Core.
An implementation ofIHttpClientFactory is available for creatingHttpClient instances. The factory:
HttpClient instances. For example, register and configure agithub client for accessing GitHub. Register and configure a default client for other purposes.HttpClientHandler instances to avoid common DNS problems that occur when managingHttpClient lifetimes manually.For more information, seeMake HTTP requests using IHttpClientFactory in ASP.NET Core.
The content root is the base path for:
.cshtml,.razor).json,.xml).db)During development, the content root defaults to the project's root directory. This directory is also the base path for both the app's content files and theWeb root. Specify a different content root by setting its path whenbuilding the host. For more information, seeContent root.
The web root is the base path for public, static resource files, such as:
.css).js).png,.jpg)By default, static files are served only from the web root directory and its sub-directories. The web root path defaults to{content root}/wwwroot. Specify a different web root by setting its path whenbuilding the host. For more information, seeWeb root.
Prevent publishing files inwwwroot with the<Content> project item in the project file. The following example prevents publishing content inwwwroot/local and its sub-directories:
<ItemGroup> <Content Update="wwwroot\local\**\*.*" CopyToPublishDirectory="Never" /></ItemGroup>In Razor.cshtml files,~/ points to the web root. A path beginning with~/ is referred to as avirtual path.
For more information, seeStatic files in ASP.NET Core.
Many of the articles and tutorials include links to sample code.
AspNetCore.Docs-main.zip file.To demonstrate multiple scenarios, sample apps use the#define and#if-#else/#elif-#endif preprocessor directives to selectively compile and run different sections of sample code. For those samples that make use of this approach, set the#define directive at the top of the C# files to define the symbol associated with the scenario that you want to run. Some samples require defining the symbol at the top of multiple files in order to run a scenario.
For example, the following#define symbol list indicates that four scenarios are available (one scenario per symbol). The current sample configuration runs theTemplateCode scenario:
#define TemplateCode // or LogFromMain or ExpandDefault or FilterInCodeTo change the sample to run theExpandDefault scenario, define theExpandDefault symbol and leave the remaining symbols commented-out:
#define ExpandDefault // TemplateCode or LogFromMain or FilterInCodeFor more information on usingC# preprocessor directives to selectively compile sections of code, see#define (C# Reference) and#if (C# Reference).
Some sample apps contain sections of code surrounded by#region and#endregion C# directives. The documentation build system injects these regions into the rendered documentation topics.
Region names usually contain the word "snippet." The following example shows a region namedsnippet_WebHostDefaults:
#region snippet_WebHostDefaultsHost.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>(); });#endregionThe preceding C# code snippet is referenced in the topic's markdown file with the following line:
[!code-csharp[](sample/SampleApp/Program.cs?name=snippet_WebHostDefaults)]You may safely ignore or remove the#region and#endregion directives that surround the code. Don't alter the code within these directives if you plan to run the sample scenarios described in the topic.
For more information, seeContribute to the ASP.NET documentation: Code snippets.
Was this page helpful?
Need help with this topic?
Want to try using Ask Learn to clarify or guide you through this topic?
Was this page helpful?
Want to try using Ask Learn to clarify or guide you through this topic?