So many problems; where to begin? :)
Your
OnChanged
event handler is ignoring the information about
which file changed, and sending a notification for
all files in the folder. You should use
e.FullName
to process just the file which has changed:
private static void OnChanged(object sender, FileSystemEventArgs e)
{
string file = e.FullName;
Console.WriteLine("EventListener Match File Found. FILE NAME : {0}", file);
try
{
string stringReceived = File.ReadAllText(file);
SendMailFunction(stringReceived);
File.Delete(file);
}
catch (IOException)
{
}
}
Your
RunEventListenerPrgm
method is creating multiple new
FileSystemWatcher
instances in a tight loop. Every single instance you create is going to trigger the
OnChanged
handler every time a file is changed. I'm amazed that you only managed to receive hundreds of messages for a single file!
The method will never terminate cleanly, so a quick-and-dirty fix would be to move the creation of the
FileSystemWatcher
instance outside of the loop:
public static void RunEventListenerPrgm()
{
var m_Watcher = new System.IO.FileSystemWatcher
{
Filter = "*.txt",
Path = @"C:\EventListenerFolder\",
NotifyFilter = NotifyFilters.LastAccess | NotifyFilters.LastWrite | NotifyFilters.FileName | NotifyFilters.DirectoryName
};
m_Watcher.Created += OnChanged;
m_Watcher.EnableRaisingEvents = true;
while (true)
{
}
}
However, this will probably consume 100% of one of your CPU cores all the time the program is running!
A slightly better alternative would be to use the
WaitForChanged
method:
public static void RunEventListenerPrgm()
{
var m_Watcher = new System.IO.FileSystemWatcher
{
Filter = "*.txt",
Path = @"C:\EventListenerFolder\",
NotifyFilter = NotifyFilters.LastAccess | NotifyFilters.LastWrite | NotifyFilters.FileName | NotifyFilters.DirectoryName
};
while (true)
{
WaitForChangedResult result = m_Watcher.WaitForChanged(WatcherChangeTypes.Created | WatcherChangeTypes.Changed);
if (!result.TimedOut)
{
OnChanged(result.Name);
}
}
}
private static void OnChanged(string file)
{
Console.WriteLine("EventListener Match File Found. FILE NAME : {0}", file);
try
{
string stringReceived = File.ReadAllText(file);
SendMailFunction(stringReceived);
File.Delete(file);
}
catch (IOException)
{
}
}
Ideally, you'd need to find some way to notify the method when your application was closing, so that it could stop the loop cleanly.
Finally, there is a known issue where the
FileSystemWatcher
can generate multiple events for the same change. There are numerous workarounds to be found - for example:
FileSystemWatcher Changed event is raised twice - Stack Overflow[
^]
FileSystemWatcher generates duplicate events – How to workaround – BizTalk 2006 – Windows SharePoint Services adapter[
^]