据我所知,RC2支持在Windows Services中托管应用程序。我尝试在一个简单的web项目上测试它(使用.NET框架4.6.1)。
下面是我的Program.cs代码:
using System;
using System.IO;
using System.Linq;
using System.ServiceProcess;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Hosting.WindowsServices;
namespace WebApplication4
{
public class Program : ServiceBase
{
public static void Main(string[] args)
{
if (args.Contains("--windows-service"))
{
Run(new Program());
return;
}
var program = new Program();
program.OnStart(null);
Console.ReadLine();
program.OnStop();
}
protected override void OnStart(string[] args)
{
var host = new WebHostBuilder()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.UseStartup<Startup>()
.Build();
host.RunAsService();
}
protected override void OnStop() {}
}
}所有其他东西基本上都来自.NET核心模板(尽管我将框架改为net461,并在project.json中添加了一些依赖项)。
在用dotnet publish发布它并用sc create创建Windows service之后,我可以成功地启动我的服务,但我无法连接到我的任何控制器(端口没有列出)。我想我做错了什么。
所以我猜主要的问题是如何制作自托管web api并将其作为Windows服务运行。所有找到的解决方案在RC2更新后都不起作用。
发布于 2016-05-26 22:41:58
这里有几个选择--使用微软的WebHostService类、继承WebHostService或编写自己的类。后者的原因是,使用微软的实现,我们不能编写带有继承WebHostService的类型参数的泛型扩展方法,因为这个类不包含无参数构造函数,也不能访问服务定位器。
使用WebHostService
在本例中,我将创建一个控制台应用程序,它使用Microsoft.DotNet.Web.targets,输出一个.exe,并作为MVC应用程序(视图、控制器等)运行。我假设创建控制台应用程序,更改.xproj中的目标,修改project.json以具有适当的发布选项,以及从标准.NET核心web应用程序模板复制视图、控制器和webroot -都很简单。
现在最重要的部分是:
System.Diagnostics.Process.GetCurrentProcess().MainModule.FileName;= Path.GetDirectoryName(exePath);var exePath= = WebHostBuilder() .UseKestrel() .UseContentRoot( directoryPath ) .UseStartup() .Build();if (Debugger.IsAttached || args.Contains("--debug")) { host.Run();} else { host.RunAsService();} }
现在可以使用以下命令轻松安装.exe
sc create MyService binPath = "Full\Path\To\The\Console\file.exe"一旦服务启动,web应用程序就会被托管,并成功地找到并呈现它的视图。
继承WebHostService
这种方法的一个主要好处是,它允许我们覆盖OnStopping、OnStarting和OnStarted方法。
假设下面是我们的自定义类,它继承了WebHostService
internal class CustomWebHostService : WebHostService
{
public CustomWebHostService(IWebHost host) : base(host)
{
}
protected override void OnStarting(string[] args)
{
// Log
base.OnStarting(args);
}
protected override void OnStarted()
{
// More log
base.OnStarted();
}
protected override void OnStopping()
{
// Even more log
base.OnStopping();
}
}按照上面的步骤,我们必须写下我们自己的扩展方法,该方法使用我们的自定义类运行主机:
public static class CustomWebHostWindowsServiceExtensions
{
public static void RunAsCustomService(this IWebHost host)
{
var webHostService = new CustomWebHostService(host);
ServiceBase.Run(webHostService);
}
}与前面的入口点示例相比,唯一需要更改的行是最后的else语句,它必须调用正确的扩展方法
host.RunAsCustomService();最后,使用与上面相同的步骤安装服务。
sc create MyService binPath = "Full\Path\To\The\Console\file.exe"发布于 2016-10-29 23:03:55
如果可以只在完整的.NET框架上运行,那么前面的答案就足够了(继承自ServiceBase或使用微软的WebHostService)。
但是,如果你有/想要在.NET内核上运行(例如,在windows nano服务器上,作为普通应用程序和windows上的服务工作的单一二进制文件,或者需要与旧的.NET框架版本上的应用程序并行运行,所以你不能更新系统框架),你将不得不通过P/Invokes自己进行适当的windows API调用。因为我必须这样做,所以我创建了一个library that does exactly that。
当以管理权限(例如dotnet MyService.dll --register-as-service)运行时,也可以安装sample。
发布于 2017-05-24 17:31:55
您需要引用Microsoft.AspNetCore.Hosting和Microsoft.AspNetCore.Hosting.WindowsServices,并在启动类中使用以下代码,以使其可作为windows服务运行:
public static void Main(string[] args)
{
var host = new WebHostBuilder()
.UseIISIntegration()
.UseKestrel()
.UseContentRoot(@"Path\To\Content\Root")
.UseStartup<Startup>()
.Build();
if (Debugger.IsAttached || args.Contains("--debug"))
{
host.Run();
}
else
{
host.RunAsService();
}
}然后,您需要为IWebHost.RunAsService添加一个扩展方法,以便使用OnStopping和OnStarting事件处理程序将其包装在自定义WebHostService类中:
public static class MyWebHostServiceServiceExtensions
{
public static void RunAsMyService(this IWebHost host)
{
var webHostService = new MyWebHostService(host);
ServiceBase.Run(webHostService);
}
}
internal class MyWebHostService : WebHostService
{
public MyWebHostService(IWebHost host) : base(host)
{
}
protected override void OnStarting(string[] args)
{
base.OnStarting(args);
}
protected override void OnStarted()
{
base.OnStarted();
}
protected override void OnStopping()
{
base.OnStopping();
}
}这篇文章的How to host your ASP.NET Core in a Windows Service和评论涵盖了细节。
更新(在Quick summary of what’s new in ASP.NET Core 2.0中查看更多详细信息):
在ASP.NET Core 1.1中,我们有这样的东西:
public class Program
{
public static void Main(string[] args)
{
var host = new WebHostBuilder()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.UseIISIntegration()
.UseStartup<Startup>()
.Build();
host.Run();
}
}在ASP.NET Core 2.0中,它看起来像这样:
public class Program
{
public static void Main(string[] args)
{
BuildWebHost(args).Run();
}
public static IWebHost BuildWebHost(string[] args) =>
WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>()
.Build();
}https://stackoverflow.com/questions/37346383
复制相似问题