linux .net core 后台执行,.NET Core运行后台定时任务

现在的dotnet core中默认封装了实现IHostedService接口的基类BackgroundService,该类实现如下:

// Copyright (c) .NET Foundation. All rights reserved.

// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;

using System.Threading;

using System.Threading.Tasks;

namespace Microsoft.Extensions.Hosting

{

///

/// Base class for implementing a long running .

///

public abstract class BackgroundService : IHostedService, IDisposable

{

private Task _executingTask;

private readonly CancellationTokenSource _stoppingCts = new CancellationTokenSource();

///

/// This method is called when the starts. The implementation should return a task that represents

/// the lifetime of the long running operation(s) being performed.

///

/// Triggered when is called.

/// A that represents the long running operations.

protected abstract Task ExecuteAsync(CancellationToken stoppingToken);

///

/// Triggered when the application host is ready to start the service.

///

/// Indicates that the start process has been aborted.

public virtual Task StartAsync(CancellationToken cancellationToken)

{

// Store the task we're executing

_executingTask = ExecuteAsync(_stoppingCts.Token);

// If the task is completed then return it, this will bubble cancellation and failure to the caller

if (_executingTask.IsCompleted)

{

return _executingTask;

}

// Otherwise it's running

return Task.CompletedTask;

}

///

/// Triggered when the application host is performing a graceful shutdown.

///

/// Indicates that the shutdown process should no longer be graceful.

public virtual async Task StopAsync(CancellationToken cancellationToken)

{

// Stop called without start

if (_executingTask == null)

{

return;

}

try

{

// Signal cancellation to the executing method

_stoppingCts.Cancel();

}

finally

{

// Wait until the task completes or the stop token triggers

await Task.WhenAny(_executingTask, Task.Delay(Timeout.Infinite, cancellationToken));

}

}

public virtual void Dispose()

{

_stoppingCts.Cancel();

}

}

}

根据BackgroundService源码,我们只要实现该类的抽象方法ExecuteAsync即可。

可以有两种实现方式来做定时程序,第一种就是实现一个Timer:

using Microsoft.Extensions.Hosting;

using Microsoft.Extensions.Logging;

using System;

using System.IO;

using System.Threading;

using System.Threading.Tasks;

namespace DemoOne.Models

{

public class TimedBackgroundService : BackgroundService

{

private readonly ILogger _logger;

private Timer _timer;

public TimedBackgroundService(ILogger logger)

{

_logger = logger;

}

protected override async Task ExecuteAsync(CancellationToken stoppingToken)

{

_timer = new Timer(DoWork, null, TimeSpan.Zero, TimeSpan.FromSeconds(5));

_logger.LogInformation("周六!");

return Task.CompletedTask;

//Console.WriteLine("MyServiceA is starting.");

//stoppingToken.Register(() => File.Create($"E:\\dotnetCore\\Practice\\Practice\\{DateTime.Now.Millisecond}.txt"));

//while (!stoppingToken.IsCancellationRequested)

//{

// Console.WriteLine("MyServiceA 开始执行");

// await Task.Delay(TimeSpan.FromSeconds(5), stoppingToken);

// Console.WriteLine("继续执行");

//}

//Console.WriteLine("MyServiceA background task is stopping.");

}

private void DoWork(object state)

{

_logger.LogInformation($"Hello World! - {DateTime.Now}");

}

public override void Dispose()

{

base.Dispose();

_timer?.Dispose();

}

}

}

我们看看StartAsync的源码。上面的实现方式会直接返回一个已完成的Task,这样就会直接运行StartAsync方法的if判断,那么如果我们不走if呢?那么就应该由StartAsync方法返回一个已完成的Task.

第二个即是:

using Microsoft.Extensions.Hosting;

using Microsoft.Extensions.Logging;

using System;

using System.IO;

using System.Threading;

using System.Threading.Tasks;

namespace DemoOne.Models

{

public class TimedBackgroundService : BackgroundService

{

protected override async Task ExecuteAsync(CancellationToken stoppingToken)

{

Console.WriteLine("MyServiceA is starting.");

stoppingToken.Register(() => File.Create($"E:\\dotnetCore\\Practice\\Practice\\{DateTime.Now.Millisecond}.txt"));

while (!stoppingToken.IsCancellationRequested)

{

Console.WriteLine("MyServiceA 开始执行");

await Task.Delay(TimeSpan.FromSeconds(5), stoppingToken);

Console.WriteLine("继续执行");

}

Console.WriteLine("MyServiceA background task is stopping.");

}

public override void Dispose()

{

base.Dispose();

}

}

}

最后我们将实现了BackgroundService的类注入到DI即可:

services.AddHostedService();

dotnet core的Microsoft.Extensions.Hosting 组件中,充斥着类似IHostedService接口中定义的方法:StartAsync、StopAsync方法。我们注入的HostedService服务会在WebHost类中通过GetRequiredService获取到注入的定时服务。随后执行StartAsync方法开始执行。建议看看Hosting组件源码,会有很多的收获。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值