Supervisor守护DotNet Core控制台程序

Supervisor 相信对Linux系统很熟的都知道这个软件,基于Python写的一个守护进程软件。具体的介绍和使用我就不再赘述了。

使用asp.net core 部署在Linux常用的方法 我们可以用Docker、Jexus 、Supervisor等。具体应该使用哪个,因不同的软件都有各自的优缺点,根据自身应用的场景选择一个即可。

在使用Supervisor 部署asp.net core的时候通常我们只要在supervisord.d 目录中添加对应的配置文件如xxx.ini或xxx.conf。(具体目录位置和配置文件扩展名请根据supervisord.conf来进行配置约束。)

然后在配置文件command 后面写上**dotnet /data/web/webapi.dll **,然后通过 **supervisorctl start webapi **即可启动我们的web程序在后台运行。

当我们在DotNet Core中写一个后台程序,比如定时任务程序、MQ的消费者程序等。这样就没必要写成Web程序;在windows里我们可以写一个windows服务程序,直接在后台运行。但是DotNet Core我们只能写控制台程序了。

普通的控制台程序我们写好后放到Linux上直接运行没问题,但是如果使用supervisor 进行部署(部署方式同asp.net core一样),会发现 怎么也启动不了。

比如这样一个程序

Supervisor守护DotNet Core控制台程序
image

Linux上可以运行

Supervisor守护DotNet Core控制台程序
image

使用Supervisord部署添加一个配置文件

Supervisor守护DotNet Core控制台程序
image

使用supervisor运行

Supervisor守护DotNet Core控制台程序
image

出现错误不能成功运行,如果网上搜索 "supervisor Exited too quickly (process log may have details)”或按照supervisor日志里的错误信息搜索,多数会告诉你目录是否配置错误、目录是否有对应权限、dotnet 命令是否能正常运行等。

我们看看运行日志

Supervisor守护DotNet Core控制台程序
image

这样看是有运行,出现【控制台程序已经启动】多次说明我们的程序被Supervisor 多次重启了,在配置文件中startretries就是启动失败后重启次数。

我们可以通过tail -f /data/logs/apptest.log 查看日志有没有文件有没有继续持续输出我们打印的时间或者通过**ps -efl |grep dotnet **查看当前程序运行的进程是否存在,后者是最准确的。

不难发现我们本次是有运行 因为有启动日志,但是很快进程就会自动退出了。

为控制台程序添加宿主

在asp.net core中我们都知道有个WebHost

asp.net core 中的WebHost

Supervisor守护DotNet Core控制台程序
image

在控制台中我们需要添加HostBuilder来作为宿主。

通过Nuget 添加Microsoft.Extensions.Hosting

修改控制台的Main函数

{
    Console.WriteLine($"控制台程序已经启动:{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")}\r\n"); var hostBuilder = new HostBuilder()
   .ConfigureServices(serviceCollection => { //注册我们的服务接口
       serviceCollection.AddSingleton<IHostedService, MyService>();
   }); await hostBuilder.RunConsoleAsync();
}

一般情况Main函数改为异步后变异会报错,会提示找不到合适的静态入口;可以设置语言版本为C#7.1及以上来解决。

Supervisor守护DotNet Core控制台程序
image

我们需要添加一个服务文类用来继承我们的宿主IHostedService接口,并重写服务启动和结束方法。

class MyService : IHostedService
    { /// <summary>
        /// 服务启动 /// </summary>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public Task StartAsync(CancellationToken cancellationToken)
        { return Task.Run(() => {
                Console.WriteLine("控制台程序已经开启"); //模拟定时需要后台处理的任务
                new Task(() => { while (true)
                    {
                        Console.WriteLine("当前时间是:" + DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"));
                        Thread.Sleep(1000);
                    }
                }).Start();

            });
        } /// <summary>
        /// 服务停止 /// </summary>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public Task StopAsync(CancellationToken cancellationToken)
        { return Task.Run(() => {
                Console.WriteLine("控制台程序已经停止");
            });

       }
    }

发布然后使用supervisorctl start apptest 开启看看

Supervisor守护DotNet Core控制台程序
image
Supervisor守护DotNet Core控制台程序
好书推荐、视频分享,与您一起进步