簡體   English   中英

多個 Worker 在 .NET 內核中並行運行

[英]Multiple Workers to run parallel-ly in .NET core

我在 .NET Core 中創建了一個 Worker Service 項目,目的是讓 3 個獨立的工作人員參與進來。 所有這 3 個工作人員應該並行運行並且獨立於其他工作人員。 這個工作服務作為一個整體將作為 Windows 服務運行。

在主 Program.cs 中,我注冊了 3 個工人,如下所示:

public static IHostBuilder CreateHostBuilder(string[] args) =>
            Host.CreateDefaultBuilder(args)
                .UseWindowsService()
                .ConfigureServices((hostContext, services) =>
                {
                    IConfiguration configuration = hostContext.Configuration;
                    services.AddHostedService<WorkerA>();
                    services.AddHostedService<WorkerB>();
                    services.AddHostedService<WorkerC>();
                });
    }

每個工作人員代碼如下,完成他們的預期工作:

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
     while (!stoppingToken.IsCancellationRequested)
     {
          WorkerA_DoWork();
          await Task.Delay(6000, stoppingToken);
     }
}

問題陳述:當我執行項目時,我遇到了一些問題,比如當 WorkerA() 沒有任何進程要運行時, WorkerB() (或) WorkerC() 沒有開始他們的工作。 我認為它基本上是在等待 WorkerA() 做某事,然后 WorkerB() 或 WorkerC() 才能開始做他們的工作。

請告知他們如何獨立工作,即:每個工人不應該等待其他工人,應該獨立運行。

當我執行項目時,我面臨一些問題,例如當 WorkerA() 沒有任何進程要運行時, WorkerB() (或) WorkerC() 不會開始他們的工作。 我認為它基本上是在等待 WorkerA() 做某事,然后 WorkerB() 或 WorkerC() 才能開始做他們的工作。

.NET Core 允許任意數量的托管服務; 但是,它開始連續執行它們。 所以這段代碼的問題是:

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
  while (!stoppingToken.IsCancellationRequested)
  {
    WorkerA_DoWork();
    await Task.Delay(6000, stoppingToken);
  }
}

WorkerA_DoWork是同步的。 即,它正在同步等待工作。

解決方案可以是兩件事之一。 要么使“獲取下一個工作項”方法異步:

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
  while (!stoppingToken.IsCancellationRequested)
  {
    await WorkerA_DoWorkAsync();
    await Task.Delay(6000, stoppingToken);
  }
}

或將整個ExecuteAsync包裝在Task.Run

protected override Task ExecuteAsync(CancellationToken stoppingToken) => Task.Run(async () =>
{
  while (!stoppingToken.IsCancellationRequested)
  {
    WorkerA_DoWork();
    await Task.Delay(6000, stoppingToken);
  }
});

遺憾的是,在 .net Core 中,您只需初始化 1 個 HostedService,這意味着只有第一個 inyected 將在后台運行。 一個可行的解決方案是創建一個 HostedService Wrapper,它初始化你的類:

public class Orchestrator: IHostedService
{
    private readonly WorkerA _workerA;
    private readonly WorkerB _workerB;

    public Orchestrator(WorkerA workerA, WorkerB workerB)
    {
        _workerA = workerA;
        _workerB = workerB;
    }
    #endregion

    public Task StartAsync(CancellationToken cancellationToken)
    {
        Task.Run(async () => await _workerA.StartAsync(cancellationToken));
        Task.Run(async () => await _workerB.StartAsync(cancellationToken));

        return Task.CompletedTask;
    }

    public Task StopAsync(CancellationToken cancellationToken)
    {
        return Task.WhenAll(StartAsync(cancellationToken));
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM