我尝试使用FileWatcher监视目录。当几个文件改变时,我必须将txt文件的添加数据插入数据库。但是在第二次尝试后它不起作用。因此,Windows显示此消息:此文件由另一个程序使用。我认为它与此代码中使用的ReaderWriterLockSlim类有关。请假设您的解决方案。我正在使用ASP.NET MVC,而不是Windows Forms App。 这里是代码
public class MultiWatcher : IDisposable
{
private List<string> filePaths;
private ReaderWriterLockSlim rwlock;
private System.Timers.Timer processTimer;
private string watchedPath;
private FileSystemWatcher watcher;
private int readLinesCount = 0;
public MultiWatcher(string watchedPath)
{
filePaths = new List<string>();
rwlock = new ReaderWriterLockSlim();
this.watchedPath = watchedPath;
InitFileSystemWatcher();
}
private void InitFileSystemWatcher()
{
watcher = new FileSystemWatcher();
watcher.Filter = "*.txt";
watcher.Changed += new FileSystemEventHandler(Watcher_FileChanged);
watcher.Error += Watcher_Error;
watcher.Path = watchedPath;
watcher.IncludeSubdirectories = true;
watcher.EnableRaisingEvents = true;
}
private void Watcher_Error(object sender, ErrorEventArgs e)
{
// Watcher crashed. Re-init.
InitFileSystemWatcher();
}
private void Watcher_FileChanged(object sender, FileSystemEventArgs e)
{
try
{
rwlock.EnterWriteLock();
filePaths.Add(e.Name);
if (processTimer == null)
{
// First file, start timer.
processTimer = new System.Timers.Timer(1000);
processTimer.Elapsed += ProcessQueue;
processTimer.Start();
}
else
{
// Subsequent file, reset timer.
processTimer.Stop();
processTimer.Start();
}
}
finally
{
rwlock.ExitWriteLock();
}
}
private void ProcessQueue(object sender, ElapsedEventArgs args)
{
try
{
//Console.WriteLine("Processing queue, " + filePaths.Count + " files created:");
rwlock.EnterReadLock();
foreach (string filePath in filePaths)
{
RecordEntry(filePath); // try to insert txt file data into database
}
filePaths.Clear();
}
finally
{
if (processTimer != null)
{
processTimer.Stop();
processTimer.Dispose();
processTimer = null;
}
rwlock.ExitReadLock();
}
}
//insert txt file data into database
private void RecordEntry(string fileName)
{
if (fileName != null)
{
using (var fs = new FileStream(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName), FileMode.Open, FileAccess.Read, FileShare.Read))
{
using (StreamReader reader = new StreamReader(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)))
{
Data_access da = new Data_access();
readLinesCount = da.GetReadLinesCount(fileName);
int totalLinesCount = File.ReadAllLines(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)).Length;
int newLinesCount = totalLinesCount - readLinesCount;
//var fileByLine = File.ReadLines(HostingEnvironment.MapPath("/Content/101_Sensors.txt")).Last();
var fileByLine = File.ReadLines(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)).Skip(readLinesCount).Take(newLinesCount);
var each = fileByLine.Select(l => l.Split('_'));
string[] parsedFileContent = new string[fileByLine.Count()];
foreach (var item in fileByLine)
{
parsedFileContent = item.Split('_');
da.AddParams(parsedFileContent, totalLinesCount, fileName);
}
da.SetReadLinesCount(totalLinesCount, fileName);
}
}
//using (StreamReader reader = new StreamReader(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)))
//{
// int totallinesCount = File.ReadAllLines(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)).Length;
// int newLinesCount = totallinesCount - readLinesCount;
// //var fileByLine = File.ReadLines(HostingEnvironment.MapPath("/Content/101_Sensors.txt")).Last();
// var fileByLine = File.ReadLines(HostingEnvironment.MapPath("~/Content/Sensors/" + fileName)).Skip(readLinesCount).Take(newLinesCount);
// var each = fileByLine.Select(l => l.Split('_'));
// string[] parsedFileContent = new string[fileByLine.Count()];
// foreach (var item in fileByLine)
// {
// parsedFileContent = item.Split('_');
// da.AddParams(parsedFileContent, totallinesCount, fileName, readLinesCount);
// }
//}
}
}
protected virtual void Dispose(bool disposing)
{
if (disposing)
{
if (rwlock != null)
{
rwlock.Dispose();
rwlock = null;
}
if (watcher != null)
{
watcher.EnableRaisingEvents = false;
watcher.Dispose();
watcher = null;
}
}
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
}