randycdouglas
asked on
Simple Windows Service not starting
My simple windows service isn't starting. I've been trying to install it locally (Windows 7 64 bit) to test. VS 2010 & C# & 64 bit. My solution properties list the active config as Debug|x86; there's not option for x64. Is this a problem? I've created an installer for the service by following these steps: http://msdn.microsoft.com/en-us/library/zt39148a.aspx. Start Type is set to automatic. My ServiceProcessInstaller is using the LocalSystem account. Please help me figure out why this service won't start.
using System;
using System.Diagnostics;
using System.IO;
using System.ServiceProcess;
namespace dupzapII
{
public partial class DupZap : ServiceBase
{
private FileSystemWatcher _watcher;
private string watchFolder = @"C:\FolderBeingWatched\";
private string destinationFolder = @"C:\FolderToMoveTo\";
public DupZap()
{
InitializeComponent();
if (!System.Diagnostics.EventLog.SourceExists("DupZap"))
{
System.Diagnostics.EventLog.CreateEventSource(
"DupZap", "DupZap");
}
eventLog1.Source = "DupZap";
eventLog1.Log = "DupZap";
}
protected override void OnStart(string[] args)
{
eventLog1.WriteEntry("DupZap Started");
try
{
_watcher = new FileSystemWatcher(watchFolder, "*.tif");
_watcher.Changed += new FileSystemEventHandler(watcher_FileChanged);
_watcher.NotifyFilter = NotifyFilters.LastWrite;
_watcher.EnableRaisingEvents = true;
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
void watcher_FileChanged(object sender, FileSystemEventArgs e)
{
try
{
eventLog1.WriteEntry("DupZap Started");
File.Move(e.FullPath, e.FullPath.Replace(watchFolder, destinationFolder));
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
protected override void OnStop()
{
eventLog1.WriteEntry("DupZap Stopped");
}
}
}
ASKER
The purpose of the service, without getting into to much detail, is to watch a folder, once a file (tif image) is copied to it, the file will be moved to another folder. Later I'll be checking the destination folder for a duplicate of the inserted file.
There is no "work" for your service to do--an event handler isn't enough to keep your service alive. An event handler only exists as long as your application exists, and since there is nothing to keep your service in memory, you get the behavior you have experienced.
What I mean by "work" is that you need to either spawn a new thread, or start a timer. You do either of these options in your OnStart method. Since it appears that the whole of your service is to let the FileSystemWatcher do its thing, I'd say all you need is a polling loop. All the loop needs to do is sleep. For example,
Now this is very basic, and it doesn't really give you a way to cleanly stop the thread, but it should give you an idea of what needs to happen for your service to run.
What I mean by "work" is that you need to either spawn a new thread, or start a timer. You do either of these options in your OnStart method. Since it appears that the whole of your service is to let the FileSystemWatcher do its thing, I'd say all you need is a polling loop. All the loop needs to do is sleep. For example,
while (true)
{
System.Threading.Thread.Sleep(1000);
}
Now this is very basic, and it doesn't really give you a way to cleanly stop the thread, but it should give you an idea of what needs to happen for your service to run.
ASKER
Thanks expert! This makes sense, but I tried it with no success. I got the same message I listed in my original post. I've listed the two different ways I tried your suggestion. See anything else that could be causing this?
Also, I see you wrote "it doesn't really give you a way to cleanly stop the thread". Why is this required and how is this done. Your help is greatly appreciated.
Also, I see you wrote "it doesn't really give you a way to cleanly stop the thread". Why is this required and how is this done. Your help is greatly appreciated.
protected override void OnStart(string[] args)
{
eventLog1.WriteEntry("DupZap Started");
try
{
while (true)
{
_watcher = new FileSystemWatcher(watchFolder, "*.tif");
_watcher.Changed += new FileSystemEventHandler(watcher_FileChanged);
_watcher.NotifyFilter = NotifyFilters.LastWrite;
_watcher.EnableRaisingEvents = true;
Thread.Sleep(1000);
}
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
I've also tried this:
protected override void OnStart(string[] args)
{
eventLog1.WriteEntry("DupZap Started");
try
{
_watcher = new FileSystemWatcher(watchFolder, "*.tif");
_watcher.NotifyFilter = NotifyFilters.LastWrite;
_watcher.EnableRaisingEvents = true;
while (true)
{
_watcher.Changed += new FileSystemEventHandler(watcher_FileChanged);
Thread.Sleep(1000);
}
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
ASKER CERTIFIED SOLUTION
membership
Create a free account to see this answer
Signing up is free and takes 30 seconds. No credit card required.
ASKER
I see. Things are so much clearer now. I was under the impression a service would continue to run on its own.
Unfortunatly, I'm still getting the same error. My new code is listed below. Your time is appreciated.
Unfortunatly, I'm still getting the same error. My new code is listed below. Your time is appreciated.
using System;
using System.Diagnostics;
using System.IO;
using System.ServiceProcess;
using System.Threading;
namespace dupzapII
{
public partial class DupZap : ServiceBase
{
private FileSystemWatcher _watcher;
private string watchFolder = @"C:\FolderBeingWatched\";
private string destinationFolder = @"C:\FolderToMoveTo\";
private System.Threading.Thread workerThread;
private bool keepRunning;
public DupZap()
{
InitializeComponent();
if (!EventLog.SourceExists("DupZap"))
{
EventLog.CreateEventSource(
"DupZap", "DupZap");
}
eventLog1.Source = "DupZap";
eventLog1.Log = "DupZap";
}
protected override void OnStart(string[] args)
{
eventLog1.WriteEntry("DupZap Started");
try
{
_watcher = new FileSystemWatcher(watchFolder, "*.tif");
_watcher.NotifyFilter = NotifyFilters.LastWrite;
_watcher.EnableRaisingEvents = true;
this.keepRunning = true;
this.workerThread = new System.Threading.Thread(RunWorkerLoop);
this.workerThread.Start();
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
void watcher_FileChanged(object sender, FileSystemEventArgs e)
{
try
{
eventLog1.WriteEntry("DupZap Started");
File.Move(e.FullPath, e.FullPath.Replace(watchFolder, destinationFolder));
}
catch (Exception ex)
{
eventLog1.WriteEntry(ex.ToString(), EventLogEntryType.Error);
}
}
protected override void OnStop()
{
this.keepRunning = false;
eventLog1.WriteEntry("DupZap Stopped");
}
private void RunWorkerLoop()
{
while (this.keepRunning)
{
System.Threading.Thread.Sleep(1000);
}
}
}
}
I copied your code into a new project and it worked fine for me. The only issue I see is that you haven't attached the handler to the event. In other words, you are missing a line like this:
Other than that, it should be working. What account are you running the service as? A local account? LOCAL SERVICE? NETWORK SERVICE? etc.?
_watcher.Changed += new FileSystemEventHandler(watcher_FileChanged);
Other than that, it should be working. What account are you running the service as? A local account? LOCAL SERVICE? NETWORK SERVICE? etc.?
ASKER
My ServiceProcessInstaller is using the LocalSystem account.
Are you certain you are uninstalling the old service and reinstalling the new, rebuilt version?
ASKER
Copying the code into a new project did the trick. Thanks expert!
ASKER
"The DupZap service on Local Computer started and then stopped. Some services stop automatically if they are not in use by other services or programs."