我想在每次加载页面时向文本文件写一些统计信息。但每隔一段时间我就会遇到“无法打开文件,已经在使用中”的错误类型。我无法100%复制这个错误,这是非常不稳定的。我的代码是
Public Sub WriteStats(ByVal ad_id As Integer)
Dim ad_date As String = Now.Year & Now.Month
Dim FILENAME As String = Server.MapPath("text/BoxedAds.txt")
Dim objStreamWriter As StreamWriter
objStreamWriter = File.AppendText(FILENAME)
objStreamWriter.WriteLine(ad_id & ";" & ad_date)
objStreamWriter.Close()
End Sub
我的问题是,如何锁定和解锁文件,以便我不再获得不稳定的错误?
由于
答案 0 :(得分:4)
如果两个或多个请求几乎同时点击您的Web服务器,他们都会尝试打开同一个文件。您需要为每个请求创建唯一的文件名。
答案 1 :(得分:4)
Public Sub WriteStats(ByVal ad_id As Integer)
Dim ad_date As String = Now.Year & Now.Month
Dim FILENAME As String = Server.MapPath("text/BoxedAds.txt")
Dim index As Integer
Using fs As New IO.FileStream(FILENAME, IO.FileMode.Append, IO.FileAccess.Write, IO.FileShare.ReadWrite), _
tl As New TextWriterTraceListener(fs)
index = Trace.Listeners.Add(tl)
Trace.WriteLine(ad_id & ";" & ad_date)
Trace.Listeners(index).Flush()
Trace.Flush()
End Using
Trace.Listeners.RemoveAt(index)
End Sub
这里有三件重要的事情:
答案 2 :(得分:1)
您将不得不处理异常并构建一些处理以在短暂的随机间隔后重新尝试写入文件。
如果你得到太多的争用,那么将它记录到数据库中的表并创建一个导出到文件的进程(如果仍需要它)可能更有意义
答案 3 :(得分:0)
我使用以下短信息时没有遇到任何问题: File.AppendAllText(path,info);
关于它引起锁定的评论,来自反射器它使用了Joel非常好地解释的相同选项。它不使用跟踪编写器,因此在高负载/大内容导致故障的情况下它不会输出到临时文件。
如果信息很大,你真的想要单独的文件。对于高负载,我会使用Joel的建议并创建一个临时文件,也可以通过捕获File.AppendAllText上的异常,并使用具有唯一文件名的相同File.AppeandAllText来完成。