Fast Reading and Writing of Configuration Files

Environment: Configuration Files, INIs

This is similar to the article published by Ayende Rahien on A C# Configuration File Reader that doesn’t use the Win32 API function. The only difference is that this code is quick and doesn’t depend on the data in the memory for a long time because the configuration file might be used or changed by some other application before the application process it. So, the following code just reads the file sequentially and, when it finds the section or key, takes the action and closes the file then and there itself. The drawback of this operation is that every time you call the function, it will open the file and close it with or without modifying. That’s a tradeoff for making sure that the configuration file is reflecting changes once the function is completed.

using System;
using System.IO;
using System.Collections.Specialized;

namespace IniMgr
{
   public class IniTask
   {
      public static void SetIniString(string sFile, string Sec,
                                      string Key, string Val)
      {
         StreamReader sr = null;
         string newLineChars = "rn";    // define newline chars.

         // But find the default new line chars from the
         // System.IO.TextWriter
         if(true)
         {
            StringWriter tw = new StringWriter();
            newLineChars    = tw.NewLine;
         }

         string slines = null;
         if (File.Exists(sFile))
         {
            bool reWrite = false;
            using ( sr = new StreamReader(sFile))
            {
               String line;
               bool foundSection = false;
               while ((line = sr.ReadLine()) != null)
               {
                  line = line.Trim();
                  if(line.Length > 1)
                  {
                     if(line[0] == '[')
                     {
                        int end = line.IndexOf("]");
                        if(end != -1)
                        {
                           string section = line.Substring(1,
                                                           end-1);
                           if(String.Compare(section,Sec,true)==0)
                           {
                              foundSection = true;
                              slines += line + newLineChars;
                              continue;
                           }
                           else
                           {
                              if(foundSection == true)
                              {
                                 // we did not find our key,
                                 // so we add one
                                 slines += Key + "=" + Val
                                               + newLineChars;;
                                 slines += line + newLineChars;
                                 line    = sr.ReadToEnd();
                                 slines += line;
                                 reWrite = true;
                                 break;
                              }
                           }
                        }
                     }
                     if(foundSection == true)
                     {
                        string [] pair = line.Split('=');
                        if(pair.Length > 1)
                        {
                           if(String.Compare(pair[0], Key,true)
                                     == 0)
                           {
                              line = Key + "=" + Val
                                               + newLineChars;
                              slines += line;
                              line    = sr.ReadToEnd();
                              slines += line;
                              reWrite = true;
                              break;
                           }
                        }
                     }
                  }
                  slines += line + newLineChars;
               }
               if(foundSection == false)
               {
                  slines += "[" + Sec + "]" + newLineChars;
                  slines += Key + "=" + Val  + newLineChars;
                  reWrite = true;
               }
               if(foundSection == true && reWrite == false)
               {
                  slines += Key + "=" + Val  + newLineChars;
                  reWrite = true;
               }
            }
            if( reWrite == true)
            {
               using (StreamWriter sw = new StreamWriter(sFile))
               {
                  sw.Write(slines);
               }
            }
         }
         else
         {
            slines = "[" + Sec + "]" + newLineChars;
            slines += Key + "=" + Val  + newLineChars;
            using (StreamWriter sw = new StreamWriter(sFile))
            {
               sw.Write(slines);
            }

         }
      }
      public static string GetIniString(string sFile, string Sec,
                                        string Key, string Val)
      {
         StreamReader sr = null;
         if (File.Exists(sFile))
         {
            using ( sr = new StreamReader(sFile))
            {
               String line;
               // Read and display lines from the file until
               // the end of the file is reached.
               bool foundSection = false;
               while ((line = sr.ReadLine()) != null)
               {
                  line = line.Trim();
                  if(line.Length > 1)
                  {
                     if(line[0] == '[')
                     {
                        int end = line.IndexOf("]");
                        if(end != -1)
                        {
                           string section = line.Substring(1,
                                                           end-1);
                           if(String.Compare(section, Sec, true)
                              == 0)
                           {
                              foundSection = true;
                              continue;
                           }
                           else
                              foundSection = false;
                        }
                     }
                     if(foundSection == true)
                     {
                        string [] pair = line.Split('=');
                        if(pair.Length > 1)
                        {
                           if(String.Compare(pair[0], Key, true)
                               == 0)
                           {
                              Val = pair[1];
                              break;
                           }
                        }
                     }
                  }
               }
            }
         }
         return Val;
      }
      // some extra functions
      public static StringCollection GetSections(string sFile)
      {
         StreamReader sr       = null;
         StringCollection myAL = new StringCollection();
         if (File.Exists(sFile))
         {

            using ( sr = new StreamReader(sFile))
            {
               String line;
               // Read and display lines from the file until the
               // end of the file is reached.
               while ((line = sr.ReadLine()) != null)
               {
                  line = line.Trim();
                  if(line.Length > 1)
                  {
                     if(line[0] == '[')
                     {
                        int end = line.IndexOf("]");
                        if(end != -1)
                        {
                           string section = line.Substring(1,
                                                           end-1);
                           myAL.Add(section);
                        }
                     }
                  }
               }
            }
         }
         return myAL;
      }
      public static StringCollection GetSectionKeys(string sFile,
                                                    string Sec)
      {
         StreamReader sr = null;
         StringCollection myAL = new StringCollection();
         if (File.Exists(sFile))
         {
            using ( sr = new StreamReader(sFile))
            {
               String line;
               // Read and display lines from the file until
               // the end of the file is reached.
               bool foundSection = false;
               while ((line = sr.ReadLine()) != null)
               {
                  line = line.Trim();
                  if(line.Length > 1)
                  {
                     if(line[0] == '[')
                     {
                        int end = line.IndexOf("]");
                        if(end != -1)
                        {
                           string section = line.Substring(1,
                                                           end-1);
                           if(String.Compare(section, Sec, true)
                              == 0)
                           {
                              foundSection = true;
                              continue;
                           }
                           else
                           {
                              if(foundSection == true)
                              {
                                 break;
                              }
                              foundSection = false;
                           }
                        }
                     }
                     if(foundSection == true)
                     {
                        string [] pair = line.Split('=');
                        if(pair.Length > 1)
                        {
                           myAL.Add(pair[0]);
                        }
                     }
                  }
               }
            }
         }
         return myAL;
      }
   }
}

For simplicity, this code doesn’t have error checks.

More by Author

Get the Free Newsletter!

Subscribe to Developer Insider for top news, trends & analysis

Must Read