Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

XmlDocument Save keeps file open

I have a simple c# function that creates a basic XML file and saves:

private void CreateXMlFile(string Filename, string Name, string Company)
        {
            XmlDocument doc = new XmlDocument();
            XmlNode docNode = doc.CreateXmlDeclaration("1.0", "UTF-8", null);
            doc.AppendChild(docNode);

            XmlNode licenseNode = doc.CreateElement("license");
            doc.AppendChild(licenseNode);

            XmlNode node = doc.CreateElement("Name");
            node.AppendChild(doc.CreateTextNode(Name));
            licenseNode.AppendChild(node);

            node = doc.CreateElement("Company");
            node.AppendChild(doc.CreateTextNode(Company));
            licenseNode.AppendChild(node);


            doc.Save(Filename);
        }

When I try to edit or delete the file I always get following error:

The process cannot access the file because it is being used by another process.

XmlDocument doesnt have any inbuilt dispose or close routines and wondered how I can force the file to close before later editing or deleting it.

I have tried to save the file using StreamWriter:

StreamWriter outStream = System.IO.File.CreateText(outfile);
            outStream.Write(data);
            outStream.Close();

But this didnt make a difference with the same error.

Your advice is greatly accepted.

Thank you

like image 900
Belliez Avatar asked Feb 17 '12 10:02

Belliez


People also ask

Should I use XDocument or XmlDocument?

XDocument is from the LINQ to XML API, and XmlDocument is the standard DOM-style API for XML. If you know DOM well, and don't want to learn LINQ to XML, go with XmlDocument . If you're new to both, check out this page that compares the two, and pick which one you like the looks of better.

How do I close XmlDocument?

close(); The close method of the XMLDocument class takes no parameters. Calling the close method will not close the output stream you specified as a parameter to the XML document. You must close this stream separately.

What's the difference between XmlDocument and XmlReader?

Based on my understanding of the two classes, XmlReader should perform faster in my scenario because it reads through an XML document only once, never storing more than the current node in memory. On the contrary, XmlDocument stores the whole XML file in memory which has some performance overhead.


2 Answers

Send Stream to XmlDocument's Save method instead of file name.

    private static void Main(string[] args)
    {
        CreateXMlFile("c:\\test.xml", "testName", "testCompany");
    }

    private static void CreateXMlFile(string Filename, string Name, string Company)
    {
        XmlDocument doc = new XmlDocument();
        XmlNode docNode = doc.CreateXmlDeclaration("1.0", "UTF-8", null);
        doc.AppendChild(docNode);

        XmlNode licenseNode = doc.CreateElement("license");
        doc.AppendChild(licenseNode);

        XmlNode node = doc.CreateElement("Name");
        node.AppendChild(doc.CreateTextNode(Name));
        licenseNode.AppendChild(node);

        node = doc.CreateElement("Company");
        node.AppendChild(doc.CreateTextNode(Company));
        licenseNode.AppendChild(node);
        StreamWriter outStream = System.IO.File.CreateText(Filename);

        doc.Save(outStream);
        outStream.Close();
    }

I tried executing above code and it is working fine at my end.

like image 136
AshokD Avatar answered Sep 30 '22 08:09

AshokD


Your code is fine. I tested it on my machine and there is no lock left after Save().

Try to use Unlocker (http://www.softpedia.com/get/System/System-Miscellaneous/Unlocker.shtml) to check whether you are really the one who holds the lock.

Which .NET framework do you use? Theres also a report (http://bytes.com/topic/net/answers/467028-xmldocument-save-does-not-close-file-properly) which was not reproducable too.

like image 44
BlueM Avatar answered Sep 30 '22 07:09

BlueM