Top VPS Hosting Provider

web hosting

Creating a Windows Service in Visual Studio 2010

by Sully Syed on September 27, 2010

Once in a blue moon I’m tasked with a project whose requirements call for a long-running (or periodically running) application that needs little in the way of user interaction. As I’ve a small cadre of .NET developers and plenty of Windows OS surrounding me, one solution has been to implement a Windows Service.

Creating a Windows Service project in Microsoft Visual Studio 2010 takes all of three or four mouse clicks. What isn’t immediately clear, and what will serve as the topic for this entry, is:

  • How to get your Windows Service to run every X seconds/minutes/hours (on a timer)
  • How to make your Windows Service installable
  • How to read application settings from a .CONFIG file
  • How to perform real-time debugging upon your Windows Service

Excited? All right, let’s roll!

How to get your Windows Service to run every X seconds/minutes/hours (on a timer)

In order to get your new Windows Service to run periodically, we make use of the System.Timers.Timer object. The code fragment below illustrates how to add the basic start, stop and timer objects and classes to the automatically-created main file, Service1.vb. I hope it’s self-explanatory.

Public Class Service1
    Public thisTimer As System.Timers.Timer
    Public IsRunning As Boolean

    ' This automatically-created subprocedure contains code you want run when the service is started.
    Protected Overrides Sub OnStart(ByVal args() As String)
        ' Set initial variable values.
        Me.IsRunning = False

        ' Create and start a timer that checks every 20 seconds.
        thisTimer = New System.Timers.Timer()
        thisTimer.Enabled = True
        thisTimer.Interval = 20000
        thisTimer.AutoReset = True
        AddHandler thisTimer.Elapsed, AddressOf thisTimer_Tick
        thisTimer.Start()
    End Sub

    ' This automatically-created subprocedure contains code you want run when the service is stopped.
    Protected Overrides Sub OnStop()

    End Sub

    ' This subprocedure is of our own creation, used to store code we want this service to actually execute.
    Public Sub DoNextExecution()
        SyncLock Me
            thisTimer.Stop()

            ' Another execution cycle begins.

            thisTimer.Start()
        End SyncLock
    End Sub

    ' Each time the timer completes an interval, it executes the code found within this subprocedure.
    Private Sub thisTimer_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs)
        DoNextExecution()
    End Sub
End Class

I should add that, like you, I was initially concerned about the CPU utilization of using a timer in this fashion. I am happy to report that the Windows Service does idle while no activity except for the timer are running.

How to make your Windows Service installable

The Windows Service requires extra code to be able to be installed onto a Windows machine. Start by adding a new item to the project of the type Installer Class. Following the lead of others, I typically name this class ProjectInstaller.vb. Then right-click on the new class and select View Designer mode.

Visual Studio 2010 unfortunately does not have the controls you require listed in the toolbox by default, so we’ll need to add them to it. Do this by opening the Tools menu and selecting Choose Toolbox Items… In the .NET Framework Components tab, sort by Namespace. Add System.ServiceProcess.ServiceInstaller and System.ServiceProcess.ServiceProcessInstaller and press OK.

Let’s configure the first item, the ServiceInstaller:

  1. Under the toolbox section Visual Basic PowerPacks, drag a ServiceInstaller into the ProjectInstaller.vb design window. Right-click on it and select Properties.
  2. Verify that the Parent property is set to ProjectInstaller.
  3. Change the Service Name property to what you want the service to be called within the list of services in Windows.
  4. Change the StartType property using the drop-down to Automatic.

Now configure the second item, the ServiceProcessInstaller:

  1. Under the toolbox section Visual Basic PowerPacks, drag a ServiceProcessInstaller into the ProjectInstaller.vb design window. Right-click on it and select Properties.
  2. Change the Parent property to ProjectInstaller.
  3. Change the Account property to LocalSystem.

That’s it – save ProjectInstaller.vb to disk. You can now use the InstallUtil.exe program to actually install your new Windows Service to a machine to begin use of it.

How to read application settings from a .CONFIG file

Nearly every application has environment settings that rarely change but, when they do, need to be easily and quickly modified. A Windows Service project provides this functionality through .CONFIG files. There are two key pieces of knowledge needed to use a .CONFIG file with a Windows Service:

  1. The .CONFIG file must reside in the same directory as the .EXE that is compiled.
  2. The .CONFIG file must be named identically to the .EXE file, with a second extension .CONFIG appended to the end.

Thus, if I have compiled SampleService.exe, I create and save a file called SampleService.exe.config to the same directory.

A Windows Service is again by default not set up to use .CONFIG files – but enabling that functionality is a three-click process:

  1. Right-click References in the project’s Solution Explorer and select Add Reference…
  2. Add a reference to System.Configuration.

You may now refer to application variables from the .CONFIG file in this manner:

System.Configuration.ConfigurationManager.AppSettings("DirectoryLogs")

The corresponding value would be written in the .CONFIG value as:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <appSettings>
        <add key="DirectoryLogs" value="E:\Database\logs\MigrationService" />
    </appSettings>
</configuration>

How to perform real-time debugging upon your Windows Service

One of the most fantastic features about all of the Visual Studio IDEs is the integrated debug tools. Most people are familiar with the method in which you begin step-by-step debugging of a web application: Start debug mode and navigate to the page using your Web browser.

Debugging a Windows Service is nearly as straightforward: Compile your Windows Service and install it as a service on your local machine (in debug mode). Then, with Visual Studio 2010 still open and using the exact same copy of the code as was just installed:

  1. Under the Debug menu, select Attach To Process…
  2. Near the bottom of the window, select Show processes in all sessions.
  3. Left-click the EXE you compiled to be run as the Windows Service in the list (it might help to sort by Process). Click Attach.

Now, if you place breakpoints at places in your functions that you know will be executed, you’ll be able to take control of the service as it continues to execute.

That covers all of our topics, from getting your Windows Service to periodically execute code to how to bug your service in real time. If you’ve got any comments or questions please leave a comment and I’ll do my best to clarify anything that may be unclear.

Related posts:

  1. Microsoft TechEd 2010: Microsoft Visual Studio 2010 Tips & Tricks
  2. Microsoft TechEd 2010: Microsoft Visual Studio 2010 For Web Deployment
  3. Using FrontPage with Windows 2008 Shared Hosting Servers
  4. Microsoft TechEd 2010: Developers Are From Mars, Testers Are From Venus
  5. The Skinny on Longhorn: Windows Server 2008 and IIS7

{ 17 comments }

Randy5 October 18, 2010 at 9:38 AM

I’m going to forward this to a friend of mine who’s looking to create a Windows service in Vistual Studio ’10. He’s gonna love having it all spelled out for him like this.

katerina November 4, 2010 at 7:51 AM

it’s great article, really helpfull, thank you :-)

Sasikumar December 8, 2010 at 7:31 AM

Very useful article.
I would like to know the following topics:
1. How to fire this service when an alert comes from database.
2. Extract the data from database and put that as a Memory Mapped File

Appreciate your help and effort!

Chris March 25, 2011 at 5:41 AM

This is a fantastic, easy to follow tutorial, keep up the good work, thanks.

waqas March 25, 2011 at 8:40 AM

Good Work. Keep it up

Kenny April 14, 2011 at 4:44 PM

Thanks for this. I worked through several other instructions and yours is the first that made it clear – and worked! Nice job.

Rusher June 9, 2011 at 12:31 AM

I agree about the clarity. And it’s hard to make such complicated directions so clear, too!

Mike June 21, 2011 at 7:22 PM

When I try to attach to my service to debug, it shows as greyed out and I can’t attach to it. Also, the name of the executable in the list is my vshost.exe and not the plain exe that I installed. Ideas?

Saga October 19, 2011 at 4:23 AM

Hi, nice article. Just as a note, I am having the same problem as Mike (June 21, 2011). Thanks.

John December 14, 2011 at 6:33 PM

Hiya,

I couldn’t get it to work…. Can anyone help? I’m a little lost once I’ve built the project. I think I’ve got everything in tact… Could someone email me that may know how to get this working? My email is john (underscore) sidney (at) hotmail (dot) co (dot) uk

Cheers!

John December 14, 2011 at 6:47 PM

Hiya,

I couldn’t get it to work…. Can anyone help? I’m a little lost once I’ve built the project. I think I’ve got everything in tact… Could someone email me that may know how to get this working? My email is john (underscore) sidney (at) hotmail (dot) co (dot) uk

Cheers!

Error from command window:
Running a transacted installation.

Beginning the Install phase of the installation.
See the contents of the log file for the C:\lrmonitor\Test\JohnService\JohnServi
ce\JohnService.exe assembly’s progress.
The file is located at C:\lrmonitor\Test\JohnService\JohnService\JohnService.Ins
tallLog.
Installing assembly ‘C:\lrmonitor\Test\JohnService\JohnService\JohnService.exe’.

Affected parameters are:
logtoconsole =
assemblypath = C:\lrmonitor\Test\JohnService\JohnService\JohnService.exe
logfile = C:\lrmonitor\Test\JohnService\JohnService\JohnService.InstallLog
Installing service Service1…
Creating EventLog source Service1 in log Application…

An exception occurred during the Install phase.
System.Security.SecurityException: The source was not found, but some or all eve
nt logs could not be searched. Inaccessible logs: Security.

The Rollback phase of the installation is beginning.
See the contents of the log file for the C:\lrmonitor\Test\JohnService\JohnServi
ce\JohnService.exe assembly’s progress.
The file is located at C:\lrmonitor\Test\JohnService\JohnService\JohnService.Ins
tallLog.
Rolling back assembly ‘C:\lrmonitor\Test\JohnService\JohnService\JohnService.exe
‘.
Affected parameters are:
logtoconsole =
assemblypath = C:\lrmonitor\Test\JohnService\JohnService\JohnService.exe
logfile = C:\lrmonitor\Test\JohnService\JohnService\JohnService.InstallLog
Restoring event log to previous state for source Service1.
An exception occurred during the Rollback phase of the System.Diagnostics.EventL
ogInstaller installer.
System.Security.SecurityException: The source was not found, but some or all eve
nt logs could not be searched. Inaccessible logs: Security.
An exception occurred during the Rollback phase of the installation. This except
ion will be ignored and the rollback will continue. However, the machine might n
ot fully revert to its initial state after the rollback is complete.

The Rollback phase completed successfully.

The transacted install has completed.
The installation failed, and the rollback has been performed.

Bent Adler July 12, 2012 at 5:31 AM

Hi,
did You find a solution for this problem. I´m having the same problem right now?

with regards
Bent

SexyDjb October 8, 2012 at 12:56 AM

The problem is because you are trying to install the service without administrative rights.
Open the visual studio command prompt with administrative rights and then install using command “installutil .exe”

Try and ask if there is any prblem

jazzy January 11, 2012 at 3:31 PM

Great article…Just a suggestion. If you can have a little piece which does some operations like writing log and pulling data/writing data etc…It will become complete guide.
Keep up good work

Thanks

Matt Johnson April 20, 2012 at 9:21 AM

Perhaps this might seem like a dumb comment, but you might alter your statement, “That’s it – save ProjectInstaller.vb to disk. You can now use the InstallUtil.exe program to actually install your new Windows Service to a machine to begin use of it.” to something that explains as clearly as the rest of your guide HOW to use the InstallUtil.exe program to actually install said service… my only point here, is that at 1 point, I didn’t KNOW HOW to use InstallUtil, and from doing Google searches, finding good examples seemed difficult. Spelling that out as well as you did everything else I believe would be very helpful to people who potentially don’t know how to do what you’re outlining.

Bent July 12, 2012 at 7:36 AM

Thanks, this was useful.

Andrew October 8, 2012 at 11:21 AM

Very useful – to resolve install issues;
Run InstallUtil from the ‘Visual Studio Command Prompt (2010)’, as Administrator. On Vista or Windows 7 with UAC enabled, instead of left clicking on the Visual Studio Command Prompt, right click and select “Run as Administrator”.

To Install:-
installutil “C:\path-to-my-proj\service.exe”

To Remove/Uninstall:-
installutil /u “C:\path-to-my-proj\service.exe”

Previous post:

Next post:

Website Hosting and Domain Hosting Email Hosting Services, Pick Up Your Email
© 2013 SoftCom Inc. All rights reserved.