If you are a true geek, one of the measurements you set your mind to figure something out and stick with it until you solve the problem. Some people call it root cause analysis. The common person calls it crazy. Normal people do not think like this but computer geeks are a bit different. Over the years, I have been interested in Windows .NET services. Ever since .NET 1.0 came out, I thought it would be cool to have my very own service. I remember a while ago Dave Wanta (Creator of ASPNetEmail) saying, if you develop your own Windows Service, it should allow the service to accept custom commands. Years have passed but I never gave up the challenge of figuring out how to do this. I wrote my own service called IISLogsSVC, the 1.0 version doesn’t have the ability to pass custom commands. The 2.0 version should have functionality to accept "on-demand" commands from a Winforms app.
This article covers a simple “Hello World” application called “AService” using the .Net 2.0 framework. Microsoft has made it very simple to do; this used to be reserved for those who knew C/C++. What does AService do exactly?? Nothing really besides log a few entries in the Application event log. It does have sample code showing how easy it is to pass custom commands using a WinForms application while the .Net service is running. I did not find a “Hello world” application like this so I hope my article helps.
One other tip, I found on MSDN the custom commands from 1 to 128 are system reserved values. Here is the link to the article hopefully that explains why the first command uses 130. I was bored and did not want to use 129. ? Some other cool things AService has a setup project included in the zip file. When I was first learning how to use Visual Studio 2003 setup projects. It was a bit overwhelming since I did not have any experience doing this type of thing. I hope that you find this useful if you are unfamiliar how to distribute a finished project.
In conclusion, you could use a nice front-end application written using Winforms while being able to interact with your .NET service. This article only scratches the surface of what you can do using Winforms and Windows .NET services together. Enjoy!
What is included in the Solution?
Three Visual Studio 2005 projects
-
AService — the .NET service code
-
AServiceGUI – the Winforms application
-
AServiceSetup – A setup project to distribute the application
Requirements
Where do I download the code?
Reference Links
Sample code – The WinForms application
Public Class Form1
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnRunCommand.Click
If cboSelectCommand.Text.ToString.ToLower = "<select command>" Then
MessageBox.Show("You forgot to select a command, please try again")
cboSelectCommand.Focus()
Else
For Each service As System.ServiceProcess.ServiceController In ServiceProcess.ServiceController.GetServices
If Me.ServiceController1.ServiceName.ToLower.Trim = service.ServiceName.ToLower.Trim Then
Select Case cboSelectCommand.Text.ToString
Case "130"
Me.ServiceController1.ExecuteCommand(130)
Case "131"
Me.ServiceController1.ExecuteCommand(131)
Case Else
Me.ServiceController1.ExecuteCommand(132)
End Select
End If
Next
End If
End Sub
Private Sub ToolBar1_ButtonClick_1(ByVal sender As System.Object, ByVal e As System.Windows.Forms.ToolBarButtonClickEventArgs) Handles ToolBar1.ButtonClick
Dim Log As New EventLog
Log.Source = "Application"
Select Case e.Button.ImageIndex
Case 0 ‘open
If Me.ServiceController1.Status = ServiceProcess.ServiceControllerStatus.Stopped Then
Me.ServiceController1.Start()
Me.ServiceController1.Refresh()
lblSVCStatus.ForeColor = Color.Green
lblSVCStatus.Text = "Started"
MessageBox.Show("Service Started")
End If
Case 1 ‘Run Service Now
If Me.ServiceController1.Status = ServiceProcess.ServiceControllerStatus.Running Then
Me.ServiceController1.Stop()
Me.ServiceController1.Refresh()
lblSVCStatus.ForeColor = Color.Red
lblSVCStatus.Text = "Stopped"
MessageBox.Show("Service Stopped")
End If
Case 2
If Me.ServiceController1.Status <> ServiceProcess.ServiceControllerStatus.Running Then
If MessageBox.Show("The Service is not started", "Start Service", MessageBoxButtons.YesNoCancel) = Windows.Forms.DialogResult.Yes Then
‘Start the service if the client wants
Me.ServiceController1.Start()
Threading.Thread.Sleep(5000)
Me.ServiceController1.Refresh()
For Each service As System.ServiceProcess.ServiceController In ServiceProcess.ServiceController.GetServices
If Me.ServiceController1.ServiceName.ToLower.Trim = service.ServiceName.ToLower.Trim = True Then
Me.ServiceController1.ExecuteCommand(130)
Log.WriteEntry("Ran the command:" & System.DateTime.Now())
lblSVCStatus.ForeColor = Color.Green
lblSVCStatus.Text = "Started"
End If
Next
End If
Else
MessageBox.Show("Process will not run, AService is already started", "Process will not run, AService is already started", MessageBoxButtons.OK)
End If
End Select
Log.Close()
Log.Dispose()
End Sub
Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
For Each service As System.ServiceProcess.ServiceController In ServiceProcess.ServiceController.GetServices
If Me.ServiceController1.ServiceName.ToLower.Trim = service.ServiceName.ToLower.Trim = True Then
If Me.ServiceController1.Status = ServiceProcess.ServiceControllerStatus.Running Then
lblSVCStatus.ForeColor = Color.Green
lblSVCStatus.Text = "Started"
ElseIf Me.ServiceController1.Status = ServiceProcess.ServiceControllerStatus.Stopped Then
lblSVCStatus.ForeColor = Color.Red
lblSVCStatus.Text = "Stopped"
Else
lblSVCStatus.ForeColor = Color.DarkBlue
lblSVCStatus.Text = "Unknown"
End If
End If
Next
End Sub
Private Sub ExitToolStripMenuItem_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles ExitToolStripMenuItem.Click
Me.Close()
End Sub
End Class
Sample code – The Windows Service Code
Public Class AService
Protected Overrides Sub OnStart(ByVal args() As String)
‘ Add code here to start your service. This method should set things
‘ in motion so your service can do its work.
End Sub
Protected Overrides Sub OnStop()
‘ Add code here to perform any tear-down necessary to stop your service.
End Sub
‘ Handle a custom command.
Protected Overrides Sub OnCustomCommand(ByVal command As Integer)
Select Case command
Case 1
System.Diagnostics.EventLog.WriteEntry("AService", "I selected :" & command.ToString())
Case 2
System.Diagnostics.EventLog.WriteEntry("AService", "I selected :" & command.ToString())
Case Else
System.Diagnostics.EventLog.WriteEntry("AService", "I selected :" & command.ToString())
End Select
End Sub ‘OnCustomCommand
End Class
Picture of A Service GUI (The Winforms app that controls the service)
Enjoy!!