Как я могу перезапустить приложение в ядре asp.net программно?
Я хочу очистить кеш и заставить приложение повторно вводить запуск.
Как я могу перезапустить приложение в ядре asp.net программно?
Я хочу очистить кеш и заставить приложение повторно вводить запуск.
.NET Core 2
Может наступить время, когда вы захотите принудительно перезапустить ваш сайт ASP.Net Core 2 программным способом. Даже в дни MVC/WebForms это не было рекомендуемой практикой, но, увы, есть способ. ASP.Net Core 2 позволяет IApplicationLifetime
объект IApplicationLifetime
, который позволит вам сделать несколько полезных вещей. Во-первых, он позволит вам регистрировать события для запуска, выключения и выключения, аналогичные тем, которые могли быть доступны через Global.asax
в тот день. Но он также предоставляет метод, позволяющий вам закрыть сайт (без взлома!). Вам нужно будет вставить это на свой сайт, а затем просто позвонить. Ниже приведен пример контроллера с маршрутом, который отключит сайт.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Mvc;
namespace MySite.Controllers
{
public class WebServicesController : Controller
{
private IApplicationLifetime ApplicationLifetime { get; set; }
public WebServicesController(IApplicationLifetime appLifetime)
{
ApplicationLifetime = appLifetime;
}
public async Task ShutdownSite()
{
ApplicationLifetime.StopApplication();
return "Done";
}
}
}
Источник: http://www.blakepell.com/asp-net-core-ability-to-restart-your-site-programatics-updated-for-2-0
Обновление: Mirask ответ является более правильным для .NET Core 2.
В Program.cs вы увидите вызов host.Run()
. Этот метод имеет перегрузку, которая принимает System.Threading.CancellationToken
. Это то, что я делаю:
public class Program {
private static CancellationTokenSource cancelTokenSource = new System.Threading.CancellationTokenSource();
public static void Main(string[] args) {
var host = new WebHostBuilder()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.UseIISIntegration()
.UseStartup<Startup>()
.Build();
host.Run(cancelTokenSource.Token);
}
public static void Shutdown() {
cancelTokenSource.Cancel();
}
}
Затем в моем контроллере я могу вызвать Program.Shutdown()
и через несколько секунд приложение умирает. Если он находится за IIS, другой запрос автоматически запустит приложение.
Если вам это нужно только для сценария разработки, вы можете использовать dotnet-watch (для dotnet) или dnx-watch (для dnx).
Если вы хотите, чтобы ваше приложение перезапускалось на производстве, вам нужно реализовать что-то похожее на то, что делает наблюдатель. Вам нужен внешний процесс, чтобы убить и перезапустить процесс. Или вам нужно приложение, чтобы запустить экземпляр самого себя, а затем убить себя. К сожалению, для этого нечего делать.
Для .NET Core 2.2 вы можете использовать следующий код:
using Microsoft.AspNetCore;
using Microsoft.AspNetCore.Hosting;
using System.Threading;
namespace BuildMonitor
{
public class Program
{
private static CancellationTokenSource cancelTokenSource = new System.Threading.CancellationTokenSource();
public static void Main(string[] args)
{
var host = CreateWebHostBuilder(args).Build();
host.RunAsync(cancelTokenSource.Token).GetAwaiter().GetResult();
}
public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>();
public static void Shutdown()
{
cancelTokenSource.Cancel();
}
}
}
А отключение сервера может быть размещено, например, за какой-то веб-страницей:
using System;
using Microsoft.AspNetCore.Mvc.RazorPages;
namespace BuildMonitor.Pages
{
public class StopServerModel : PageModel
{
public void OnGet()
{
Console.WriteLine("Forcing server shutdown.");
Program.Shutdown();
}
}
}
Например, stopServer.bat может быть таким:
@echo off
rem curl http://localhost:5000/StopServer >nul 2>&1
powershell.exe -Command (new-object System.Net.WebClient).DownloadString('http://localhost:5000/StopServer') >nul
exit /b 0
Ничто из вышеперечисленного не сработало для меня. Я застрял после первого неудачного запуска. Возможно, потому что мое приложение asp.net core 2.0 размещено внутри IIS. Мне пришлось установить AppPool "AlwaysRunning" и поместить миграции в блок try - catch; Теперь, когда SQL-сервер не работает, приложение закрывается, и каждый запрос запускает приложение снова.
public void Configure(IApplicationBuilder app,
IHostingEnvironment env)
{
// Some middleware stuff, etc...
try {
// ... db migrations and other stuff that can break startup
} catch (Exception ex) {
// log exception
Environment.Exit(-1);
}
}