Controlling a Windows Service

   


Create and manipulate a Windows service.

In the previous section, I discussed several utilities for manipulating Windows services. You might also need to manipulate a Windows service programmatically from your program. You may use this in the scenario in which you want to take some action based on the status of a service, or you may want to take some actions in a program that require you to start, pause, continue, or stop a Windows service. You may also want to programmatically manipulate a Windows service when you want to provide your own custom user interface for configuring and controlling a Windows service.

NOTE

Creating MMC Snap-ins If you want to provide an MMC-integrated administration module for your Windows service application, you can use classes from the System.Management.Instrumentation namespace. These classes make up a whole subject known as Windows Management Instrumentation (WMI), which is not a part of Exam 70-310 objectives. However, if you are curious , you can find more information in the "Managing Applications Using WMI" topic in the .NET Framework SDK documentation.


You can use the ServiceController class of the System.ServiceProcess namespace to programmatically control Windows services from your programs. In the next two sections, you'll learn what the ServiceController class is and how you can use this class in your programs.

The ServiceController Class

The ServiceController class provides functionality to connect to a Windows service and control its behavior. Table 6.5 lists some important methods and properties of this class that you'll typically use in a Windows service control program.

Table 6.5. Important Members of the ServiceController Class

Member

Type

Description

CanPauseAndContinue

Property

A value of True indicates that the service can be paused and resumed.

CanShutdown

Property

A value of True indicates that the service should be notified when the system is shutting down.

CanStop

Property

A value of True indicates that the service can be stopped after it has started.

Close()

Method

Disconnects the ServiceController object from the Windows service.

Continue()

Method

Continues a Windows service after it has been paused.

DisplayName

Property

Specifies a friendly name for the service.

This will execute a custom command on the service.

GetServices()

Method

Retrieves the Windows services installed on a computer.

MachineName

Property

Specifies the name of the computer on which this service resides. Its default value is set to the local computer. You need to change the MachineName property only in the case where you want to control the Windows services on a remote machine.

Pause()

Method

Suspends a Windows service's operation.

Refresh()

Method

Refreshes the values of all the properties with their latest values.

ServiceName

Property

Specifies the name of the Windows service.

ServicesDependedOn

Property

Specifies the set of services that this Windows service depends on.

ServiceType

Property

One of the ServiceType enumeration values that specifies how the Windows service is used. A Windows service can be of one of these types InteractiveProcess (can communicate with the desktop), Win32OwnProcess (runs in its own process), or Win32ShareProcess (shares the process with other Windows service).

Start()

Method

Starts the Windows service.

Status

Property

Retrieves the status of the Windows service.

Stop()

Method

Stops the Windows service and other services that are dependent on this service.

WaitForStatus()

Method

Waits for the service to reach the specified status, which is a value of the ServiceControllerStatus enumeration. Its possible values are ContinuePending , Paused , PausePending , Running , StartPending , Stopped , and StopPending .

Creating a Service Controller Application

In this section, I'll show you how to use various methods and properties of the ServiceController class to create a simple service controller application.

The application enumerates the list of installed services on the local machine and allows users to start, stop, pause, continue, and refresh the list of services. Step By Step 6.5 shows you how to accomplish this.

STEP BY STEP

6.5 Creating a Service Controller Application

  1. Add a new Windows Application project to the solution. Name the project StepByStep6-5 .

  2. Add a new form named frmServiceController.vb . Access the Properties window for this form and change the Text property to Service Controller .

  3. Add a ListBox control ( lbServiceList ), a Label control ( lblStatus ), and four Button controls ( btnStart , btnStop , btnPauseContinue , and btnRefresh ) to the form. Arrange the controls as shown in Figure 6.12.

    Figure 6.12. Arrange controls to create a user interface for the service controller program.

  4. Add a reference to System.ServiceProcess.dll to the project. Add the following statement to the code:

     Imports System.ServiceProcess 
  5. Double-click on an empty area on the form to attach an event handler to its Load event. Add the following code to the event handler:

     Private Sub frmServiceController_Load(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) Handles MyBase.Load     PopulateServiceList() End Sub ' Get the list of installed services Public Sub PopulateServiceList()     ' Populate services in the list box     lbServiceList.DataSource = _      ServiceController.GetServices()     ' Display friendly name     lbServiceList.DisplayMember = "DisplayName" End Sub 
  6. Double-click on the ListBox to attach an event handler to its SelectedIndexChanged event. Add the following code to its event handler:

     Private Sub lbServiceList_SelectedIndexChanged(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) _  Handles lbServiceList.SelectedIndexChanged     ' Retrieve the selected service     Dim service As ServiceController = _      CType(lbServiceList.SelectedItem, _      ServiceController)     ' And get status for it     GetServiceStatus(service) End Sub ' Find the latest service status Public Sub GetServiceStatus(_  ByVal sc As ServiceController)     ' Get the service status     Dim status As ServiceControllerStatus = sc.Status     ' Enable all buttons     btnStart.Enabled = True     btnStop.Enabled = True     btnPauseContinue.Enabled = True     ' Disable the pause button if the service does     ' not support pause and continue command     If Not sc.CanPauseAndContinue Then         btnPauseContinue.Enabled = False     End If     ' Disable the stop button if the service does     ' not support stop command     If Not sc.CanStop Then         btnStop.Enabled = False     End If     ' Enable and disable buttons based on     ' service status. Also display the text     ' for the status     Select Case status         Case ServiceControllerStatus.ContinuePending             lblStatus.Text = "Continue Pending"             btnPauseContinue.Enabled = False         Case ServiceControllerStatus.Paused             lblStatus.Text = "Paused"             btnPauseContinue.Text = "Continue"             btnStart.Enabled = False         Case ServiceControllerStatus.PausePending             lblStatus.Text = "Pause Pending"             btnPauseContinue.Enabled = False             btnStart.Enabled = False         Case ServiceControllerStatus.Running             lblStatus.Text = "Running"             btnPauseContinue.Text = "Pause"             btnStart.Enabled = False         Case ServiceControllerStatus.StartPending             lblStatus.Text = "Start Pending"             btnStart.Enabled = False         Case ServiceControllerStatus.Stopped             lblStatus.Text = "Stopped"             btnStop.Enabled = False         Case ServiceControllerStatus.StopPending             lblStatus.Text = "Stop Pending"             btnStop.Enabled = False         Case Else             lblStatus.Text = "Unknown Status"     End Select End Sub 
  7. Add the following code to handle the button events:

     Private Sub btnStart_Click(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) Handles btnStart.Click     ' It might take time so change the     ' cursor to a wait cursor     Cursor.Current = Cursors.WaitCursor     ' Retrieve the selected service     Dim service As ServiceController = _      CType(lbServiceList.SelectedItem, _      ServiceController)     ' Start the service and wait till     ' the status is Running     service.Start()     service.WaitForStatus(_      ServiceControllerStatus.Running)     ' Refresh the list     Dim intIndex As Integer = _      lbServiceList.SelectedIndex     PopulateServiceList()     lbServiceList.SelectedIndex = intIndex     ' Change the cursor back to normal     Cursor.Current = Cursors.Default End Sub Private Sub btnStop_Click(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) Handles btnStop.Click     ' It might take time so change the     ' cursor to a wait cursor     Cursor.Current = Cursors.WaitCursor     ' Retrieve the selected service     Dim service As ServiceController = _      CType(lbServiceList.SelectedItem, _      ServiceController)     ' Start the service and wait till     ' the status is Running     service.Stop()     service.WaitForStatus(_      ServiceControllerStatus.Stopped)     ' Refresh the list     Dim intIndex As Integer = _      lbServiceList.SelectedIndex     PopulateServiceList()     lbServiceList.SelectedIndex = intIndex     ' Change the cursor back to normal     Cursor.Current = Cursors.Default End Sub Private Sub btnPauseContinue_Click(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) _  Handles btnPauseContinue.Click     ' It might take time so change the     ' cursor to a wait cursor     Cursor.Current = Cursors.WaitCursor     ' Retrieve the selected service     Dim service As ServiceController = _      CType(lbServiceList.SelectedItem, _      ServiceController)     If btnPauseContinue.Text = "Pause" Then         ' Pause the service and wait till         ' the status is Paused         service.Pause()         service.WaitForStatus(_          ServiceControllerStatus.Paused)     Else         ' Resume the service and wait till         ' the status is Running         service.Continue()         service.WaitForStatus(_          ServiceControllerStatus.Running)     End If     ' Refresh the list     Dim intIndex As Integer = _      lbServiceList.SelectedIndex     PopulateServiceList()     lbServiceList.SelectedIndex = intIndex     ' Change the cursor back to normal     Cursor.Current = Cursors.Default End Sub Private Sub btnRefresh_Click(_  ByVal sender As System.Object, _  ByVal e As System.EventArgs) Handles btnRefresh.Click     ' Refresh the list     Dim intIndex As Integer = _      lbServiceList.SelectedIndex     PopulateServiceList()     lbServiceList.SelectedIndex = intIndex End Sub 
  8. Set the form as the startup object for the project.

  9. Build the StepByStep6-5 project. Set the project as the startup project for the solution and start the project. You will see a Window displaying a list of installed services as shown in Figure 6.13.

    Figure 6.13. The Service Controller form controls the Windows services programmatically.

  10. Scroll through the list of services. Select OrderService . Pause the service, and then continue. Stop the service and then start. As you do this, also create new XML files in the c:\orders directory. You'll find that the files are not processed when the OrderService is paused or stopped.

  11. Open the Application EventLog. You'll see that each time you start, pause, continue, or stop the OrderService service, an entry in the Application event log is written. This happens because you set the AutoLog property for the Windows service to true .

  12. Click on the Refresh button to update the list of installed services with any newly installed or uninstalled services.

In Step By Step 6.5, most of the code is written to make the user interface work logically. For the list of services, I am using the ServiceController.GetServices() static method to get a list of installed services that I populate in the lbServiceList control.

When the user clicks on the btnStart button, the code calls the Start() method to start the selected Windows service. The Windows service might take some time to start, and meanwhile I should restrict the user from pressing any other buttons. Therefore, I am calling the synchronous WaitForStatus() method that waits until the Windows service returns a Running status. I followed a similar logic for other control messages also.

REVIEW BREAK

  • Several tools are available for monitoring and controlling Windows services. Some notable tools are the Services MMC snap-in, Visual Studio .NET Server Explorer, the net.exe command-line utility, and the Service Control command-line utility (sc.exe).

  • The Service Control utility (sc.exe) is distributed as a part of Windows XP and later operating systems and as a part of Win32 SDK and the .NET Framework SDK. This utility is the most powerful tool to control and configure Windows services.

  • Some programs might also need to monitor Windows services programmatically. The FCL provides the System.ServiceProcess.ServiceController class to programmatically control the Windows services.

  • The ServiceController.GetServices() method is used to enumerate installed services on a computer. You can use the Start() , Stop() , Pause() , and Continue() methods to change the status of a Windows service. The WaitforStatus() synchronous method is useful when you would like the current thread to pause execution and wait for the Windows service to enter in the specified state.


   
Top


MCAD. MCSD Training Guide (Exam 70-310. Developing XML Web Services and Server Components with Visual Basic. NET and the. NET Framework)
MCAD/MCSD Training Guide (70-310): Developing XML Web Services and Server Components with Visual Basic(R) .NET and the .NET Framework
ISBN: 0789728206
EAN: 2147483647
Year: 2002
Pages: 166

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net