ASP.NET Core Web 主機

ASP.NET Core 應用程式會設定並啟動「主機」。 主機負責應用程式啟動和存留期管理。 至少,主機會設定伺服器和要求處理管線。 主機也可以設定記錄、相依性插入和設定。

此文章涵蓋 Web 主機,而且我們僅因為回溯相容性而繼續提供它。 ASP.NET Core範本會 WebApplicationBuilder 建立 和 WebApplication ,建議用於 Web 應用程式。 如需 和 WebApplication 的詳細資訊 WebApplicationBuilder ,請參閱從 ASP.NET Core 5.0 移轉至 6.0

設定主機

使用 的 IWebHostBuilder 實例建立主機。 這通常會在應用程式的進入點中執行,也就是 Main 中的 Program.cs 方法。 一般應用程式呼叫 CreateDefaultBuilder 以開始設定主機:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
        WebHost.CreateDefaultBuilder(args)
            .UseStartup<Startup>();
}

呼叫 CreateDefaultBuilder 的程式碼位於名為 CreateWebHostBuilder 的方法中,這將它與 Main 中呼叫產生器物件上之 Run 的方法分開。 若您使用e Entity Framework Core 工具,則此分開是必要的。 工具預期找到它們可以在設計階段呼叫的 CreateWebHostBuilder 方法,以在不執行應用程式的情況下設定主機。 替代方式是實作 IDesignTimeDbContextFactory。 如需詳細資訊,請參閱設計階段 DbContext 建立

CreateDefaultBuilder 會執行下列工作:

CreateDefaultBuilder 定義的組態可以由 ConfigureAppConfigurationConfigureLogging 和其他方法和擴充方法 IWebHostBuilder 覆寫和增強。 數個範例如下:

  • ConfigureAppConfiguration 用來為應用程式指定其他 IConfiguration 專案。 下列 ConfigureAppConfiguration 呼叫會新增委派,以在 檔案中包含 appsettings.xml 應用程式組態。 可能會多次呼叫 ConfigureAppConfiguration。 請注意,此組態不適用於主機 (例如,伺服器 URL 或環境)。 請參閱主機組態值一節。

    WebHost.CreateDefaultBuilder(args)
        .ConfigureAppConfiguration((hostingContext, config) =>
        {
            config.AddXmlFile("appsettings.xml", optional: true, reloadOnChange: true);
        })
        ...
    
  • 下列 ConfigureLogging 呼叫會新增委派,以將最小記錄層級設定 SetMinimumLevel 為 () LogLevel.Warning 。 此設定會 appsettings.Development.json 覆寫 (LogLevel.Debug) 和 appsettings.Production.jsonLogLevel.Error () 中設定的 CreateDefaultBuilder 設定。 可能會多次呼叫 ConfigureLogging

    WebHost.CreateDefaultBuilder(args)
        .ConfigureLogging(logging => 
        {
            logging.SetMinimumLevel(LogLevel.Warning);
        })
        ...
    
  • 下列呼叫會 ConfigureKestrel 覆寫 在 設定時 KestrelCreateDefaultBuilder 所建立的預設Limits.MaxRequestBodySize為 30,000,000 個位元組:

    WebHost.CreateDefaultBuilder(args)
        .ConfigureKestrel((context, options) =>
        {
            options.Limits.MaxRequestBodySize = 20000000;
        });
    

「內容根目錄」會決定主機搜尋內容檔案 (例如 MVC 檢視檔案) 的位置。 從專案的根資料夾啟動應用程式時,會使用專案的根資料夾作為內容根目錄。 這是 Visual Studiodotnet 新範本中使用的預設值。

如需應用程式設定的詳細資訊,請參閱 ASP.NET Core 中的組態

注意

除了使用靜態 CreateDefaultBuilder 方法,從 建立主機 WebHostBuilder 是支援使用 ASP.NET Core 2.x 的方法。

設定主機時, Configure 可以提供 和 ConfigureServices 方法。 如果指定 Startup 類別,它必須定義 Configure 方法。 如需詳細資訊,請參閱 ASP.NET Core 中的應用程式啟動。 多次呼叫 ConfigureServices 會彼此附加。 對 WebHostBuilder 多次呼叫 ConfigureUseStartup 則會取代先前的設定。

主機組態值

WebHostBuilder 依賴下列方法來設定主機組態值:

  • 主機建立器組態,其中包含 ASPNETCORE_{configurationKey} 格式的環境變數。 例如: ASPNETCORE_ENVIRONMENT
  • 例如 和 UseConfiguration (的 UseContentRoot 延伸模組請參閱覆寫組態一節) 。
  • UseSetting 和相關聯的索引鍵。 使用 UseSetting 設定值時,此值會設定為字串,而不論其類型為何。

主機使用設定最後一個值的任何選項。 如需詳細資訊,請參閱下一節的覆寫組態

應用程式索引鍵 (名稱)

在主機建構期間呼叫 或 ConfigureUseStartup ,會自動 IWebHostEnvironment.ApplicationName 設定 屬性。 該值會設定為包含應用程式進入點的組件名稱。 若要明確設定值,請使用 WebHostDefaults.ApplicationKey

索引鍵:applicationName
類型字串
預設:包含應用程式進入點的組件名稱。
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_APPLICATIONNAME

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.ApplicationKey, "CustomApplicationName")

擷取啟動錯誤

此設定會控制啟動錯誤的擷取。

索引鍵:captureStartupErrors
類型bool (true1)
預設值false 除非應用程式在 Kestrel IIS 後方執行,否則預設值為 true
使用下列專案進行設定CaptureStartupErrors
環境變數ASPNETCORE_CAPTURESTARTUPERRORS

當它為 false 時,啟動期間發生的錯誤會導致主機結束。 當它為 true 時,主機會擷取啟動期間的例外狀況,並嘗試啟動伺服器。

WebHost.CreateDefaultBuilder(args)
    .CaptureStartupErrors(true)

內容根目錄

此設定會決定 ASP.NET Core開始搜尋內容檔案的位置。

索引鍵:contentRoot
類型字串
預設值:預設為應用程式組件所在的資料夾。
使用下列專案進行設定UseContentRoot
環境變數ASPNETCORE_CONTENTROOT

內容根目錄也會作為 Web 根目錄的基底路徑。 如果內容根路徑不存在,主機將無法啟動。

WebHost.CreateDefaultBuilder(args)
    .UseContentRoot("c:\\<content-root>")

如需詳細資訊,請參閱

詳細錯誤

決定是否應該擷取詳細的錯誤。

索引鍵:detailedErrors
類型bool (true1)
預設值:false
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_DETAILEDERRORS

啟用時 (或當 Environment 設定為 Development 時),應用程式會擷取詳細例外狀況。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.DetailedErrorsKey, "true")

環境

設定應用程式的環境。

索引鍵:environment
類型字串
預設值:Production
使用下列專案進行設定UseEnvironment
環境變數ASPNETCORE_ENVIRONMENT

環境可以設定為任何值。 架構定義的值包括 DevelopmentStagingProduction。 值不區分大小寫。 根據預設,Environment 是從 ASPNETCORE_ENVIRONMENT 環境變數讀取。 使用 Visual Studio時,可以在 檔案中 launchSettings.json 設定環境變數。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

WebHost.CreateDefaultBuilder(args)
    .UseEnvironment(EnvironmentName.Development)

裝載啟動組件

設定應用程式的裝載啟動組件。

索引鍵:hostingStartupAssemblies
類型字串
預設值:空字串
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPASSEMBLIES

在啟動時載入的裝載啟動組件字串,以分號分隔。

雖然設定值會預設為空字串,但裝載啟動組件一律會包含應用程式的組件。 提供裝載啟動組件時,它們會新增至應用程式的組件,以便在應用程式在啟動時建置其通用服務時載入。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupAssembliesKey, "assembly1;assembly2")

HTTPS 連接埠

設定 HTTPS 重新導向連接埠。 用於強制 HTTPS

機碼:HTTPs_port
類型字串
預設值:未設定預設值。
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HTTPS_PORT

WebHost.CreateDefaultBuilder(args)
    .UseSetting("https_port", "8080")

裝載啟動排除組件

在啟動時排除以分號分隔的裝載啟動組件字串。

索引鍵:hostingStartupExcludeAssemblies
類型字串
預設值:空字串
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPEXCLUDEASSEMBLIES

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupExcludeAssembliesKey, "assembly1;assembly2")

偏好裝載 URL

表示主機是否應接聽使用 WebHostBuilder 設定的 URL,而不是 IServer 實作所設定的 URL。

索引鍵:preferHostingUrls
類型bool (true1)
預設值:true
使用下列專案進行設定PreferHostingUrls
環境變數ASPNETCORE_PREFERHOSTINGURLS

WebHost.CreateDefaultBuilder(args)
    .PreferHostingUrls(false)

防止裝載啟動

可防止自動載入裝載啟動組件,包括應用程式組件所設定的裝載啟動組件。 如需詳細資訊,請參閱在 ASP.NET Core 中使用裝載啟動組件 (部分機器翻譯)。

索引鍵preventHostingStartup
類型bool (true1)
預設值:false
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_PREVENTHOSTINGSTARTUP

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.PreventHostingStartupKey, "true")

伺服器 URL

表示伺服器應該接聽要求的 IP 位址或主機位址,以及連接埠和通訊協定。

索引鍵:urls
類型字串
預設:http://localhost:5000
使用下列專案進行設定UseUrls
環境變數ASPNETCORE_URLS

設定為伺服器應該回應的 URL 前置清單,並以分號 (;) 分隔。 例如: http://localhost:123 。 使用 「*」 表示伺服器應該使用指定的埠和通訊協定接聽任何 IP 位址或主機名稱的要求,例如 () http://*:5000 。 通訊協定 (http://https://) 必須包含在每個 URL 中。 支援的格式會依伺服器而有所不同。

WebHost.CreateDefaultBuilder(args)
    .UseUrls("http://*:5000;http://localhost:5001;https://hostname:5002")

Kestrel 有自己的端點組態 API。 如需詳細資訊,請參閱設定 ASP.NET Core Kestrel Web 服務器的端點

關機逾時

指定等待 Web 主機關機的時間長度。

索引鍵:shutdownTimeoutSeconds
類型int
預設值:5
使用下列專案進行設定UseShutdownTimeout
環境變數ASPNETCORE_SHUTDOWNTIMEOUTSECONDS

雖然索引鍵接受 intUseSetting (例如 .UseSetting(WebHostDefaults.ShutdownTimeoutKey, "10")),UseShutdownTimeout 擴充方法會採用 TimeSpan

在逾時期間,裝載會:

如果在所有的託管服務停止之前逾時期限已到期,則應用程式關閉時,會停止任何剩餘的作用中服務。 即使服務尚未完成處理也會停止。 如果服務需要更多時間才能停止,請增加逾時。

WebHost.CreateDefaultBuilder(args)
    .UseShutdownTimeout(TimeSpan.FromSeconds(10))

啟動組件

決定要搜尋 Startup 類別的組件。

索引鍵:startupAssembly
類型字串
預設值:應用程式的組件
使用下列專案進行設定UseStartup
環境變數ASPNETCORE_STARTUPASSEMBLY

可以參考依名稱 (string) 或類型 (TStartup) 的組件。 如果呼叫多個 UseStartup 方法,最後一個將會優先。

WebHost.CreateDefaultBuilder(args)
    .UseStartup("StartupAssemblyName")
WebHost.CreateDefaultBuilder(args)
    .UseStartup<TStartup>()

Web 根目錄

設定應用程式靜態資產的相對路徑。

索引鍵:webroot
類型字串
預設值:預設值為 wwwroot{content root}/wwwroot的路徑必須存在。 如果路徑不存在,則會使用無作業檔案提供者。
使用下列專案設定UseWebRoot
環境變數ASPNETCORE_WEBROOT

WebHost.CreateDefaultBuilder(args)
    .UseWebRoot("public")

如需詳細資訊,請參閱

覆寫組態

使用 Configuration 來設定 Web 主機。 在下列範例中,會選擇性地在檔案中 hostsettings.json 指定主機組態。 從 hostsettings.json 檔案載入的任何組態,都可以由命令列引數覆寫。 組建組態 (在 config 中) 用以使用 UseConfiguration 來設定主機。 IWebHostBuilder 組態會新增至應用程式的組態,但相反的不是 true, ConfigureAppConfiguration 不會影響設定 IWebHostBuilder

以 config first、命令列引數 config second 覆寫 所提供的 UseUrlshostsettings.json 組態:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args)
    {
        var config = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("hostsettings.json", optional: true)
            .AddCommandLine(args)
            .Build();

        return WebHost.CreateDefaultBuilder(args)
            .UseUrls("http://*:5000")
            .UseConfiguration(config)
            .Configure(app =>
            {
                app.Run(context => 
                    context.Response.WriteAsync("Hello, World!"));
            });
    }
}

hostsettings.json:

{
    urls: "http://*:5005"
}

注意

UseConfiguration 只會將索引鍵從提供的 IConfiguration 複製到主機建立器的組態。 因此,ON JS 、INI 和 XML 設定檔的設定 reloadOnChange: true 沒有任何作用。

若要指定主機在特定 URL 上執行,所要的值可以在執行 dotnet run 時從命令提示字元傳入。 命令列引數會 urls 覆寫檔案中的 hostsettings.json 值,而伺服器會接聽埠 8080:

dotnet run --urls "http://*:8080"

管理主機

執行

Run 方法會啟動 Web 應用程式,並且封鎖呼叫執行緒,直到主機關閉為止:

host.Run();

開始

藉由呼叫 Start 方法,以非封鎖方式執行主機:

using (host)
{
    host.Start();
    Console.ReadLine();
}

如果 URL 的清單傳遞至 Start 方法,它會接聽指定的 URL:

var urls = new List<string>()
{
    "http://*:5000",
    "http://localhost:5001"
};

var host = new WebHostBuilder()
    .UseKestrel()
    .UseStartup<Startup>()
    .Start(urls.ToArray());

using (host)
{
    Console.ReadLine();
}

應用程式可以使用預先設定的 CreateDefaultBuilder 預設值,使用便利的靜態方法初始化並啟動新的主機。 這些方法會啟動不含主控台輸出的伺服器,並 WaitForShutdown 等候中斷 (Ctrl-C/SIGINT 或 SIGTERM) :

Start(RequestDelegate app)

使用 RequestDelegate 啟動:

using (var host = WebHost.Start(app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, RequestDelegate app)

使用 URL 和 RequestDelegate 來啟動:

using (var host = WebHost.Start("http://localhost:8080", app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

產生與 Start(RequestDelegate app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

Start(Action<IRouteBuilder> routeBuilder)

使用 IRouteBuilder (Microsoft.AspNetCore.Routing) 的執行個體來使用路由中介軟體:

using (var host = WebHost.Start(router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

使用下列瀏覽器要求與範例:

要求 回應
http://localhost:5000/hello/Martin Hello, Martin!
http://localhost:5000/buenosdias/Catrina Buenos dias, Catrina!
http://localhost:5000/throw/ooops! 擲回例外狀況,字串為 "ooops!"
http://localhost:5000/throw 擲回例外狀況,字串為 "Un oh!"
http://localhost:5000/Sante/Kevin Sante, Kevin!
http://localhost:5000 Hello World!

WaitForShutdown 會封鎖,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM)。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, Action<IRouteBuilder> routeBuilder)

使用 URL 和 IRouteBuilder 的執行個體:

using (var host = WebHost.Start("http://localhost:8080", router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 Start(Action<IRouteBuilder> routeBuilder) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

StartWith(Action<IApplicationBuilder> app)

提供委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith(app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

StartWith(string url, Action<IApplicationBuilder> app)

提供 URL 和委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith("http://localhost:8080", app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 StartWith(Action<IApplicationBuilder> app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

IWebHostEnvironment 介面

介面 IWebHostEnvironment 提供應用程式 Web 裝載環境的相關資訊。 使用建構函式插入以取得 IWebHostEnvironment,才能使用其屬性和擴充方法:

public class CustomFileReader
{
    private readonly IWebHostEnvironment _env;

    public CustomFileReader(IWebHostEnvironment env)
    {
        _env = env;
    }

    public string ReadFile(string filePath)
    {
        var fileProvider = _env.WebRootFileProvider;
        // Process the file here
    }
}

以慣例為基礎的方法可用來根據環境在啟動時設定應用程式。 或者,將 IWebHostEnvironment 插入至 Startup 建構函式,以便用於 ConfigureServices

public class Startup
{
    public Startup(IWebHostEnvironment env)
    {
        HostingEnvironment = env;
    }

    public IWebHostEnvironment HostingEnvironment { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        if (HostingEnvironment.IsDevelopment())
        {
            // Development configuration
        }
        else
        {
            // Staging/Production configuration
        }

        var contentRootPath = HostingEnvironment.ContentRootPath;
    }
}

注意

除了 IsDevelopment 擴充方法,IWebHostEnvironment 也提供 IsStagingIsProductionIsEnvironment(string environmentName) 方法。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

IWebHostEnvironment 服務也可直接插入至 Configure 方法,以便設定處理管線:

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // In Development, use the Developer Exception Page
        app.UseDeveloperExceptionPage();
    }
    else
    {
        // In Staging/Production, route exceptions to /error
        app.UseExceptionHandler("/error");
    }

    var contentRootPath = env.ContentRootPath;
}

建立自訂中介軟體時,IWebHostEnvironment 可以插入至 Invoke 方法:

public async Task Invoke(HttpContext context, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // Configure middleware for Development
    }
    else
    {
        // Configure middleware for Staging/Production
    }

    var contentRootPath = env.ContentRootPath;
}

IHostApplicationLifetime 介面

IHostApplicationLifetime 允許啟動後和關機活動。 在介面上的三個屬性是用來註冊定義啟動和關閉事件之 Action 方法的取消語彙基元。

取消權杖 觸發時機...
ApplicationStarted 已完全啟動主機。
ApplicationStopped 主機正在完成正常關機程序。 應該處理所有要求。 關機封鎖,直到完成此事件。
ApplicationStopping 主機正在執行正常關機程序。 可能仍在處理要求。 關機封鎖,直到完成此事件。
public class Startup
{
    public void Configure(IApplicationBuilder app, IHostApplicationLifetime appLifetime)
    {
        appLifetime.ApplicationStarted.Register(OnStarted);
        appLifetime.ApplicationStopping.Register(OnStopping);
        appLifetime.ApplicationStopped.Register(OnStopped);

        Console.CancelKeyPress += (sender, eventArgs) =>
        {
            appLifetime.StopApplication();
            // Don't terminate the process immediately, wait for the Main thread to exit gracefully.
            eventArgs.Cancel = true;
        };
    }

    private void OnStarted()
    {
        // Perform post-startup activities here
    }

    private void OnStopping()
    {
        // Perform on-stopping activities here
    }

    private void OnStopped()
    {
        // Perform post-stopped activities here
    }
}

StopApplication 會要求應用程式終止。 當呼叫類別的 Shutdown 方法時,下列類別使用 StopApplication 來順利關閉應用程式:

public class MyClass
{
    private readonly IHostApplicationLifetime _appLifetime;

    public MyClass(IHostApplicationLifetime appLifetime)
    {
        _appLifetime = appLifetime;
    }

    public void Shutdown()
    {
        _appLifetime.StopApplication();
    }
}

範圍驗證

CreateDefaultBuildertrue如果應用程式的環境為 [開發],則會設定 ServiceProviderOptions.ValidateScopes 為 。

ValidateScopes 設定為 true 時,預設服務提供者會執行檢查以確認:

  • 範圍服務不是直接或間接由開機服務提供者解析。
  • 範圍服務不是直接或間接插入至單一服務。

根服務提供者會在呼叫 BuildServiceProvider 時建立。 當提供者啟動應用程式時,根服務提供者的存留期與應用程式/伺服器的存留期一致,並會在應用程式關閉時處置。

範圍服務會由建立這些服務的容器處置。 若是在根容器中建立範圍服務,因為當應用程式/伺服器關機時,服務只會由根容器處理,所以服務的存留期會提升為單一服務等級。 當呼叫 BuildServiceProvider 時,驗證服務範圍會攔截到這些情況。

若要一律驗證範圍,包括生產環境中, ServiceProviderOptionsUseDefaultServiceProvider 請在主機產生器上使用 設定 :

WebHost.CreateDefaultBuilder(args)
    .UseDefaultServiceProvider((context, options) => {
        options.ValidateScopes = true;
    })

其他資源

ASP.NET Core 應用程式會設定並啟動「主機」。 主機負責應用程式啟動和存留期管理。 至少,主機會設定伺服器和要求處理管線。 主機也可以設定記錄、相依性插入和設定。

此文章涵蓋 Web 主機,而且我們僅因為回溯相容性而繼續提供它。 ASP.NET Core範本會建立.NET 泛型主機,建議用於所有應用程式類型。

設定主機

使用 的 IWebHostBuilder 實例建立主機。 這通常在應用程式的進入點執行,也就是 Main 方法。

在專案範本中, Main 位於 Program.cs 。 一般應用程式呼叫 CreateDefaultBuilder 以開始設定主機:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
        WebHost.CreateDefaultBuilder(args)
            .UseStartup<Startup>();
}

呼叫 CreateDefaultBuilder 的程式碼位於名為 CreateWebHostBuilder 的方法中,這將它與 Main 中呼叫產生器物件上之 Run 的方法分開。 若您使用e Entity Framework Core 工具,則此分開是必要的。 工具預期找到它們可以在設計階段呼叫的 CreateWebHostBuilder 方法,以在不執行應用程式的情況下設定主機。 替代方式是實作 IDesignTimeDbContextFactory。 如需詳細資訊,請參閱設計階段 DbContext 建立

CreateDefaultBuilder 會執行下列工作:

CreateDefaultBuilder 定義的組態可以由 ConfigureAppConfigurationConfigureLogging 和其他方法和擴充方法 IWebHostBuilder 覆寫和增強。 數個範例如下:

  • ConfigureAppConfiguration 用來為應用程式指定其他 IConfiguration 專案。 下列 ConfigureAppConfiguration 呼叫會新增委派,以在 檔案中包含 appsettings.xml 應用程式組態。 可能會多次呼叫 ConfigureAppConfiguration。 請注意,此組態不適用於主機 (例如,伺服器 URL 或環境)。 請參閱主機組態值一節。

    WebHost.CreateDefaultBuilder(args)
        .ConfigureAppConfiguration((hostingContext, config) =>
        {
            config.AddXmlFile("appsettings.xml", optional: true, reloadOnChange: true);
        })
        ...
    
  • 下列 ConfigureLogging 呼叫會新增委派,以將最小記錄層級設定 SetMinimumLevel 為 () LogLevel.Warning 。 此設定會 appsettings.Development.json 覆寫 (LogLevel.Debug) 和 appsettings.Production.jsonLogLevel.Error () 中設定的 CreateDefaultBuilder 設定。 可能會多次呼叫 ConfigureLogging

    WebHost.CreateDefaultBuilder(args)
        .ConfigureLogging(logging => 
        {
            logging.SetMinimumLevel(LogLevel.Warning);
        })
        ...
    
  • 下列呼叫會 ConfigureKestrel 覆寫 在 設定時 KestrelCreateDefaultBuilder 所建立的預設Limits.MaxRequestBodySize為 30,000,000 個位元組:

    WebHost.CreateDefaultBuilder(args)
        .ConfigureKestrel((context, options) =>
        {
            options.Limits.MaxRequestBodySize = 20000000;
        });
    

「內容根目錄」會決定主機搜尋內容檔案 (例如 MVC 檢視檔案) 的位置。 從專案的根資料夾啟動應用程式時,會使用專案的根資料夾作為內容根目錄。 這是 Visual Studiodotnet 新範本中使用的預設值。

如需應用程式設定的詳細資訊,請參閱 ASP.NET Core 中的組態

注意

除了使用靜態 CreateDefaultBuilder 方法,從 建立主機 WebHostBuilder 是支援使用 ASP.NET Core 2.x 的方法。

設定主機時, Configure 可以提供 和 ConfigureServices 方法。 如果指定 Startup 類別,它必須定義 Configure 方法。 如需詳細資訊,請參閱 ASP.NET Core 中的應用程式啟動。 多次呼叫 ConfigureServices 會彼此附加。 對 WebHostBuilder 多次呼叫 ConfigureUseStartup 則會取代先前的設定。

主機組態值

WebHostBuilder 依賴下列方法來設定主機組態值:

  • 主機建立器組態,其中包含 ASPNETCORE_{configurationKey} 格式的環境變數。 例如: ASPNETCORE_ENVIRONMENT
  • 例如 和 UseConfiguration (的 UseContentRoot 延伸模組請參閱覆寫組態一節) 。
  • UseSetting 和相關聯的索引鍵。 使用 UseSetting 設定值時,此值會設定為字串,而不論其類型為何。

主機使用設定最後一個值的任何選項。 如需詳細資訊,請參閱下一節的覆寫組態

應用程式索引鍵 (名稱)

在主機建構期間呼叫 或 ConfigureUseStartup ,會自動 IWebHostEnvironment.ApplicationName 設定 屬性。 該值會設定為包含應用程式進入點的組件名稱。 若要明確設定值,請使用 WebHostDefaults.ApplicationKey

索引鍵:applicationName
類型字串
預設:包含應用程式進入點的組件名稱。
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_APPLICATIONNAME

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.ApplicationKey, "CustomApplicationName")

擷取啟動錯誤

此設定會控制啟動錯誤的擷取。

索引鍵:captureStartupErrors
類型bool (true1)
預設值false 除非應用程式在 Kestrel IIS 後方執行,否則預設值為 true
使用下列專案進行設定CaptureStartupErrors
環境變數ASPNETCORE_CAPTURESTARTUPERRORS

當它為 false 時,啟動期間發生的錯誤會導致主機結束。 當它為 true 時,主機會擷取啟動期間的例外狀況,並嘗試啟動伺服器。

WebHost.CreateDefaultBuilder(args)
    .CaptureStartupErrors(true)

內容根目錄

此設定會決定 ASP.NET Core開始搜尋內容檔案的位置。

索引鍵:contentRoot
類型字串
預設值:預設為應用程式組件所在的資料夾。
使用下列專案進行設定UseContentRoot
環境變數ASPNETCORE_CONTENTROOT

內容根目錄也會作為 Web 根目錄的基底路徑。 如果內容根路徑不存在,主機將無法啟動。

WebHost.CreateDefaultBuilder(args)
    .UseContentRoot("c:\\<content-root>")

如需詳細資訊,請參閱

詳細錯誤

決定是否應該擷取詳細的錯誤。

索引鍵:detailedErrors
類型bool (true1)
預設值:false
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_DETAILEDERRORS

啟用時 (或當 Environment 設定為 Development 時),應用程式會擷取詳細例外狀況。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.DetailedErrorsKey, "true")

環境

設定應用程式的環境。

索引鍵:environment
類型字串
預設值:Production
使用下列專案設定UseEnvironment
環境變數ASPNETCORE_ENVIRONMENT

環境可以設定為任何值。 架構定義的值包括 DevelopmentStagingProduction。 值不區分大小寫。 根據預設,Environment 是從 ASPNETCORE_ENVIRONMENT 環境變數讀取。 使用 Visual Studio時,可以在 檔案中 launchSettings.json 設定環境變數。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

WebHost.CreateDefaultBuilder(args)
    .UseEnvironment(EnvironmentName.Development)

裝載啟動組件

設定應用程式的裝載啟動組件。

索引鍵:hostingStartupAssemblies
類型字串
預設值:空字串
使用下列專案設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPASSEMBLIES

在啟動時載入的裝載啟動組件字串,以分號分隔。

雖然設定值會預設為空字串,但裝載啟動組件一律會包含應用程式的組件。 提供裝載啟動組件時,它們會新增至應用程式的組件,以便在應用程式在啟動時建置其通用服務時載入。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupAssembliesKey, "assembly1;assembly2")

HTTPS 連接埠

設定 HTTPS 重新導向連接埠。 用於強制 HTTPS

機碼:HTTPs_port
類型字串
預設值:未設定預設值。
使用下列專案設定UseSetting
環境變數ASPNETCORE_HTTPS_PORT

WebHost.CreateDefaultBuilder(args)
    .UseSetting("https_port", "8080")

裝載啟動排除組件

在啟動時排除以分號分隔的裝載啟動組件字串。

索引鍵:hostingStartupExcludeAssemblies
類型字串
預設值:空字串
使用下列專案設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPEXCLUDEASSEMBLIES

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupExcludeAssembliesKey, "assembly1;assembly2")

偏好裝載 URL

表示主機是否應接聽使用 WebHostBuilder 設定的 URL,而不是 IServer 實作所設定的 URL。

索引鍵:preferHostingUrls
類型bool (true1)
預設值:true
使用下列專案設定PreferHostingUrls
環境變數ASPNETCORE_PREFERHOSTINGURLS

WebHost.CreateDefaultBuilder(args)
    .PreferHostingUrls(false)

防止裝載啟動

可防止自動載入裝載啟動組件,包括應用程式組件所設定的裝載啟動組件。 如需詳細資訊,請參閱在 ASP.NET Core 中使用裝載啟動組件 (部分機器翻譯)。

索引鍵preventHostingStartup
類型bool (true1)
預設值:false
使用下列專案設定UseSetting
環境變數ASPNETCORE_PREVENTHOSTINGSTARTUP

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.PreventHostingStartupKey, "true")

伺服器 URL

表示伺服器應該接聽要求的 IP 位址或主機位址,以及連接埠和通訊協定。

索引鍵:urls
類型字串
預設:http://localhost:5000
使用下列專案設定UseUrls
環境變數ASPNETCORE_URLS

設定為伺服器應該回應的 URL 前置清單,並以分號 (;) 分隔。 例如: http://localhost:123 。 使用 「*」 表示伺服器應該使用指定的埠和 (通訊協定接聽任何 IP 位址或主機名稱的要求, http://*:5000 例如,) 。 通訊協定 (http://https://) 必須包含在每個 URL 中。 支援的格式會依伺服器而有所不同。

WebHost.CreateDefaultBuilder(args)
    .UseUrls("http://*:5000;http://localhost:5001;https://hostname:5002")

Kestrel 有自己的端點組態 API。 如需詳細資訊,請參閱設定 ASP.NET Core Kestrel Web 服務器的端點

關機逾時

指定等待 Web 主機關機的時間長度。

索引鍵:shutdownTimeoutSeconds
類型int
預設值:5
使用下列專案設定UseShutdownTimeout
環境變數ASPNETCORE_SHUTDOWNTIMEOUTSECONDS

雖然索引鍵接受 intUseSetting (例如 .UseSetting(WebHostDefaults.ShutdownTimeoutKey, "10")),UseShutdownTimeout 擴充方法會採用 TimeSpan

在逾時期間,裝載會:

如果在所有的託管服務停止之前逾時期限已到期,則應用程式關閉時,會停止任何剩餘的作用中服務。 即使服務尚未完成處理也會停止。 如果服務需要更多時間才能停止,請增加逾時。

WebHost.CreateDefaultBuilder(args)
    .UseShutdownTimeout(TimeSpan.FromSeconds(10))

啟動組件

決定要搜尋 Startup 類別的組件。

索引鍵:startupAssembly
類型字串
預設值:應用程式的組件
使用下列專案設定UseStartup
環境變數ASPNETCORE_STARTUPASSEMBLY

可以參考依名稱 (string) 或類型 (TStartup) 的組件。 如果呼叫多個 UseStartup 方法,最後一個將會優先。

WebHost.CreateDefaultBuilder(args)
    .UseStartup("StartupAssemblyName")
WebHost.CreateDefaultBuilder(args)
    .UseStartup<TStartup>()

Web 根目錄

設定應用程式靜態資產的相對路徑。

索引鍵:webroot
類型字串
預設值:預設值為 wwwroot{content root}/wwwroot的路徑必須存在。 如果路徑不存在,則會使用無作業檔案提供者。
使用下列專案設定UseWebRoot
環境變數ASPNETCORE_WEBROOT

WebHost.CreateDefaultBuilder(args)
    .UseWebRoot("public")

如需詳細資訊,請參閱

覆寫組態

使用 Configuration 來設定 Web 主機。 在下列範例中,會選擇性地在 hostsettings.json 檔案中指定主機組態。 從 hostsettings.json 檔案載入的任何組態都可以由命令列引數覆寫。 組建組態 (在 config 中) 用以使用 UseConfiguration 來設定主機。 IWebHostBuilder 組態會新增至應用程式的組態,但相反的並不成立, ConfigureAppConfiguration 不會影響設定 IWebHostBuilder

以 config first、命令列引數 config second 覆寫所提供的 UseUrlshostsettings.json 組態:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args)
    {
        var config = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("hostsettings.json", optional: true)
            .AddCommandLine(args)
            .Build();

        return WebHost.CreateDefaultBuilder(args)
            .UseUrls("http://*:5000")
            .UseConfiguration(config)
            .Configure(app =>
            {
                app.Run(context => 
                    context.Response.WriteAsync("Hello, World!"));
            });
    }
}

hostsettings.json:

{
    urls: "http://*:5005"
}

注意

UseConfiguration 只會將索引鍵從提供的 IConfiguration 複製到主機建立器的組態。 因此,ON、INI 和 XML 設定檔的 JS 設定 reloadOnChange: true 沒有任何作用。

若要指定主機在特定 URL 上執行,所要的值可以在執行 dotnet run 時從命令提示字元傳入。 命令列引數會 urls 覆寫檔案中的 hostsettings.json 值,而伺服器會接聽埠 8080:

dotnet run --urls "http://*:8080"

管理主機

執行

Run 方法會啟動 Web 應用程式,並且封鎖呼叫執行緒,直到主機關閉為止:

host.Run();

開始

藉由呼叫 Start 方法,以非封鎖方式執行主機:

using (host)
{
    host.Start();
    Console.ReadLine();
}

如果 URL 的清單傳遞至 Start 方法,它會接聽指定的 URL:

var urls = new List<string>()
{
    "http://*:5000",
    "http://localhost:5001"
};

var host = new WebHostBuilder()
    .UseKestrel()
    .UseStartup<Startup>()
    .Start(urls.ToArray());

using (host)
{
    Console.ReadLine();
}

應用程式可以使用預先設定的 CreateDefaultBuilder 預設值,使用便利的靜態方法初始化並啟動新的主機。 這些方法會啟動沒有主控台輸出的伺服器,並 WaitForShutdown 等候中斷 (Ctrl-C/SIGINT 或 SIGTERM) :

Start(RequestDelegate app)

使用 RequestDelegate 啟動:

using (var host = WebHost.Start(app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, RequestDelegate app)

使用 URL 和 RequestDelegate 來啟動:

using (var host = WebHost.Start("http://localhost:8080", app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

產生與 Start(RequestDelegate app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

Start(Action<IRouteBuilder> routeBuilder)

使用 IRouteBuilder (Microsoft.AspNetCore.Routing) 的執行個體來使用路由中介軟體:

using (var host = WebHost.Start(router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

使用下列瀏覽器要求與範例:

要求 回應
http://localhost:5000/hello/Martin Hello, Martin!
http://localhost:5000/buenosdias/Catrina Buenos dias, Catrina!
http://localhost:5000/throw/ooops! 擲回例外狀況,字串為 "ooops!"
http://localhost:5000/throw 擲回例外狀況,字串為 "Un oh!"
http://localhost:5000/Sante/Kevin Sante, Kevin!
http://localhost:5000 Hello World!

WaitForShutdown 會封鎖,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM)。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, Action<IRouteBuilder> routeBuilder)

使用 URL 和 IRouteBuilder 的執行個體:

using (var host = WebHost.Start("http://localhost:8080", router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 Start(Action<IRouteBuilder> routeBuilder) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

StartWith(Action<IApplicationBuilder> app)

提供委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith(app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

StartWith(string url, Action<IApplicationBuilder> app)

提供 URL 和委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith("http://localhost:8080", app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 StartWith(Action<IApplicationBuilder> app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

IWebHostEnvironment 介面

介面 IWebHostEnvironment 提供應用程式 Web 裝載環境的相關資訊。 使用建構函式插入以取得 IWebHostEnvironment,才能使用其屬性和擴充方法:

public class CustomFileReader
{
    private readonly IWebHostEnvironment _env;

    public CustomFileReader(IWebHostEnvironment env)
    {
        _env = env;
    }

    public string ReadFile(string filePath)
    {
        var fileProvider = _env.WebRootFileProvider;
        // Process the file here
    }
}

以慣例為基礎的方法可用來根據環境在啟動時設定應用程式。 或者,將 IWebHostEnvironment 插入至 Startup 建構函式,以便用於 ConfigureServices

public class Startup
{
    public Startup(IWebHostEnvironment env)
    {
        HostingEnvironment = env;
    }

    public IWebHostEnvironment HostingEnvironment { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        if (HostingEnvironment.IsDevelopment())
        {
            // Development configuration
        }
        else
        {
            // Staging/Production configuration
        }

        var contentRootPath = HostingEnvironment.ContentRootPath;
    }
}

注意

除了 IsDevelopment 擴充方法,IWebHostEnvironment 也提供 IsStagingIsProductionIsEnvironment(string environmentName) 方法。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

IWebHostEnvironment 服務也可直接插入至 Configure 方法,以便設定處理管線:

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // In Development, use the Developer Exception Page
        app.UseDeveloperExceptionPage();
    }
    else
    {
        // In Staging/Production, route exceptions to /error
        app.UseExceptionHandler("/error");
    }

    var contentRootPath = env.ContentRootPath;
}

建立自訂中介軟體時,IWebHostEnvironment 可以插入至 Invoke 方法:

public async Task Invoke(HttpContext context, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // Configure middleware for Development
    }
    else
    {
        // Configure middleware for Staging/Production
    }

    var contentRootPath = env.ContentRootPath;
}

IHostApplicationLifetime 介面

IHostApplicationLifetime 允許啟動後和關機活動。 在介面上的三個屬性是用來註冊定義啟動和關閉事件之 Action 方法的取消語彙基元。

取消權杖 觸發時機...
ApplicationStarted 已完全啟動主機。
ApplicationStopped 主機正在完成正常關機程序。 應該處理所有要求。 關機封鎖,直到完成此事件。
ApplicationStopping 主機正在執行正常關機程序。 可能仍在處理要求。 關機封鎖,直到完成此事件。
public class Startup
{
    public void Configure(IApplicationBuilder app, IHostApplicationLifetime appLifetime)
    {
        appLifetime.ApplicationStarted.Register(OnStarted);
        appLifetime.ApplicationStopping.Register(OnStopping);
        appLifetime.ApplicationStopped.Register(OnStopped);

        Console.CancelKeyPress += (sender, eventArgs) =>
        {
            appLifetime.StopApplication();
            // Don't terminate the process immediately, wait for the Main thread to exit gracefully.
            eventArgs.Cancel = true;
        };
    }

    private void OnStarted()
    {
        // Perform post-startup activities here
    }

    private void OnStopping()
    {
        // Perform on-stopping activities here
    }

    private void OnStopped()
    {
        // Perform post-stopped activities here
    }
}

StopApplication 會要求應用程式終止。 當呼叫類別的 Shutdown 方法時,下列類別使用 StopApplication 來順利關閉應用程式:

public class MyClass
{
    private readonly IHostApplicationLifetime _appLifetime;

    public MyClass(IHostApplicationLifetime appLifetime)
    {
        _appLifetime = appLifetime;
    }

    public void Shutdown()
    {
        _appLifetime.StopApplication();
    }
}

範圍驗證

CreateDefaultBuilder 如果應用程式的環境是 [開發],則會設定 ServiceProviderOptions.ValidateScopestrue

ValidateScopes 設定為 true 時,預設服務提供者會執行檢查以確認:

  • 範圍服務不是直接或間接由開機服務提供者解析。
  • 範圍服務不是直接或間接插入至單一服務。

根服務提供者會在呼叫 BuildServiceProvider 時建立。 當提供者啟動應用程式時,根服務提供者的存留期與應用程式/伺服器的存留期一致,並會在應用程式關閉時處置。

範圍服務會由建立這些服務的容器處置。 若是在根容器中建立範圍服務,因為當應用程式/伺服器關機時,服務只會由根容器處理,所以服務的存留期會提升為單一服務等級。 當呼叫 BuildServiceProvider 時,驗證服務範圍會攔截到這些情況。

若要一律驗證範圍,包括生產環境中, ServiceProviderOptionsUseDefaultServiceProvider 請在主機產生器上使用 設定 :

WebHost.CreateDefaultBuilder(args)
    .UseDefaultServiceProvider((context, options) => {
        options.ValidateScopes = true;
    })

其他資源

ASP.NET Core 應用程式會設定並啟動「主機」。 主機負責應用程式啟動和存留期管理。 至少,主機會設定伺服器和要求處理管線。 主機也可以設定記錄、相依性插入和設定。

此文章涵蓋 Web 主機,而且我們僅因為回溯相容性而繼續提供它。 ASP.NET Core範本會建立.NET 泛型主機,建議用於所有應用程式類型。

設定主機

使用 的 IWebHostBuilder 實例建立主機。 這通常在應用程式的進入點執行,也就是 Main 方法。

在專案範本中, Main 位於 Program.cs 。 一般應用程式呼叫 CreateDefaultBuilder 以開始設定主機:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
        WebHost.CreateDefaultBuilder(args)
            .UseStartup<Startup>();
}

呼叫 CreateDefaultBuilder 的程式碼位於名為 CreateWebHostBuilder 的方法中,這將它與 Main 中呼叫產生器物件上之 Run 的方法分開。 若您使用e Entity Framework Core 工具,則此分開是必要的。 工具預期找到它們可以在設計階段呼叫的 CreateWebHostBuilder 方法,以在不執行應用程式的情況下設定主機。 替代方式是實作 IDesignTimeDbContextFactory。 如需詳細資訊,請參閱設計階段 DbContext 建立

CreateDefaultBuilder 會執行下列工作:

CreateDefaultBuilder 定義的組態可以由 、 ConfigureLogging 和其他方法和擴充方法 IWebHostBuilder 覆寫和增強 ConfigureAppConfiguration 。 數個範例如下:

  • ConfigureAppConfiguration 用於指定應用程式的其他 IConfiguration 專案。 下列 ConfigureAppConfiguration 呼叫會新增委派,以在檔案中包含 appsettings.xml 應用程式組態。 可能會多次呼叫 ConfigureAppConfiguration。 請注意,此組態不適用於主機 (例如,伺服器 URL 或環境)。 請參閱主機組態值一節。

    WebHost.CreateDefaultBuilder(args)
        .ConfigureAppConfiguration((hostingContext, config) =>
        {
            config.AddXmlFile("appsettings.xml", optional: true, reloadOnChange: true);
        })
        ...
    
  • 下列 ConfigureLogging 呼叫會新增委派,將最小記錄層級 (SetMinimumLevel) 設定為 LogLevel.Warning 。 此設定會覆寫 (appsettings.Development.jsonLogLevel.Debug) appsettings.Production.json 和 (LogLevel.Error) 所設定的 CreateDefaultBuilder 設定。 可能會多次呼叫 ConfigureLogging

    WebHost.CreateDefaultBuilder(args)
        .ConfigureLogging(logging => 
        {
            logging.SetMinimumLevel(LogLevel.Warning);
        })
        ...
    
  • 下列呼叫會 ConfigureKestrel 覆寫 在 設定時 KestrelCreateDefaultBuilder 所建立的預設Limits.MaxRequestBodySize為 30,000,000 個位元組:

    WebHost.CreateDefaultBuilder(args)
        .ConfigureKestrel((context, options) =>
        {
            options.Limits.MaxRequestBodySize = 20000000;
        });
    

「內容根目錄」會決定主機搜尋內容檔案 (例如 MVC 檢視檔案) 的位置。 從專案的根資料夾啟動應用程式時,會使用專案的根資料夾作為內容根目錄。 這是 Visual Studiodotnet 新範本中使用的預設值。

如需應用程式設定的詳細資訊,請參閱 ASP.NET Core 中的組態

注意

除了使用靜態 CreateDefaultBuilder 方法,從 WebHostBuilder 建立主機是支援使用 ASP.NET Core 2.x 的方法。

設定主機時, Configure 可以提供 和 ConfigureServices 方法。 如果指定 Startup 類別,它必須定義 Configure 方法。 如需詳細資訊,請參閱 ASP.NET Core 中的應用程式啟動。 多次呼叫 ConfigureServices 會彼此附加。 對 WebHostBuilder 多次呼叫 ConfigureUseStartup 則會取代先前的設定。

主機組態值

WebHostBuilder 依賴下列方法來設定主機組態值:

  • 主機建立器組態,其中包含 ASPNETCORE_{configurationKey} 格式的環境變數。 例如: ASPNETCORE_ENVIRONMENT
  • 和 等 UseContentRoot 擴充 UseConfiguration 功能 (請參閱覆 寫組態 一節) 。
  • UseSetting 和相關聯的索引鍵。 使用 UseSetting 設定值時,此值會設定為字串,而不論其類型為何。

主機使用設定最後一個值的任何選項。 如需詳細資訊,請參閱下一節的覆寫組態

應用程式索引鍵 (名稱)

IWebHostEnvironment.ApplicationName 主機建構期間呼叫 或 ConfigureUseStartup ,會自動設定 屬性。 該值會設定為包含應用程式進入點的組件名稱。 若要明確設定值,請使用 WebHostDefaults.ApplicationKey

索引鍵:applicationName
類型字串
預設:包含應用程式進入點的組件名稱。
使用下列專案設定UseSetting
環境變數ASPNETCORE_APPLICATIONNAME

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.ApplicationKey, "CustomApplicationName")

擷取啟動錯誤

此設定會控制啟動錯誤的擷取。

索引鍵:captureStartupErrors
類型bool (true1)
預設值:除非 false 應用程式在 Kestrel IIS 後方執行,否則預設為 true
使用下列專案設定CaptureStartupErrors
環境變數ASPNETCORE_CAPTURESTARTUPERRORS

當它為 false 時,啟動期間發生的錯誤會導致主機結束。 當它為 true 時,主機會擷取啟動期間的例外狀況,並嘗試啟動伺服器。

WebHost.CreateDefaultBuilder(args)
    .CaptureStartupErrors(true)

內容根目錄

此設定會決定 ASP.NET Core開始搜尋內容檔案的位置。

索引鍵:contentRoot
類型字串
預設值:預設為應用程式組件所在的資料夾。
使用下列專案設定UseContentRoot
環境變數ASPNETCORE_CONTENTROOT

內容根目錄也會做為 Web 根目錄的基底路徑。 如果內容根路徑不存在,主機將無法啟動。

WebHost.CreateDefaultBuilder(args)
    .UseContentRoot("c:\\<content-root>")

如需詳細資訊,請參閱

詳細錯誤

決定是否應該擷取詳細的錯誤。

索引鍵:detailedErrors
類型bool (true1)
預設值:false
使用下列專案設定UseSetting
環境變數ASPNETCORE_DETAILEDERRORS

啟用時 (或當 Environment 設定為 Development 時),應用程式會擷取詳細例外狀況。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.DetailedErrorsKey, "true")

環境

設定應用程式的環境。

索引鍵:environment
類型字串
預設值:Production
使用下列專案進行設定UseEnvironment
環境變數ASPNETCORE_ENVIRONMENT

環境可以設定為任何值。 架構定義的值包括 DevelopmentStagingProduction。 值不區分大小寫。 根據預設,Environment 是從 ASPNETCORE_ENVIRONMENT 環境變數讀取。 使用 Visual Studio時,可以在 檔案中 launchSettings.json 設定環境變數。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

WebHost.CreateDefaultBuilder(args)
    .UseEnvironment(EnvironmentName.Development)

裝載啟動組件

設定應用程式的裝載啟動組件。

索引鍵:hostingStartupAssemblies
類型字串
預設值:空字串
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPASSEMBLIES

在啟動時載入的裝載啟動組件字串,以分號分隔。

雖然設定值會預設為空字串,但裝載啟動組件一律會包含應用程式的組件。 提供裝載啟動組件時,它們會新增至應用程式的組件,以便在應用程式在啟動時建置其通用服務時載入。

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupAssembliesKey, "assembly1;assembly2")

HTTPS 連接埠

設定 HTTPS 重新導向連接埠。 用於強制 HTTPS

機碼:HTTPs_port
類型字串
預設值:未設定預設值。
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HTTPS_PORT

WebHost.CreateDefaultBuilder(args)
    .UseSetting("https_port", "8080")

裝載啟動排除組件

在啟動時排除以分號分隔的裝載啟動組件字串。

索引鍵:hostingStartupExcludeAssemblies
類型字串
預設值:空字串
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_HOSTINGSTARTUPEXCLUDEASSEMBLIES

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.HostingStartupExcludeAssembliesKey, "assembly1;assembly2")

偏好裝載 URL

表示主機是否應接聽使用 WebHostBuilder 設定的 URL,而不是 IServer 實作所設定的 URL。

索引鍵:preferHostingUrls
類型bool (true1)
預設值:true
使用下列專案進行設定PreferHostingUrls
環境變數ASPNETCORE_PREFERHOSTINGURLS

WebHost.CreateDefaultBuilder(args)
    .PreferHostingUrls(false)

防止裝載啟動

可防止自動載入裝載啟動組件,包括應用程式組件所設定的裝載啟動組件。 如需詳細資訊,請參閱在 ASP.NET Core 中使用裝載啟動組件 (部分機器翻譯)。

索引鍵preventHostingStartup
類型bool (true1)
預設值:false
使用下列專案進行設定UseSetting
環境變數ASPNETCORE_PREVENTHOSTINGSTARTUP

WebHost.CreateDefaultBuilder(args)
    .UseSetting(WebHostDefaults.PreventHostingStartupKey, "true")

伺服器 URL

表示伺服器應該接聽要求的 IP 位址或主機位址,以及連接埠和通訊協定。

索引鍵:urls
類型字串
預設:http://localhost:5000
使用下列專案進行設定UseUrls
環境變數ASPNETCORE_URLS

設定為伺服器應該回應的 URL 前置清單,並以分號 (;) 分隔。 例如: http://localhost:123 。 使用 「*」 表示伺服器應該使用指定的埠和通訊協定接聽任何 IP 位址或主機名稱的要求,例如 () http://*:5000 。 通訊協定 (http://https://) 必須包含在每個 URL 中。 支援的格式會依伺服器而有所不同。

WebHost.CreateDefaultBuilder(args)
    .UseUrls("http://*:5000;http://localhost:5001;https://hostname:5002")

Kestrel 有自己的端點組態 API。 如需詳細資訊,請參閱Kestrel ASP.NET Core 中的網頁伺服器

關機逾時

指定等待 Web 主機關機的時間長度。

索引鍵:shutdownTimeoutSeconds
類型int
預設值:5
使用下列專案進行設定UseShutdownTimeout
環境變數ASPNETCORE_SHUTDOWNTIMEOUTSECONDS

雖然索引鍵接受 intUseSetting (例如 .UseSetting(WebHostDefaults.ShutdownTimeoutKey, "10")),UseShutdownTimeout 擴充方法會採用 TimeSpan

在逾時期間,裝載會:

如果在所有的託管服務停止之前逾時期限已到期,則應用程式關閉時,會停止任何剩餘的作用中服務。 即使服務尚未完成處理也會停止。 如果服務需要更多時間才能停止,請增加逾時。

WebHost.CreateDefaultBuilder(args)
    .UseShutdownTimeout(TimeSpan.FromSeconds(10))

啟動組件

決定要搜尋 Startup 類別的組件。

索引鍵:startupAssembly
類型字串
預設值:應用程式的組件
使用下列專案進行設定UseStartup
環境變數ASPNETCORE_STARTUPASSEMBLY

可以參考依名稱 (string) 或類型 (TStartup) 的組件。 如果呼叫多個 UseStartup 方法,最後一個將會優先。

WebHost.CreateDefaultBuilder(args)
    .UseStartup("StartupAssemblyName")
WebHost.CreateDefaultBuilder(args)
    .UseStartup<TStartup>()

Web 根目錄

設定應用程式靜態資產的相對路徑。

索引鍵:webroot
類型字串
預設值:預設值為 wwwroot{content root}/wwwroot的路徑必須存在。 如果路徑不存在,則會使用無作業檔案提供者。
使用下列專案進行設定UseWebRoot
環境變數ASPNETCORE_WEBROOT

WebHost.CreateDefaultBuilder(args)
    .UseWebRoot("public")

如需詳細資訊,請參閱

覆寫組態

使用 Configuration 來設定 Web 主機。 在下列範例中,會選擇性地在檔案中 hostsettings.json 指定主機組態。 從 hostsettings.json 檔案載入的任何組態,都可以由命令列引數覆寫。 組建組態 (在 config 中) 用以使用 UseConfiguration 來設定主機。 IWebHostBuilder 組態會新增至應用程式的組態,但相反的不是 true, ConfigureAppConfiguration 不會影響設定 IWebHostBuilder

以 config first、命令列引數 config second 覆寫 所提供的 UseUrlshostsettings.json 組態:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args)
    {
        var config = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("hostsettings.json", optional: true)
            .AddCommandLine(args)
            .Build();

        return WebHost.CreateDefaultBuilder(args)
            .UseUrls("http://*:5000")
            .UseConfiguration(config)
            .Configure(app =>
            {
                app.Run(context => 
                    context.Response.WriteAsync("Hello, World!"));
            });
    }
}

hostsettings.json:

{
    urls: "http://*:5005"
}

注意

UseConfiguration 只會將索引鍵從提供的 IConfiguration 複製到主機建立器的組態。 因此,ON JS 、INI 和 XML 設定檔的設定 reloadOnChange: true 沒有任何作用。

若要指定主機在特定 URL 上執行,所要的值可以在執行 dotnet run 時從命令提示字元傳入。 命令列引數會 urls 覆寫檔案中的 hostsettings.json 值,而伺服器會接聽埠 8080:

dotnet run --urls "http://*:8080"

管理主機

執行

Run 方法會啟動 Web 應用程式,並且封鎖呼叫執行緒,直到主機關閉為止:

host.Run();

開始

藉由呼叫 Start 方法,以非封鎖方式執行主機:

using (host)
{
    host.Start();
    Console.ReadLine();
}

如果 URL 的清單傳遞至 Start 方法,它會接聽指定的 URL:

var urls = new List<string>()
{
    "http://*:5000",
    "http://localhost:5001"
};

var host = new WebHostBuilder()
    .UseKestrel()
    .UseStartup<Startup>()
    .Start(urls.ToArray());

using (host)
{
    Console.ReadLine();
}

應用程式可以使用預先設定的 CreateDefaultBuilder 預設值,使用便利的靜態方法初始化並啟動新的主機。 這些方法會啟動不含主控台輸出的伺服器,並 WaitForShutdown 等候中斷 (Ctrl-C/SIGINT 或 SIGTERM) :

Start(RequestDelegate app)

使用 RequestDelegate 啟動:

using (var host = WebHost.Start(app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, RequestDelegate app)

使用 URL 和 RequestDelegate 來啟動:

using (var host = WebHost.Start("http://localhost:8080", app => app.Response.WriteAsync("Hello, World!")))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

產生與 Start(RequestDelegate app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

Start(Action<IRouteBuilder> routeBuilder)

使用 IRouteBuilder (Microsoft.AspNetCore.Routing) 的執行個體來使用路由中介軟體:

using (var host = WebHost.Start(router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shutdown the host...");
    host.WaitForShutdown();
}

使用下列瀏覽器要求與範例:

要求 回應
http://localhost:5000/hello/Martin Hello, Martin!
http://localhost:5000/buenosdias/Catrina Buenos dias, Catrina!
http://localhost:5000/throw/ooops! 擲回例外狀況,字串為 "ooops!"
http://localhost:5000/throw 擲回例外狀況,字串為 "Un oh!"
http://localhost:5000/Sante/Kevin Sante, Kevin!
http://localhost:5000 Hello World!

WaitForShutdown 會封鎖,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM)。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

Start(string url, Action<IRouteBuilder> routeBuilder)

使用 URL 和 IRouteBuilder 的執行個體:

using (var host = WebHost.Start("http://localhost:8080", router => router
    .MapGet("hello/{name}", (req, res, data) => 
        res.WriteAsync($"Hello, {data.Values["name"]}!"))
    .MapGet("buenosdias/{name}", (req, res, data) => 
        res.WriteAsync($"Buenos dias, {data.Values["name"]}!"))
    .MapGet("throw/{message?}", (req, res, data) => 
        throw new Exception((string)data.Values["message"] ?? "Uh oh!"))
    .MapGet("{greeting}/{name}", (req, res, data) => 
        res.WriteAsync($"{data.Values["greeting"]}, {data.Values["name"]}!"))
    .MapGet("", (req, res, data) => res.WriteAsync("Hello, World!"))))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 Start(Action<IRouteBuilder> routeBuilder) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

StartWith(Action<IApplicationBuilder> app)

提供委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith(app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

在瀏覽器中提出要求, http://localhost:5000 以接收回應 「Hello World!」 WaitForShutdown 區塊,直到發出中斷 (Ctrl-C/SIGINT 或 SIGTERM) 為止。 應用程式會顯示 Console.WriteLine 訊息並等候按鍵動作以便結束。

StartWith(string url, Action<IApplicationBuilder> app)

提供 URL 和委派以設定 IApplicationBuilder

using (var host = WebHost.StartWith("http://localhost:8080", app => 
    app.Use(next => 
    {
        return async context => 
        {
            await context.Response.WriteAsync("Hello World!");
        };
    })))
{
    Console.WriteLine("Use Ctrl-C to shut down the host...");
    host.WaitForShutdown();
}

產生與 StartWith(Action<IApplicationBuilder> app) 相同的結果,除了應用程式會在 http://localhost:8080 回應。

IWebHostEnvironment 介面

介面 IWebHostEnvironment 提供應用程式 Web 裝載環境的相關資訊。 使用建構函式插入以取得 IWebHostEnvironment,才能使用其屬性和擴充方法:

public class CustomFileReader
{
    private readonly IWebHostEnvironment _env;

    public CustomFileReader(IWebHostEnvironment env)
    {
        _env = env;
    }

    public string ReadFile(string filePath)
    {
        var fileProvider = _env.WebRootFileProvider;
        // Process the file here
    }
}

以慣例為基礎的方法可用來根據環境在啟動時設定應用程式。 或者,將 IWebHostEnvironment 插入至 Startup 建構函式,以便用於 ConfigureServices

public class Startup
{
    public Startup(IWebHostEnvironment env)
    {
        HostingEnvironment = env;
    }

    public IWebHostEnvironment HostingEnvironment { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        if (HostingEnvironment.IsDevelopment())
        {
            // Development configuration
        }
        else
        {
            // Staging/Production configuration
        }

        var contentRootPath = HostingEnvironment.ContentRootPath;
    }
}

注意

除了 IsDevelopment 擴充方法,IWebHostEnvironment 也提供 IsStagingIsProductionIsEnvironment(string environmentName) 方法。 如需詳細資訊,請參閱在 ASP.NET Core 中使用多個環境 (部分機器翻譯)。

IWebHostEnvironment 服務也可直接插入至 Configure 方法,以便設定處理管線:

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // In Development, use the Developer Exception Page
        app.UseDeveloperExceptionPage();
    }
    else
    {
        // In Staging/Production, route exceptions to /error
        app.UseExceptionHandler("/error");
    }

    var contentRootPath = env.ContentRootPath;
}

建立自訂中介軟體時,IWebHostEnvironment 可以插入至 Invoke 方法:

public async Task Invoke(HttpContext context, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        // Configure middleware for Development
    }
    else
    {
        // Configure middleware for Staging/Production
    }

    var contentRootPath = env.ContentRootPath;
}

IHostApplicationLifetime 介面

IHostApplicationLifetime 允許啟動後和關機活動。 在介面上的三個屬性是用來註冊定義啟動和關閉事件之 Action 方法的取消語彙基元。

取消權杖 觸發時機...
ApplicationStarted 已完全啟動主機。
ApplicationStopped 主機正在完成正常關機程序。 應該處理所有要求。 關機封鎖,直到完成此事件。
ApplicationStopping 主機正在執行正常關機程序。 可能仍在處理要求。 關機封鎖,直到完成此事件。
public class Startup
{
    public void Configure(IApplicationBuilder app, IHostApplicationLifetime appLifetime)
    {
        appLifetime.ApplicationStarted.Register(OnStarted);
        appLifetime.ApplicationStopping.Register(OnStopping);
        appLifetime.ApplicationStopped.Register(OnStopped);

        Console.CancelKeyPress += (sender, eventArgs) =>
        {
            appLifetime.StopApplication();
            // Don't terminate the process immediately, wait for the Main thread to exit gracefully.
            eventArgs.Cancel = true;
        };
    }

    private void OnStarted()
    {
        // Perform post-startup activities here
    }

    private void OnStopping()
    {
        // Perform on-stopping activities here
    }

    private void OnStopped()
    {
        // Perform post-stopped activities here
    }
}

StopApplication 會要求應用程式終止。 當呼叫類別的 Shutdown 方法時,下列類別使用 StopApplication 來順利關閉應用程式:

public class MyClass
{
    private readonly IHostApplicationLifetime _appLifetime;

    public MyClass(IHostApplicationLifetime appLifetime)
    {
        _appLifetime = appLifetime;
    }

    public void Shutdown()
    {
        _appLifetime.StopApplication();
    }
}

範圍驗證

CreateDefaultBuildertrue如果應用程式的環境為 [開發],則會設定 ServiceProviderOptions.ValidateScopes 為 。

ValidateScopes 設定為 true 時,預設服務提供者會執行檢查以確認:

  • 範圍服務不是直接或間接由開機服務提供者解析。
  • 範圍服務不是直接或間接插入至單一服務。

根服務提供者會在呼叫 BuildServiceProvider 時建立。 當提供者啟動應用程式時,根服務提供者的存留期與應用程式/伺服器的存留期一致,並會在應用程式關閉時處置。

範圍服務會由建立這些服務的容器處置。 若是在根容器中建立範圍服務,因為當應用程式/伺服器關機時,服務只會由根容器處理,所以服務的存留期會提升為單一服務等級。 當呼叫 BuildServiceProvider 時,驗證服務範圍會攔截到這些情況。

若要一律驗證範圍,包括生產環境中, ServiceProviderOptionsUseDefaultServiceProvider 請在主機產生器上使用 設定 :

WebHost.CreateDefaultBuilder(args)
    .UseDefaultServiceProvider((context, options) => {
        options.ValidateScopes = true;
    })

其他資源