2 // System.Data.OleDb.OleDbConnection
5 // Konstantin Triger <kostat@mainsoft.com>
6 // Boris Kirzner <borisk@mainsoft.com>
8 // (C) 2006 Mainsoft Corporation (http://www.mainsoft.com)
12 // Permission is hereby granted, free of charge, to any person obtaining
13 // a copy of this software and associated documentation files (the
14 // "Software"), to deal in the Software without restriction, including
15 // without limitation the rights to use, copy, modify, merge, publish,
16 // distribute, sublicense, and/or sell copies of the Software, and to
17 // permit persons to whom the Software is furnished to do so, subject to
18 // the following conditions:
20 // The above copyright notice and this permission notice shall be
21 // included in all copies or substantial portions of the Software.
23 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
26 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
27 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
28 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
29 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
33 using System.Collections;
34 using System.Collections.Specialized;
36 using System.Globalization;
39 namespace Mainsoft.Data.Configuration
41 public class ConnectionStringDictionary: IConnectionStringDictionary
45 private readonly IDictionary _dictionary;
46 private readonly NameValueCollection _mapping;
47 private readonly NameValueCollection _actualKeys;
48 const string DataDirectoryPlaceholder = "|DataDirectory|";
54 public ConnectionStringDictionary(string connectionString, NameValueCollection defaultMapping)
56 _actualKeys = new NameValueCollection(StringComparer.OrdinalIgnoreCase);
57 _dictionary = Parse (connectionString);
58 _mapping = defaultMapping;
61 #endregion // Constructors
65 public string GetConnectionStringKey (string key)
67 string cached = _actualKeys [key];
72 for(int i = 0, c = _mapping.Keys.Count; i < c; i++) {
73 if (string.Compare(key, _mapping.Keys[i], StringComparison.OrdinalIgnoreCase) == 0) {
74 string[] values = _mapping.GetValues(i);
75 for(int j = 0; j < values.Length; j++) {
76 string actualKey = values[j];
77 if (_dictionary.Contains (actualKey)) {
78 _actualKeys.Add (key, actualKey);
85 if (_dictionary.Contains(key))
91 public object GetValue (string key)
93 return _dictionary [key];
96 public static IDictionary Parse (string connectionString)
98 IDictionary userParameters = new Hashtable (StringComparer.OrdinalIgnoreCase);
100 if (connectionString == null || connectionString.Length == 0) {
101 return userParameters;
103 //connectionString += ";";
105 if (connectionString.IndexOf (DataDirectoryPlaceholder, StringComparison.Ordinal) >= 0) {
106 string dataDirectory = (string) AppDomain.CurrentDomain.GetData ("DataDirectory");
107 if (dataDirectory != null && dataDirectory.Length > 0) {
108 char lastChar = dataDirectory [dataDirectory.Length - 1];
109 if (lastChar != Path.DirectorySeparatorChar &&
110 lastChar != Path.AltDirectorySeparatorChar)
111 dataDirectory += '/';
113 connectionString = connectionString.Replace (DataDirectoryPlaceholder, dataDirectory);
116 bool inQuote = false;
117 bool inDQuote = false;
120 string name = String.Empty;
121 string value = String.Empty;
122 StringBuilder sb = new StringBuilder (connectionString.Length);
124 for (int i = 0; i < connectionString.Length; i ++) {
125 char c = connectionString [i];
127 if (i == connectionString.Length - 1)
130 peek = connectionString [i + 1];
136 else if (peek == c) {
146 else if (peek == c) {
151 inDQuote = !inDQuote;
154 if (inDQuote || inQuote)
157 if (name != null && name.Length > 0) {
158 value = sb.ToString();
159 userParameters [name.Trim()] = value.Trim();
163 value = String.Empty;
168 if (inDQuote || inQuote || !inName)
170 else if (peek == c) {
175 name = sb.ToString();
181 if (inQuote || inDQuote)
183 else if (sb.Length > 0 && peek != ';')
192 if (inDQuote || inQuote)
193 throw new ArgumentException("connectionString");
195 if (name != null && name.Length > 0) {
196 value = sb.ToString();
197 userParameters [name.Trim()] = value.Trim();
200 return userParameters;
204 #endregion // Methods
206 #region IDictionary Members
208 public virtual bool IsFixedSize
210 get { return _dictionary.IsFixedSize; }
213 public virtual bool IsReadOnly
215 get { return _dictionary.IsReadOnly; }
218 public virtual ICollection Keys
221 return _dictionary.Keys;
225 public virtual object this [object key] {
228 if (!(key is String))
229 throw new ArgumentException("key is not string");
231 string skey = (string)key;
233 skey = GetConnectionStringKey(skey);
237 return _dictionary[skey];
241 if (!(key is String))
242 throw new ArgumentException("key is not string");
244 string skey = (string)key;
246 skey = GetConnectionStringKey(skey);
250 _dictionary[skey] = value;
254 public virtual ICollection Values
256 get { return _dictionary.Values; }
259 public virtual void Add (object key, object value)
261 _dictionary.Add ((string)key, (string)value);
264 public virtual void Clear ()
266 _dictionary.Clear ();
269 public virtual bool Contains (object key)
271 return _dictionary.Contains (key);
274 public virtual IDictionaryEnumerator GetEnumerator ()
276 return _dictionary.GetEnumerator ();
279 public virtual void Remove (object key)
281 _dictionary.Remove ((string)key);
284 #endregion // IDictionary Members
286 #region IEnumerable Members
288 IEnumerator IEnumerable.GetEnumerator ()
290 return this.GetEnumerator();
293 #endregion // IEnumerable Members
295 #region ICollection Members
297 public virtual bool IsSynchronized
299 get { return ((ICollection)_dictionary).IsSynchronized; }
302 public virtual int Count
304 get { return _dictionary.Count; }
307 public virtual void CopyTo (Array array, int index)
309 _dictionary.CopyTo (array, index);
312 public virtual object SyncRoot
314 get {return ((ICollection)_dictionary).SyncRoot; }
317 #endregion // ICollection Members