如何下载从log4Net生成的日志文件

时间:2015-01-14 10:04:00

标签: c# asp.net-mvc logging log4net

我在ASP.NET MVC 4应用程序中使用log4net,我正在尝试从log4Net下载生成的日志文件。

我想用FileResult下载日志文件,例如:

[Authorize(Roles = "Admin")]
public FileResult DownloadUserInterfaceLog()
{
    // Get the path of the log file
    string path = (LogManager.GetCurrentLoggers()[0].Logger.Repository.GetAppenders()[0] as FileAppender).File;
    // Get the file
    byte[] fileBytes = System.IO.File.ReadAllBytes(path);
    string fileName = "Log.txt";
    // Return the expected file
    return File(fileBytes, System.Net.Mime.MediaTypeNames.Application.Octet, fileName);
}

我的问题是当我调用System.IO.File.ReadAllBytes(path);时出现异常,导致日志文件已被其他进程使用。

我已经放<lockingModel value="log4net.Appender.FileAppender+MinimalLock" /> (which should release the file after any modification) in my Web.Config但没有成功。

Web.Config中的log4Net配置开始:

<log4net>
    <appender name="Appender-root" type="log4net.Appender.RollingFileAppender">
        <lockingModel value="log4net.Appender.FileAppender+MinimalLock" />
        <file value="Path..." />
        <appendToFile value="true" />

2 个答案:

答案 0 :(得分:2)

您需要在访问文件之前关闭Appender:

((FileAppender)LogManager.GetCurrentLoggers()[0].Logger.Repository.GetAppenders()[0]).Close()

答案 1 :(得分:2)

Here是一篇关于类似问题的文章。

  

File.ReadAllBytes()函数被编写为使用类似的调用   以下实例化FileStream:

FileStream fs = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read)
     

请注意,FileShare被指定为Read。这意味着如果你有   另一段代码同时写入同一个文件,你   即使另一段代码创建了,也会出错   FileStream通过将共享模式指定为“ReadWrite”,如下所示:

FileStream fs = new FileStream(path, FileMode.Create, FileAccess.Write, FileShare.ReadWrite)

解决方案是编写自己的自定义ReadAllBytes:

public static byte[] ReadAllBytes(String path)
{
    byte[] bytes;
    using (FileStream fs = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
    {
        int index = 0;
        long fileLength = fs.Length;
        if (fileLength > Int32.MaxValue)
            throw new IOException(“File too long”);
        int count = (int)fileLength;
        bytes = new byte[count];
        while (count > 0)
        {
            int n = fs.Read(bytes, index, count);
            if (n == 0)
                throw new InvalidOperationException(“End of file reached before expected”);
            index += n;
            count -= n;
        }
    }
return bytes;
}