Home > Enterprise >  StreamWriter adds extra character(s) on new line(s) at the end of file
StreamWriter adds extra character(s) on new line(s) at the end of file

Time:04-29

I'm trying to modify an .ini file, in C# with .NET 5.0, using FileStream and StreamReader / StreamWriter. I just need to modify the first line of the file so I read the entire file into a list of strings called strList, modify the first line, and then write it all back to the same file.

List<string> strList = new List<string>();

using (FileStream fs = File.OpenRead(@"C:\MyFolder\test.ini"))
{
    using (StreamReader sr = new StreamReader(fs))
    {
        while (!sr.EndOfStream)
        {
            strList.Add(sr.ReadLine());
        }
    }
}

strList[0] = "test01";

using (FileStream fs = File.OpenWrite(@"C:\MyFolder\test.ini"))
{
    using (StreamWriter sw = new StreamWriter(fs))
    {
        for (int x = 0; x < ewsLines.Count; x  )
        {          
            sw.WriteLine(strList[x]);            
        }
    }
}

The issue I'm running into is that I'll have new character(s) at the end of my file on new line(s). I verified that the number of lines I read from the file matches what is in the file and that the for loop only writes that same number of lines back into the file. I don't have any issues writing other strings except for "test01". This string is the only one that causes the issue that I just described. It seems to be grabbing characters from the last line like R or LAYER from MULTI_LAYER.

Ex 1: This

S10087_U1
Cq4InEq=TRUE
XtrVer=5.5
IOCUPDATEMDB=TRUE
ARCHITECTURE=MULTI_LAYER

Becomes this

test01
Cq4InEq=TRUE
XtrVer=5.5
IOCUPDATEMDB=TRUE
ARCHITECTURE=MULTI_LAYER
R

Ex 2: This

test01 - Copy
Cq4InEq=TRUE
XtrVer=5.5
IOCUPDATEMDB=TRUE
ARCHITECTURE=MULTI_LAYER
ER

Becomes this

test01
Cq4InEq=TRUE
XtrVer=5.5
IOCUPDATEMDB=TRUE
ARCHITECTURE=MULTI_LAYER
LAYER

Replacing the StreamWriter portion with the following seems to fix the issue but I'm trying to figure out why using StreamWriter doesn't work as I expect it to.

File.WriteAllLines(@"C:\MyFolder\test.ini", strList);

CodePudding user response:

This is because you're using File.OpenWrite. From the remarks in the documentation:

The OpenWrite method opens a file if one already exists for the file path, or creates a new file if one does not exist. For an existing file, it does not append the new text to the existing text. Instead, it overwrites the existing characters with the new characters. If you overwrite a longer string (such as "This is a test of the OpenWrite method") with a shorter string (such as "Second run"), the file will contain a mix of the strings ("Second runtest of the OpenWrite method").

While you could just change your code to use File.Create instead, I'd suggest changing the code more significantly - not just the writing, but the reading too:

string path = @"C:\MyFolder\test.ini";
var lines = File.ReadAllLines(path);
lines[0] = "test01";
File.WriteAllLines(path, lines);

That's much simpler code to do the same thing.

The half-way house between the two would be to use File.OpenText (to return a StreamWriter) and File.CreateText (to return a StreamWriter). There's no need to do the wrapping yourself.

  • Related