Initial commit
[mono.git] / mcs / class / referencesource / System / sys / system / configuration / DictionarySectionHandler.cs
1 //------------------------------------------------------------------------------
2 // <copyright file="DictionarySectionHandler.cs" company="Microsoft">
3 //     Copyright (c) Microsoft Corporation.  All rights reserved.
4 // </copyright>
5 //------------------------------------------------------------------------------
6
7 namespace System.Configuration {
8     using System.Collections;
9     using System.Collections.Specialized;
10     using System.Xml;
11     using System.Globalization;
12
13     /// <devdoc>
14     /// Simple dictionary config factory
15     /// config is a dictionary mapping key-&gt;value
16     /// 
17     ///     &lt;add key="name" value="text"&gt;  sets key=text 
18     ///     &lt;remove key="name"&gt;            removes the definition of key
19     ///     &lt;clear&gt;                        removes all definitions
20     /// 
21     /// </devdoc>
22     public class DictionarySectionHandler : IConfigurationSectionHandler {
23
24         /// <devdoc>
25         /// Given a partially composed config object (possibly null)
26         /// and some input from the config system, return a
27         /// further partially composed config object
28         /// </devdoc>
29         public virtual object Create(Object parent, Object context, XmlNode section) {
30             Hashtable res;
31
32             // start res off as a shallow clone of the parent
33
34             if (parent == null)
35                 res = new Hashtable(StringComparer.OrdinalIgnoreCase);
36             else
37                 res = (Hashtable)((Hashtable)parent).Clone();
38
39             // process XML
40
41             HandlerBase.CheckForUnrecognizedAttributes(section);
42
43             foreach (XmlNode child in section.ChildNodes) {
44
45                 // skip whitespace and comments, throws if non-element
46                 if (HandlerBase.IsIgnorableAlsoCheckForNonElement(child))
47                     continue;
48
49                 // handle <add>, <remove>, <clear> tags
50                 if (child.Name == "add") {
51                     HandlerBase.CheckForChildNodes(child);
52                     String key = HandlerBase.RemoveRequiredAttribute(child, KeyAttributeName);
53                     String value;
54                     if (ValueRequired)
55                         value = HandlerBase.RemoveRequiredAttribute(child, ValueAttributeName);
56                     else
57                         value = HandlerBase.RemoveAttribute(child, ValueAttributeName);
58                     HandlerBase.CheckForUnrecognizedAttributes(child);
59
60                     if (value == null)
61                         value = "";
62
63                     res[key] = value;
64                 }
65                 else if (child.Name == "remove") {
66                     HandlerBase.CheckForChildNodes(child);
67                     String key = HandlerBase.RemoveRequiredAttribute(child, KeyAttributeName);
68                     HandlerBase.CheckForUnrecognizedAttributes(child);
69
70                     res.Remove(key);
71                 }
72                 else if (child.Name.Equals("clear")) {
73                     HandlerBase.CheckForChildNodes(child);
74                     HandlerBase.CheckForUnrecognizedAttributes(child);
75                     res.Clear();
76                 }
77                 else {
78                     HandlerBase.ThrowUnrecognizedElement(child);
79                 }
80             }
81
82             return res;
83         }
84
85         /// <devdoc>
86         ///    Make the name of the key attribute configurable by derived classes.
87         /// </devdoc>
88         protected virtual string KeyAttributeName {
89             get { return "key";}
90         }
91
92         /// <devdoc>
93         ///    Make the name of the value attribute configurable by derived classes.
94         /// </devdoc>
95         protected virtual string ValueAttributeName {
96             get { return "value";}
97         }
98
99         // 
100         internal virtual bool ValueRequired {
101             get { return false; }
102         }
103     }
104 }