Truncate the beginning of a log file in .NET.

I have a VB.NET application that writes status to a log file in text format. Over time, the file becomes large, and I would like to know if there is an effective way to truncate the beginning of the file.

To simplify the task, I want to specify the file size (say, 2-3 mb), and I write the log using StreamWriter:

Using strm As New IO.StreamWriter(filelocation.log, True)
    strm.WriteLine("msg to write")
    strm.Close()
End Using

I thought about using strm.BaseStream.Lengthit to determine which part of the file was cut, but with the help of .SetLengthit it will cut from the end - not the desired result.

+3
source share
6 answers

log4net, . , . , , . , :

<log4net>
    <appender name="GeneralLog" type="log4net.Appender.RollingFileAppender">
        <file value="ClientTools.log"/>
        <appendToFile value="true"/>
        <maximumFileSize value="3000KB"/>
        <rollingStyle value="Size"/>
        <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%d{HH:mm:ss} [%t] %-5p %c - %m%n"/>
        </layout>
    </appender>
    <root>
        <level value="DEBUG"/>
        <appender-ref ref="GeneralLog"/>
    </root>
    <logger name="NHibernate" additivity="false">
        <level value="DEBUG"/>
        <appender-ref ref="GeneralLog"/>
    </logger>
</log4net>

app.config ClientTools.log , , , 3 .

, Init() -: ILog;

public void InitiateLogging()
{
    log4net.Config.XmlConfigurator.Configure();
    log = LogManager.GetLogger("MyApplication");
}

, - , :

log.Info("No resources available.");
// or
log.Fatal(exception.Message);
// or
log.Warn("Something bad may happen here.");

, , .. DRY.

+2

, 3 , , . - ( #):

System.IO.FileInfo f = new FileInfo(file_name);
if (f.Length > (1024 * 1024 * 3)){ 
    // File is over 3MB
    //
    // Perhaps back it up?
    // Then...
    using (StreamWriter sw = new StreamWriter(file_name, false))
    {
        // Overwrite the contents....
    }
}else{
    // Open as normal for append mode
}

, , , .

0

  • (A)
  • (B).
  • B.
  • A.
  • B A.
0

( ) :

  If New FileInfo("yourFilePathHere").Length > (2 ^ 21) Then
        File.WriteAllText("yourFilePathHere", _
        File.ReadAllText("yourFilePathHere").Substring(ToInt32(2 ^ 21)))
  End If
0

, :

private void ShrinkLogFile()
{
    var file = new FileInfo(Filename);
    if (file.Exists && file.Length > MaxFileSize)
    {
        MoveLinesToBeginningStartingAt(file.Length - (MaxFileSize / 2));
    }
}
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2202:Do not dispose objects multiple times")]
private void MoveLinesToBeginningStartingAt(long offsetToKeep)
{
    // Open the file twice.  We'll read from the end and write to the beginning.
    using (var fileReader = new FileStream(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
    using (var fileWriter = new FileStream(Filename, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite))
    {
        // Find the end of the first line so we start at the beginning of a new line.
        fileReader.Position = offsetToKeep;
        using (var reader = new StreamReader(fileReader, Encoding.UTF8, true, 512, true))   // Note that we leave fileReader open...
        {
            offsetToKeep += reader.ReadLine().Length;       // Advance offset past the (probably) partial first line
            offsetToKeep += Environment.NewLine.Length;     // Advance past the newline
        }

        // Go to new position and copy the rest of the file to the beginning of the same file.
        fileReader.Position = offsetToKeep;
        fileReader.CopyTo(fileWriter);

        // Truncate the file
        var fileInfo = new FileInfo(Filename);
        fileWriter.SetLength(fileInfo.Length - offsetToKeep);
    }
}

, :

  • (xxx), , , "Shrink".
  • , .
0

, . 60 .

dim LogPath as string = "YourLogPath"    
Dim lineCount = File.ReadAllLines(LogPath).Length

        If lineCount > 60 Then ' because I want my log to be 60 lines long
            Dim delLineCount As Integer = lineCount - 60
            Dim lines As List(Of String) = New List(Of String)(File.ReadAllLines(LogPath))
            lines.RemoveRange(0, delLineCount)
            File.WriteAllLines(LogPath, lines.ToArray())
        End If
0

Source: https://habr.com/ru/post/1734255/


All Articles