Using XML Key-Value Pairs in C# as a Dictionary

In C#, To represent key-value pairs in XML, you typically use elements and attributes. Here's a basic example of how you can store key-value pairs in XML.

Step 1. XML file look.

<?xml version="1.0" encoding="utf-8"?>

<KeyPairValueSettings>

  <KeyPairValueSetting key="Key1" value="Demo example 1" />
  <KeyPairValueSetting key="Key2" value="Demo example 2" />
  <KeyPairValueSetting key="Key3" value="Demo example 3" />
  <KeyPairValueSetting key="Key4" value="Demo example 4" />
  <KeyPairValueSetting key="Key5" value="" />

</KeyPairValueSettings>

Step 2. Create an interface for it.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace WpfXamlSettingsFile
{
    public interface ISettingsHelper
    {
        bool SetValue(eXmlSettingsKeys keyToUpdate, string newValue);
        string GetValue(eXmlSettingsKeys key);
    }
}

Step 3. Create Enum class.

public enum eXmlSettingsKeys

{
    Key1,
    Key2,
    Key3,
    Key4,
    Key5,
}

Step 4. Create implementation for the interface “ISettingsHelper”

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml;

namespace WpfXamlSettingsFile
{
    public class SettingsHelper : ISettingsHelper
    {
        private static Dictionary<eXmlSettingsKeys, string> dicXmlSettings;
        private static string initialDirectoryPath = @"D:\TestingProjects\XmlSetting";
        private static string filePath = @"D:\TestingProjects\XmlSetting\XmlSetiings.xml";
        private static readonly object lockObject = new object();
        private static XmlDocument xmlGlobalDocInstance = null;

        public static void LoadSettings()
        {
            xmlGlobalDocInstance = new XmlDocument();

            if (!File.Exists(filePath))
            {
                CreateAndSaveXmlDocument();
            }

            if (File.Exists(filePath))
            {
                foreach (eXmlSettingsKeys key in Enum.GetValues(typeof(eXmlSettingsKeys)))
                {
                    bool result = IsKeyExistInXml(key);
                    if (!result)
                    {
                        AddNewKeyToXml(key.ToString());
                    }
                }

                LoadXmlSettingDictionary();
            }
        }

        private static void LoadXmlSettingDictionary()
        {
            var settingResult = XmlSettingsFromFile(filePath);
            if (settingResult != null)
            {
                dicXmlSettings = settingResult;
            }
        }

        private static bool IsKeyExistInXml(eXmlSettingsKeys keyToCheck)
        {
            if (System.IO.File.Exists(filePath))
            {
                xmlGlobalDocInstance.Load(filePath);
                foreach (XmlNode node in xmlGlobalDocInstance.SelectNodes("//KeyPairValueSetting"))
                {
                    if (Enum.TryParse(node.Attributes["key"].Value, out eXmlSettingsKeys keyInXml))
                    {
                        if (keyInXml == keyToCheck)
                        {
                            return true;
                        }
                    }
                }
            }
            return false;
        }

        private static void AddNewKeyToXml(string newKey)
        {
            if (System.IO.File.Exists(filePath))
            {
                xmlGlobalDocInstance.Load(filePath);
            }
            else
            {
                XmlElement rootElement = xmlGlobalDocInstance.CreateElement("KeyPairValueSettings");
                xmlGlobalDocInstance.AppendChild(rootElement);
            }

            XmlElement newSettingElement = xmlGlobalDocInstance.CreateElement("KeyPairValueSetting");
            newSettingElement.SetAttribute("key", newKey);
            newSettingElement.SetAttribute("value", "");

            xmlGlobalDocInstance.DocumentElement?.AppendChild(newSettingElement);

            xmlGlobalDocInstance.Save(filePath);
        }

        private static void CreateAndSaveXmlDocument()
        {
            if (!Directory.Exists(initialDirectoryPath))
            {
                Directory.CreateDirectory(initialDirectoryPath);
            }

            XmlDeclaration xmlDeclaration = xmlGlobalDocInstance.CreateXmlDeclaration("1.0", "utf-8", null);
            xmlGlobalDocInstance.AppendChild(xmlDeclaration);

            XmlElement rootElement = xmlGlobalDocInstance.CreateElement("KeyPairValueSettings");
            xmlGlobalDocInstance.AppendChild(rootElement);

            xmlGlobalDocInstance.Save(filePath);
        }

        private static Dictionary<eXmlSettingsKeys, string> XmlSettingsFromFile(string filePath)
        {
            Dictionary<eXmlSettingsKeys, string> keyValuePairs = new Dictionary<eXmlSettingsKeys, string>();
            if (File.Exists(filePath))
            {
                xmlGlobalDocInstance.Load(filePath);
                foreach (XmlNode node in xmlGlobalDocInstance.SelectNodes("//KeyPairValueSetting"))
                {
                    string key = node.Attributes["key"].Value;
                    string value = node.Attributes["value"].Value;
                    keyValuePairs[(eXmlSettingsKeys)Enum.Parse(typeof(eXmlSettingsKeys), key)] = value;
                }
            }
            return keyValuePairs;
        }

        public string GetValue(eXmlSettingsKeys key)
        {
            string retValue = "";
            lock (lockObject)
            {
                if (dicXmlSettings.ContainsKey(key))
                {
                    retValue = dicXmlSettings[key];
                }
            }
            return retValue;
        }

        public bool SetValue(eXmlSettingsKeys keyToUpdate, string newValue)
        {
            bool retValue = false;

            dicXmlSettings[keyToUpdate] = newValue;
            lock (lockObject)
            {
                XmlElement rootElement;

                if (System.IO.File.Exists(filePath))
                {
                    xmlGlobalDocInstance.Load(filePath);
                    rootElement = xmlGlobalDocInstance.DocumentElement;
                    rootElement?.RemoveAll(); // Clear existing settings
                }
                else
                {
                    rootElement = xmlGlobalDocInstance.CreateElement("KeyPairValueSettings");
                    xmlGlobalDocInstance.AppendChild(rootElement);
                }

                foreach (var entry in dicXmlSettings)
                {
                    XmlElement settingElement = xmlGlobalDocInstance.CreateElement("KeyPairValueSetting");
                    settingElement.SetAttribute("key", entry.Key.ToString());
                    settingElement.SetAttribute("value", entry.Value);
                    rootElement?.AppendChild(settingElement);
                }

                xmlGlobalDocInstance.AppendChild(rootElement);
                xmlGlobalDocInstance.Save(filePath);
            }

            return retValue;
        }
    }
}

Note. Please substitute the following paths with your specific directory and file path.

private static string initialDirectoryPath = @"D:\TestingProjects\XmlSetting";

private static string filePath= @"D:\TestingProjects\XmlSetting\XmlSetiings.xml";

Step 5. Use Xml Get and Set method.

I utilized a WPF application to consume the GET and SET methods. Feel free to employ your own application for the same purpose.

Main window

Xaml

<Window x:Class="WpfXamlSettingsFile.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">

    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="40"/>
            <RowDefinition Height="40"/>
            <RowDefinition Height="40"/>
            <RowDefinition Height="40"/>
            <RowDefinition Height="40"/>
        </Grid.RowDefinitions>

        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="*"/>
            <ColumnDefinition Width="*"/>
        </Grid.ColumnDefinitions>

        <TextBlock Text="Enum List" FontSize="20" FontWeight="Bold" Grid.Column="0" Grid.Row="0"/>
        <ComboBox Grid.Row="0" Grid.Column="1" SelectionChanged="ComboBox_SelectionChanged">
            <ComboBoxItem>Key1</ComboBoxItem>
            <ComboBoxItem>Key2</ComboBoxItem>
            <ComboBoxItem>Key3</ComboBoxItem>
            <ComboBoxItem>Key4</ComboBoxItem>
        </ComboBox>

        <TextBlock Text="Set Value" FontSize="20" FontWeight="Bold" Grid.Column="0" Grid.Row="1"/>
        <TextBox x:Name="TxtSetValue" Grid.Row="1" Grid.Column="1"/>

        <TextBlock Text="Get Value" FontSize="20" FontWeight="Bold" Grid.Column="0" Grid.Row="2"/>
        <TextBox x:Name="TxtGetValue" Grid.Row="2" Grid.Column="1"/>

        <Button x:Name="BtnGetValue" Content="Get Xml Value" FontSize="20" Grid.Column="0" Grid.Row="3" Click="BtnGetValue_Click"/>
        <Button x:Name="BtnSetDefaultValue" Content="SetXml Value" Grid.Column="1" FontSize="20" Grid.Row="3" Click="BtnSetDefaultValue_Click"/>
    </Grid>
</Window>

Xaml.cs

using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace WpfXamlSettingsFile
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        string selectedEnumValue = string.Empty;
        SettingsHelper SettingsHelper = new SettingsHelper();

        public MainWindow()
        {
            InitializeComponent();
            SettingsHelper.LoadSettings();
        }

        private void ComboBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            ComboBox comboBox = (ComboBox)sender;

            if (comboBox.SelectedItem != null)
            {
                // Get the selected item's value as a string
                selectedEnumValue = ((ComboBoxItem)comboBox.SelectedItem).Content.ToString();
            }
        }

        private void GetValue_Click(object sender, RoutedEventArgs e)
        {
            // Your implementation for GetValue_Click
        }

        private void SetDefaultValue_Click(object sender, RoutedEventArgs e)
        {
            // Your implementation for SetDefaultValue_Click
        }

        private void BtnGetValue_Click(object sender, RoutedEventArgs e)
        {
            eXmlSettingsKeys enumValue = (eXmlSettingsKeys)Enum.Parse(typeof(eXmlSettingsKeys), selectedEnumValue);
            TxtGetValue.Text = SettingsHelper.GetValue(enumValue);
        }

        private void BtnSetDefaultValue_Click(object sender, RoutedEventArgs e)
        {
            eXmlSettingsKeys enumValue = (eXmlSettingsKeys)Enum.Parse(typeof(eXmlSettingsKeys), selectedEnumValue);
            bool result = SettingsHelper.SetValue(enumValue, TxtSetValue.Text);
        }
    }
}

Repository path: https://github.com/OmatrixTech/XMLSettingExample


Similar Articles