c# - 开发将使用/创建多个线程的 C# Windows 服务需要专家意见

标签 c# multithreading threadpool async-await

我正在开发 c# windows 服务,它将监视多个文件、文件夹和数据库表的任何更改。观察者分为三种类型(我称它们为观察者)。

  1. FileWatcher:使用 .Net FileSystemWatcher 持续监视文件并引发要发送警报的事件。发送警报后, watch 功能恢复。

  2. FolderWatcher:使用 .Net Timer 持续监视文件夹,并引发一个事件,在特定条件下发送警报。发送警报后, watch 功能恢复。

  3. DBWatcher:每分钟(计时器)执行一次 SQL 查询,如果结果错误则发送警报。

你可以猜到这些all watchers会一直运行在windows服务运行的地方。

它们都实现了一个接口(interface)IWatcher并提供了一个方法BeginWatch来执行每个watcher所需的操作,例如使用计时器每分钟查询一次DB(如果watcher是数据库观察者)。创建这些观察器的输入是一个 XML 文件。它包含如下内容:

<?xml version="1.0" encoding="utf-8"?>
<watchlist>

    <watcher type="FolderWatcher">
        <path>D:\Projects\.Net\V1\</path>
        <PauseInMinBtwAlerts>1</PauseInMinBtwAlerts>
        <alert>xxx@xxx.com</alert>
    </watcher>

    <watcher type="FileWatcher">
        <path>D:\Projects\.Net\</path>
        <fileName>e.txt</fileName>
        <alert>yyy@yyy.com</alert>
    </watcher>

    <watcher type="DBWatcher">
        <sqlquery>select blah blah blah ... </sqlquery>
        <connectionstring>connection string for the DB</connectionstring>
        <alert>yyy@yyy.com</alert>
    </watcher>

</watchlist>

这个 XML 告诉我们要创建多少观察者。可以创建几十个观察者。

由于我们遇到的一些问题,我们决定每个观察者将在不同的线程上运行。因此,如果出现未处理的异常,只能停止/终止该线程,我们会通过电子邮件将情况通知 IT 部门。我们必须能够稍后恢复它。

现在我很困惑。因为有线程、异步任务、池线程、后台线程等。我应该使用什么???/我是这个线程的新手。

让我告诉你我的需求,然后你可以指导我找到一些合适的解决方案:

  1. 我希望每个观察者都在一个单独的线程中运行。
  2. 线程必须连续运行,我的观察者必须能够观察到 Windows 服务本身关闭。
  3. 线程必须能够与其父线程(创建每个线程的类)通信以更新其状态。
  4. 线程中任何未处理的异常都必须在线程本身中捕获,然后传达给父类(使用第 3 点)。

我创建了以下类,它将负责创建、通信和管理所有线程:

public class WatcherThreadsManager
{
    //This will keep list of all active threads ... as I will be communicating with them later
    private List<Thread> _watcherThreads;

    public WatcherThreadsManager()
    {
        this._watcherThreads = new List<Thread>();
    }

    //I will call this method and pass in any watcher which i want to run in a new thread
    public void CreateWatcherThread(IWatcher watcher)
    {
        Thread _watcher = new Thread(_createWatcherThread);

        //the Copy() will produce its deeply copied copy ... i wanted to make sure thread works on a free object .. not sure
        _watcher.Start(watcher.Copy());

        //Add Thread to threads' list
        this._watcherThreads.Add(_watcher);
    }

    private void _createWatcherThread(object wat)
    {
        IWatcher watcher = wat as IWatcher;
        try
        {
            //the following function will begin the watch.
            //I dont want any loop either .. as i want to call the BeginWatch() method only once.
            watcher.BeginWatch();
        }
        catch (Exception ex)
        {
            // i should be able to inform the parent thread about the exception so this thread is set to sleep. as we can reactivate it later when the issue fixes.
            // how to do that?
        }
    }
} 

实现我想要的目标的最佳方式是什么?

最佳答案

您可以通过使用 Tasks 实现您的所有要求,这里有几个链接供您进一步阅读:

  1. Creating threads - Task.Factory.StartNew vs new Thread()

  2. Best Practice LongRunning Task creation

  3. Task Report Progress

  4. Handling Task exceptions

祝你好运!

关于c# - 开发将使用/创建多个线程的 C# Windows 服务需要专家意见,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16361274/

相关文章:

c# outputcache 在 php 中等效?

java - 是否可以并行检查方法调用所花费的时间

java - 在 ECLIPSE 中运行并发 Java NIO 服务器 (Netty) 时,Java 运行时环境检测到 fatal error

c++ - c++11后台运行线程

multithreading - 什么是正确使用 Vala 线程池?

c# - 仅使用 'x' 前缀引起的神秘 404 路由错误?

c# - 控制台应用程序中的 .NET 全局异常处理程序

multithreading - 有关 OSGi 中的线程数的信息

c# - 使用 Windows 身份验证连接到 SQL Server

Java - 使用具有线程间通信的两个线程打印数字序列