Jaime Menendez Llana
Jaime Menendez Llana

Reputation: 473

Run timer in windows service

I have a windows service which is checking in a given path if there are new files created. To do that, I made with a timer which is checking every second the creation of new files in the directory. All the actions of the windows service I'm saving in a log through Log4net library. The problem comes when I start the service. It stops when I want to start the timer.

Thats my window service class:

public partial class WindowsService : ServiceBase
{

    private aTimer timer;
    private static readonly ILog logger = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);

    public WindowsService()
    {            
        InitializeComponent();
    }

    public void OnDebug()
    {
        OnStart(null);
    }

    private void StartTimer()
    {
        timer.StartTimer();
    }

    private void StopTimer()
    {
        timer.CloseTimer();
    }


    protected override void OnStart(string[] args)
    {
        logger.Debug("Service is started.");
        logger.Debug("-----------------------------------------------------------");
        this.StartTimer();


    }

    protected override void OnStop()
    {
        this.StopTimer();         
        logger.Debug("-----------------------------------------------------------");
        logger.Debug("Service is stopped.");

    }
}

Thats it's my Timer class:

public class aTimer
{
    private System.Timers.Timer timer;
    private bool timerTaskSuccess;

    private static readonly String path = "C:\\path\\";
    private static readonly ILog logger = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);

    public aTimer() { }

    public void StartTimer()
    {
        try
        {
            timer = new System.Timers.Timer(1000);

            timer.Elapsed += OnTimedEvent;
            timer.AutoReset = true;
            timer.Enabled = true;
            timer.Start();

            timerTaskSuccess = false;
        }
        catch (Exception ex)
        {
            logger.ErrorFormat("Error ocurred while starting the timer: '{0}'", ex);
        }

        Watcher watcher = new Watcher();
        watcher.CreateWatcher(path);
    }

    private void OnTimedEvent(Object source, ElapsedEventArgs e)
    {
        try
        {
            logger.InfoFormat("The Elapsed event was raised at '{0:HH:mm:ss}'", e.SignalTime);
            timerTaskSuccess = true;
        }
        catch (Exception ex)
        {
            logger.ErrorFormat("Error ocurred while catching event the timer: '{0}'", ex);
            timerTaskSuccess = false;
        }
        finally
        {
            if (timerTaskSuccess)
            {
                timer.Start();
            }
        }

    }


    public void CloseTimer()
    {
        try
        {
            timer.Enabled = false;
            timer.Stop();
            timer.Dispose();
            timer = null;

            timerTaskSuccess = true;
        }
        catch (Exception ex)
        {
            logger.ErrorFormat("Error ocurred while stopping the timer: '{0}'", ex);
        }

    }
}

Anyone could help me. I test the logical code in a console application and it's working fine. Where is the issue? Thanks!

Upvotes: 0

Views: 2322

Answers (2)

Kirk Broadhurst
Kirk Broadhurst

Reputation: 28718

There are two main approaches to debugging Windows Services. One is more rigorous but takes longer; the other is quick and simple.

  1. Debug in Visual Studio. Wrap all your code so that it can start as a Windows Service or as a Console Application. There are lots of ways to do this, but the best I've seen involved conditional compilation in the application's main method. When running in Debug, the main class is simply executed. When running in Release, the Service pattern kicks in and the service starts normally.

  2. Debug an installed Windows Service. Put a large sleep / wait into your application, and after installing simply attach to it using Visual Studio. If you sleep for 30 seconds that should be plenty of time to go back to Visual Studio, go to the attach menu, find the application and attach. The execution will stop at your breakpoint.

Upvotes: -1

Thorsten Dittmar
Thorsten Dittmar

Reputation: 56697

You declare the member

private aTimer timer;

but you never actually call the constructor, like:

timer = new aTimer();

So in your WindowsService.StartTimer() method you get a NullReferenceException. Add the above line to your service's constructor and you should be fine.

Upvotes: 2

Related Questions