为什么我无法在线程中启动Windows服务?

时间:2017-01-08 09:18:09

标签: c# multithreading

我的代码开始取决于底层应用程序是在控制台服务中运行而不是在任务的线程中运行。以下是主要方法的一小部分:

//ANSAR BANK THREAD
Thread AnsarBankThread = new Thread(Ansar);
Console.WriteLine("Start The AnsarBankThread");
AnsarBankThread.Start();
//MELLAT BANK THREAD
Thread MellatBankThread = new Thread(Mellat);
Console.WriteLine("Start The MellatBankThread");
MellatBankThread.Start();


这是将要执行的代码:

static void Ansar()
{
    var AnsarBank1 = new AnsarBank();
    if (Environment.UserInteractive)
    {
        AnsarBank1.Start();
    }
    else
    {
        var servicesToRun = new ServiceBase[]{ AnsarBank1 };
        ServiceBase.Run(servicesToRun);
    }
}
static void Mellat()
{
    var MellatBank1 = new MellatBank();
    if (Environment.UserInteractive)
    {
        MellatBank1.Start();
    }
    else
    {
        var servicesToRun = new ServiceBase[]{ MellatBank1 };
        ServiceBase.Run(servicesToRun);
    }
}


这是我的AnsarBank服务代码:

protected override void OnStart(string[] args)
{
    var timer = new System.Timers.Timer(5000); // fire every 30 second
    timer.Elapsed += OnElapsedTime;
    timer.Enabled = true;
}
private void OnElapsedTime(object source, ElapsedEventArgs e)
{
    File.WriteAllText(@"d:\Temp\Ansar.txt", "Ansar Bank Writer\n");
}
public void Start()
{
    OnStart(new string[0]);
}


这是我的MellatBank服务:

protected override void OnStart(string[] args)
{
    var timer = new System.Timers.Timer(5000); // fire every 30 second
    timer.Elapsed += OnElapsedTime;
    timer.Enabled = true;
}
private void OnElapsedTime(object source, ElapsedEventArgs e)
{
    File.WriteAllText(@"d:\Temp\MellatBank.txt", "Mellat Bank writer\n");
}
public void Start()
{
    OnStart(new string[0]);
} 


但是,如果我运行代码,则只会创建文件Ansar.txt并且文件MellatBank.txt丢失! 有人可以在我的代码中遇到问题吗?我将不胜感激任何帮助!
Chnage代码:

System.Timers.Timer personalTimer = null;

        public AnsarBank()
        {
            personalTimer = new System.Timers.Timer(5000);
            InitializeComponent();
        }

        protected override void OnStart(string[] args)
        {
            //var timer = new System.Timers.Timer(5000); // fire every 30 second
            personalTimer.Elapsed += OnElapsedTimeAnsar;
            personalTimer.Enabled = true;
        }


但是不行。

1 个答案:

答案 0 :(得分:1)

问题是什么?

1。变量超出范围:

感谢@Matthewatson :我还建议将方法之外的计时器变量移到类中。计时器对象可以直接进行垃圾收集,因为垃圾收集器没有看到它被进一步使用。

为什么认为该变量不再使用的gc?

只是因为你在方法中创建了它。它是本地的,因为课程本身没有任何参考,所以没有任何暗示它需要进一步的gc!

在我查看this问题之后,这应该是真的。

示例代码中的解决方案:

class SomeClass {
    System.Timers.Timer personalTimer = null; //Timer is now garbage collected after the object of SomeClass goes out of scope!

    SomeClass() {
        personalTimer = new Syste.Timers.Timer(30000) // Now every 30 seconds!
    }

    protected override void OnStart(string[] args)
    {
        personalTimer.Elapsed += OnElapsedTime;
        personalTimer.AutoReset = true; //Add this line to keep continuos activation
        personalTimer.Enabled = true;
    }

    ....
}

2.文件访问问题

尝试完代码后,我遇到异常,因为路径可能不存在。所以我在创建文件之前更改了代码以创建路径。我还添加了检查文件是否存在以及是否存在文本的文本。旧解决方案每次都替换文件。这对我很好。我不知道你用InitializeComponents(...)做了什么,这似乎是gui的东西,所以我不知道。

请将服务类中的代码更改为以下内容:

    namespace WebService
{
    partial class MellatBank : ServiceBase
    {
        System.Timers.Timer personalTimer = null;


        public MellatBank()
        {
            personalTimer = new System.Timers.Timer(1000);

            this.ServiceName = "MellatBankService";
        }
        protected override void OnStart(string[] args)
        {
            personalTimer.Elapsed += OnElapsedTimeMellat;
            personalTimer.AutoReset = true; //Add this line to keep continuos activation
            personalTimer.Enabled = true;
            //var timer = new System.Timers.Timer(5000); // fire every 30 second
            //personalTimer.Elapsed += OnElapsedTimeMellat;
            //personalTimer.Enabled = true;
        }
        private void OnElapsedTimeMellat(object source, ElapsedEventArgs e)
        {
            try
            {
                if (!Directory.Exists(@"D:\Temp"))
                 Directory.CreateDirectory(@"D:\Temp\");
                if (!File.Exists(@"D:\Temp\MellatBank.txt"))
                {

                    var f = File.CreateText(@"D:\Temp\MellatBank.txt");
                    f.Write(@"D:\Temp\MellatBank.txt", "Mellat Bank writer\n");
                    f.Close();
                }
                else
                {
                    var f = File.AppendText(@"D:\Temp\MellatBank.txt");
                    f.Write("Mellat Bank writer\n");
                    f.Close();
                }
            }
            catch (System.Exception ex)
            {
                Console.Error.WriteLine("IO EXCEPTION: {0}", ex.ToString());
            }
        }
        public void Start()
        {
            OnStart(new string[0]);
        }
        protected override void OnStop()
        {
            Console.Out.WriteLine("ended!");
            // TODO: Add code here to perform any tear-down necessary to stop your service.
        }

    }
}


namespace WebService
{
    partial class AnsarBank : ServiceBase
    {

        System.Timers.Timer personalTimer = null;

        public AnsarBank()
        {
            personalTimer = new System.Timers.Timer(1000);
            this.ServiceName = "AnsarBankService";
        }

        protected override void OnStart(string[] args)
        {


            personalTimer.Elapsed += OnElapsedTimeAnsar;
            personalTimer.AutoReset = true; //Add this line to keep continuos activation
            personalTimer.Enabled = true;
            //var timer = new System.Timers.Timer(5000); // fire every 30 second
            //personalTimer.Elapsed += OnElapsedTimeAnsar;
            //personalTimer.Enabled = true;
        }
        private void OnElapsedTimeAnsar(object source, ElapsedEventArgs e)
        {
            try
            {

                if (!Directory.Exists(@"D:\Temp"))
                    Directory.CreateDirectory(@"D:\Temp\");
                if (!File.Exists(@"D:\Temp\Ansar.txt"))
                {

                    var f = File.CreateText(@"D:\Temp\Ansar.txt");
                    f.Write(@"D:\Temp\Ansar.txt", "Ansar Bank writer\n");
                    f.Close();
                }
                else
                {
                    var f = File.AppendText(@"D:\Temp\Ansar.txt");
                    f.Write("Ansar Bank Writer\n");
                    f.Close();
                }
            }
            catch (System.Exception ex)
            {
                Console.Error.WriteLine("IO EXCEPTION: {0}", ex.ToString());
            }
        }
        public void Start()
        {
            OnStart(new string[0]);
        }
        protected override void OnStop()
        {
            Console.Out.WriteLine("ended!");
        }
    }
}

编辑:

查看代码后,我发现只有应用程序运行时,您的服务才会运行。因此,您的服务可能已经停止,然后他们才能编写任何可以解释您问题的内容。

PS: 如果您不知道类字段是什么,请 再次练习面向对象编程(OOP)的基础知识