Pregunta

Quiero escribir algunas estadísticas en un archivo de texto cada vez que una persona carga una página. Pero de vez en cuando me aparece el error 'No se pudo abrir el archivo, ya está en uso'. No puedo 100% replicar este error, es muy errático. Mi código es

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

Mi pregunta es, ¿cómo puedo bloquear y desbloquear el archivo para dejar de recibir los errores erráticos?

Gracias

¿Fue útil?

Solución

Tendrá que manejar la excepción y generar algo de manejo para volver a intentar escribir en el archivo después de un breve intervalo aleatorio.

Si obtiene demasiada contención, entonces podría tener más sentido registrarlo en una tabla en una base de datos y crear un proceso para exportar a un archivo (si aún es necesario)

Otros consejos

Si dos o más solicitudes llegan a su servidor web aproximadamente al mismo tiempo, todas intentarán abrir el mismo archivo. Deberá crear nombres de archivo únicos para cada solicitud.

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

Tres cosas importantes aquí:

  1. Uso de IO.FileShare.ReadWrite para permitir múltiples escritores en el archivo a la vez.
  2. La instrucción Using para asegurarse de que la secuencia se cierra inmediatamente, incluso si se produce una excepción. Esto minimizará las colisiones
  3. TextWriterTraceListener creará un archivo temporal para usted si no puede abrir el archivo que solicita, para asegurarse de que el mensaje no se pierda.

No he tenido ningún problema con información corta usando: File.AppendAllText (ruta, información);

Con respecto al comentario que causa bloqueos, desde el reflector usa las mismas opciones explicadas muy bien por Joel. No utiliza el escritor de rastreo, por lo que no se enviará a un archivo temporal en el caso de que una carga alta / contenido grande cause problemas.

Si la información es grande, realmente desea archivos separados. Para una carga alta, iría con la sugerencia de Joel y crearía un archivo temporal, que se puede hacer alternativamente capturando la excepción en File.AppendAllText y usando el mismo File.AppeandAllText con un nombre de archivo único.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top