Reputation:
I've been working on this small piece of code that seems trivial but still, i cannot really see where is the problem. My functions do a pretty simple thing. Opens a file, copy its contents, replace a string inside and copy it back to the original file (a simple search and replace inside a text file then). I didn't really know how to do that as I'm adding lines to the original file, so I just create a copy of the file, (file.temp) copy also a backup (file.temp) then delete the original file(file) and copy the file.temp to file. I get an exception while doing the delete of the file. Here is the sample code:
private static bool modifyFile(FileInfo file, string extractedMethod, string modifiedMethod)
{
Boolean result = false;
FileStream fs = new FileStream(file.FullName + ".tmp", FileMode.Create, FileAccess.Write);
StreamWriter sw = new StreamWriter(fs);
StreamReader streamreader = file.OpenText();
String originalPath = file.FullName;
string input = streamreader.ReadToEnd();
Console.WriteLine("input : {0}", input);
String tempString = input.Replace(extractedMethod, modifiedMethod);
Console.WriteLine("replaced String {0}", tempString);
try
{
sw.Write(tempString);
sw.Flush();
sw.Close();
sw.Dispose();
fs.Close();
fs.Dispose();
streamreader.Close();
streamreader.Dispose();
File.Copy(originalPath, originalPath + ".old", true);
FileInfo newFile = new FileInfo(originalPath + ".tmp");
File.Delete(originalPath);
File.Copy(fs., originalPath, true);
result = true;
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
return result;
}`
And the related exception
System.IO.IOException: The process cannot access the file 'E:\mypath\myFile.cs' because it is being used by another process.
at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
at System.IO.File.Delete(String path)
at callingMethod.modifyFile(FileInfo file, String extractedMethod, String modifiedMethod)
Normally these errors come from unclosed file streams, but I've taken care of that. I guess I've forgotten an important step but cannot figure out where. Thank you very much for your help,
Upvotes: 27
Views: 159445
Reputation: 1
My reputation being too small to comment an answer, here is my feedback concerning roquen answer (using settings on xmlwriter to force the stream to close): it works perfectly and it made me save a lot of time. roquen's example requires some adjustment, here is the code that works on .NET framework 4.8 :
XmlWriterSettings settings = new XmlWriterSettings();
settings.CloseOutput = true;
writer = XmlWriter.Create(stream, settings);
Upvotes: 0
Reputation: 1
After creating a file you must force the stream to release the resources:
//FSm is stream for creating file on a path//
System.IO.FileStream FS = new System.IO.FileStream(path + fname,
System.IO.FileMode.Create);
pro.CopyTo(FS);
FS.Dispose();
Upvotes: 0
Reputation: 136
System.Drawing.Image FileUploadPhoto = System.Drawing.Image.FromFile(location1);
FileUploadPhoto.Save(location2);
FileUploadPhoto.Dispose();
Upvotes: -2
Reputation: 351
Try this: It works in any case, if the file doesn't exists, it will create it and then write to it. And if already exists, no problem it will open and write to it :
using (FileStream fs= new FileStream(@"File.txt",FileMode.Create,FileAccess.ReadWrite))
{
fs.close();
}
using (StreamWriter sw = new StreamWriter(@"File.txt"))
{
sw.WriteLine("bla bla bla");
sw.Close();
}
Upvotes: 3
Reputation: 41
After coming across this error and not finding anything on the web that set me right, I thought I'd add another reason for getting this Exception - namely that the source and destination paths in the File Copy command are the same. It took me a while to figure it out, but it may help to add code somewhere to throw an exception if source and destination paths are pointing to the same file.
Good luck!
Upvotes: 4
Reputation: 191
I realize that I is kinda late, but still better late than never. I was having similar problem recently. I used XMLWriter
to subsequently update XML file and was receiving the same errors. I found the clean solution for this:
The XMLWriter
uses underlying FileStream
to access the modified file. Problem is that when you call XMLWriter.Close()
method, the underlying stream doesn't get closed and is locking the file. What you need to do is to instantiate your XMLWriter
with settings and specify that you need that underlying stream closed.
Example:
XMLWriterSettings settings = new Settings();
settings.CloseOutput = true;
XMLWriter writer = new XMLWriter(filepath, settings);
Hope it helps.
Upvotes: 19
Reputation: 16848
Sounds like an external process (AV?) is locking it, but can't you avoid the problem in the first place?
private static bool modifyFile(FileInfo file, string extractedMethod, string modifiedMethod)
{
try
{
string contents = File.ReadAllText(file.FullName);
Console.WriteLine("input : {0}", contents);
contents = contents.Replace(extractedMethod, modifiedMethod);
Console.WriteLine("replaced String {0}", contents);
File.WriteAllText(file.FullName, contents);
return true;
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
return false;
}
}
Upvotes: 23
Reputation: 12015
Are you running a real-time antivirus scanner by any chance ? If so, you could try (temporarily) disabling it to see if that is what is accessing the file you are trying to delete. (Chris' suggestion to use Sysinternals process explorer is a good one).
Upvotes: 3
Reputation: 180788
It worked for me.
Here is my test code. Test run follows:
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
FileInfo f = new FileInfo(args[0]);
bool result = modifyFile(f, args[1],args[2]);
}
private static bool modifyFile(FileInfo file, string extractedMethod, string modifiedMethod)
{
Boolean result = false;
FileStream fs = new FileStream(file.FullName + ".tmp", FileMode.Create, FileAccess.Write);
StreamWriter sw = new StreamWriter(fs);
StreamReader streamreader = file.OpenText();
String originalPath = file.FullName;
string input = streamreader.ReadToEnd();
Console.WriteLine("input : {0}", input);
String tempString = input.Replace(extractedMethod, modifiedMethod);
Console.WriteLine("replaced String {0}", tempString);
try
{
sw.Write(tempString);
sw.Flush();
sw.Close();
sw.Dispose();
fs.Close();
fs.Dispose();
streamreader.Close();
streamreader.Dispose();
File.Copy(originalPath, originalPath + ".old", true);
FileInfo newFile = new FileInfo(originalPath + ".tmp");
File.Delete(originalPath);
File.Copy(originalPath + ".tmp", originalPath, true);
result = true;
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
return result;
}
}
}
C:\testarea>ConsoleApplication1.exe file.txt padding testing
input : <style type="text/css">
<!--
#mytable {
border-collapse: collapse;
width: 300px;
}
#mytable th,
#mytable td
{
border: 1px solid #000;
padding: 3px;
}
#mytable tr.highlight {
background-color: #eee;
}
//-->
</style>
replaced String <style type="text/css">
<!--
#mytable {
border-collapse: collapse;
width: 300px;
}
#mytable th,
#mytable td
{
border: 1px solid #000;
testing: 3px;
}
#mytable tr.highlight {
background-color: #eee;
}
//-->
</style>
Upvotes: 4
Reputation: 1821
The code works as best I can tell. I would fire up Sysinternals process explorer and find out what is holding the file open. It might very well be Visual Studio.
Upvotes: 5