1

im trying to figure out how i can get a notification when the state of a Windows Service changes. First i tryied a timer that check the state every view seconds with the ServiceControl.State. I found this "NotifyServiceStatusChange" but no examples or something like that and dont know how to use that.

Or is there a other way?

Background information: I have an application. The application has 2 buttons. Everytime the state of the service changes one of the buttons should be disabled. Like Service-State running then disable the "Start Service" button.

abatishchev
  • 98,240
  • 88
  • 296
  • 433
Ray Yago
  • 115
  • 1
  • 1
  • 12
  • I have a desktop program that displays service status and it just polls it every 1 second, which is good enough for my needs. Here's a working example of how how to use `NotifyServiceStatusChange` in .NET, but it's rather complicated: https://stackoverflow.com/questions/20061459/why-wont-my-solution-work-to-p-invoke-notifyservicestatuschange-in-c - unless you really need to use this approach I'd stick to the much simpler polling version. – Dai Feb 21 '18 at 18:42

2 Answers2

1

Have you had a look at the ServiceController Class? Something like this should get you started.

ServiceController sc = new ServiceController("ServiceName");
switch (sc.Status)
{
    case ServiceControllerStatus.Running:
        break;
    case ServiceControllerStatus.Stopped:
        break;
    case ServiceControllerStatus.Paused:
        break;
}

If you would like to avoid constantly polling on a timer, you could have a look at WaitForStatus. Have your background workers always waiting for a specified status to enable buttons, disable buttons or whatever.

This is a very basic example, but to answer your question about infinite loop - no. see my comments and debug step this, you will understand why.

ServiceController sc = new ServiceController("ServiceName");
for (;;)
{
     // for pauses execution, waiting for stopped status.
     sc.WaitForStatus(ServiceControllerStatus.Stopped);
     // continues when stopped status signaled, disable button 

     // for waiting for running status.
     sc.WaitForStatus(ServiceControllerStatus.Running);
     //continues when running status signaled, enable button
     // for will continue but wait for stopped status signal

}

This is why I recommended doing this check in a background worker or just something off of the main thread so that your entire application does not get jammed up while waiting for status changes.

clamchoda
  • 4,411
  • 2
  • 36
  • 74
  • thats what im using. A timer witch runs this every few seconds – Ray Yago Feb 21 '18 at 18:51
  • so if i got u right i could create a timer that calls the backgroundworker witch has the "WaitForStatus" code. – Ray Yago Feb 21 '18 at 19:16
  • @Ray Yago I only recommended the backgroundworker because WaitForStatus will pause the current thread while waiting for a status. You shouldn't need a timer AND a backgroundworker. You could even just do it on a separate thread. I just assumed you did not want to lock up your main application while monitoring the status change. Personally I would just stuff WaitForStatus in a loop on a backgroundworker if I was in your scenario. – clamchoda Feb 21 '18 at 19:22
0

If I understood it correctly, you have a windows service running in the background and another app that wants to be notified. If that is the case, you will need to implement some form of communication between them. Depending on your requirements, and where you are going to run the solution, you can use Message Queue (MSMQ for example) where you can subscribe/broadcast your messages. Another alternative it would be to user some Real Time Communication (like TCP/Socket, signalR or even using firebase to notify your app).