如何使用filestream / streamwriter处理并发文件访问?

时间:2009-12-10 17:32:32

标签: vb.net concurrency .net-2.0 filestream streamwriter

我正在编写一个审计文件,该文件在每个用户使用我的应用程序时为应用程序编写应用程序中的多个变量的用户名,时间和旧/更改值。它使用FileStreamStreamWriter来访问审核文件。每个用户的所有审核都将写入同一文件。

问题是,当两个用户同时更新此审核文件时,每个变量的“旧值”在用户之间混淆。为什么会这样,你怎么解决这里的并发问题呢?

一些代码,为简洁而缩短......

Dim fs As FileStream
Dim w As StreamWriter

Public Sub WriteAudit(ByVal filename As String, ByVal username As String, ByVal oldAddress As String, ByVal newAddress As String, ByVal oldCity As String, ByVal newCity As String)
    Dim now As DateTime = DateTime.Now
    Dim audit As String = ""
    audit += now + "," + username + "," + oldAddress + "," + newAddress + "," + oldCity + "," + newCity

    fs = New FileStream(filename, FileMode.Append)
    w = New StreamWriter(fs)
    w.WriteLine(audit)
    w.Close()
    fs.Close()
End Sub

它存在于AuditLogger类中,该类通过实例变量引用(每次访问函数时重新分配)。

3 个答案:

答案 0 :(得分:2)

你可以试试这个:

TextWriter tw = TextWriter.Synchronized(File.AppendText(filePath));

File.AppendText()方法返回一个StreamWriter对象,TextWriter.Synchronized()方法包装该对象以创建一个可以像StreamWriter一样使用的线程安全的TextWriter。

答案 1 :(得分:2)

重构应用程序,这样您就不必每次都创建AuditLogger类的新实例。直接使用singleton patterndependency-injection框架在整个应用程序中使用相同的实例。

从那里开始,实现变得更加容易:用lock语句包围写操作,或者使用罗伯特答案中提到的TextWriter.Synchronized

这篇文章可能有用:

答案 2 :(得分:0)

有两种方式:

首先,使用共享数据库而不是文件。即使是简单的访问数据库也可以比磁盘上的文件更优雅地处理多个用户。

其次,您可以为每个用户使用单独的文件吗?也许将它存储在%APPDATA%文件夹中?或者也许在某个地方的网络共享上?