1 //------------------------------------------------------------------------------
2 // <copyright file="OdbcConnectionStringBuilder.cs" company="Microsoft">
3 // Copyright (c) Microsoft Corporation. All rights reserved.
5 // <owner current="true" primary="true">Microsoft</owner>
6 // <owner current="true" primary="false">Microsoft</owner>
7 //------------------------------------------------------------------------------
10 using System.Collections;
11 using System.Collections.Generic;
12 using System.ComponentModel;
14 using System.Data.Common;
15 using System.Diagnostics;
16 using System.Globalization;
17 using System.Runtime.Serialization;
18 using System.Security.Permissions;
21 namespace System.Data.Odbc {
23 [DefaultProperty("Driver")]
24 [System.ComponentModel.TypeConverterAttribute(typeof(OdbcConnectionStringBuilder.OdbcConnectionStringBuilderConverter))]
25 public sealed class OdbcConnectionStringBuilder : DbConnectionStringBuilder {
27 private enum Keywords { // must maintain same ordering as _validKeywords array
34 private static readonly string[] _validKeywords;
35 private static readonly Dictionary<string,Keywords> _keywords;
37 private string[] _knownKeywords;
39 private string _dsn = DbConnectionStringDefaults.Dsn;
40 // private string _namedConnection = DbConnectionStringDefaults.NamedConnection;
42 private string _driver = DbConnectionStringDefaults.Driver;
44 static OdbcConnectionStringBuilder() {
45 string[] validKeywords = new string[2];
46 validKeywords[(int)Keywords.Driver] = DbConnectionStringKeywords.Driver;
47 validKeywords[(int)Keywords.Dsn] = DbConnectionStringKeywords.Dsn;
48 // validKeywords[(int)Keywords.NamedConnection] = DbConnectionStringKeywords.NamedConnection;
49 _validKeywords = validKeywords;
51 Dictionary<string,Keywords> hash = new Dictionary<string,Keywords>(2, StringComparer.OrdinalIgnoreCase);
52 hash.Add(DbConnectionStringKeywords.Driver, Keywords.Driver);
53 hash.Add(DbConnectionStringKeywords.Dsn, Keywords.Dsn);
54 // hash.Add(DbConnectionStringKeywords.NamedConnection, Keywords.NamedConnection);
55 Debug.Assert(2 == hash.Count, "initial expected size is incorrect");
59 public OdbcConnectionStringBuilder() : this((string)null) {
62 public OdbcConnectionStringBuilder(string connectionString) : base(true) {
63 if (!ADP.IsEmpty(connectionString)) {
64 ConnectionString = connectionString;
68 public override object this[string keyword] {
70 ADP.CheckArgumentNull(keyword, "keyword");
72 if (_keywords.TryGetValue(keyword, out index)) {
80 ADP.CheckArgumentNull(keyword, "keyword");
83 if (_keywords.TryGetValue(keyword, out index)) {
85 case Keywords.Driver: Driver = ConvertToString(value); break;
86 case Keywords.Dsn: Dsn = ConvertToString(value); break;
87 // case Keywords.NamedConnection: NamedConnection = ConvertToString(value); break;
89 Debug.Assert(false, "unexpected keyword");
90 throw ADP.KeywordNotSupported(keyword);
94 base[keyword] = value;
95 ClearPropertyDescriptors();
96 _knownKeywords = null;
105 [DisplayName(DbConnectionStringKeywords.Driver)]
106 [ResCategoryAttribute(Res.DataCategory_Source)]
107 [ResDescriptionAttribute(Res.DbConnectionString_Driver)]
108 [RefreshPropertiesAttribute(RefreshProperties.All)]
109 public string Driver {
110 get { return _driver; }
112 SetValue(DbConnectionStringKeywords.Driver, value);
117 [DisplayName(DbConnectionStringKeywords.Dsn)]
118 [ResCategoryAttribute(Res.DataCategory_NamedConnectionString)]
119 [ResDescriptionAttribute(Res.DbConnectionString_DSN)]
120 [RefreshPropertiesAttribute(RefreshProperties.All)]
124 SetValue(DbConnectionStringKeywords.Dsn, value);
129 [DisplayName(DbConnectionStringKeywords.NamedConnection)]
130 [ResCategoryAttribute(Res.DataCategory_NamedConnectionString)]
131 [ResDescriptionAttribute(Res.DbConnectionString_NamedConnection)]
132 [RefreshPropertiesAttribute(RefreshProperties.All)]
133 [TypeConverter(typeof(NamedConnectionStringConverter))]
134 public string NamedConnection {
135 get { return _namedConnection; }
137 SetValue(DbConnectionStringKeywords.NamedConnection, value);
138 _namedConnection = value;
142 public override ICollection Keys {
144 string[] knownKeywords = _knownKeywords;
145 if (null == knownKeywords) {
146 knownKeywords = _validKeywords;
149 foreach(string keyword in base.Keys) {
151 foreach(string s in knownKeywords) {
162 string[] tmp = new string[knownKeywords.Length + count];
163 knownKeywords.CopyTo(tmp, 0);
165 int index = knownKeywords.Length;
166 foreach(string keyword in base.Keys) {
168 foreach(string s in knownKeywords) {
175 tmp[index++] = keyword;
180 _knownKeywords = knownKeywords;
182 return new System.Data.Common.ReadOnlyCollection<string>(knownKeywords);
186 public override void Clear() {
188 for(int i = 0; i < _validKeywords.Length; ++i) {
191 _knownKeywords = _validKeywords;
194 public override bool ContainsKey(string keyword) {
195 ADP.CheckArgumentNull(keyword, "keyword");
196 return _keywords.ContainsKey(keyword) || base.ContainsKey(keyword);
199 private static string ConvertToString(object value) {
200 return DbConnectionStringBuilderUtil.ConvertToString(value);
203 private object GetAt(Keywords index) {
205 case Keywords.Driver: return Driver;
206 case Keywords.Dsn: return Dsn;
207 // case Keywords.NamedConnection: return NamedConnection;
209 Debug.Assert(false, "unexpected keyword");
210 throw ADP.KeywordNotSupported(_validKeywords[(int)index]);
215 protected override void GetProperties(Hashtable propertyDescriptors) {
217 if (TryGetValue(DbConnectionStringSynonyms.TRUSTEDCONNECTION, out value)) {
218 bool trusted = false;
220 trusted = (bool)value;
222 else if ((value is string) && !Boolean.TryParse((string)value, out trusted)) {
227 Attribute[] attributes = new Attribute[] {
228 BrowsableAttribute.Yes,
229 RefreshPropertiesAttribute.All,
231 DbConnectionStringBuilderDescriptor descriptor;
232 descriptor = new DbConnectionStringBuilderDescriptor(DbConnectionStringSynonyms.TRUSTEDCONNECTION,
233 this.GetType(), typeof(bool), false, attributes);
234 descriptor.RefreshOnChange = true;
235 propertyDescriptors[DbConnectionStringSynonyms.TRUSTEDCONNECTION] = descriptor;
237 if (ContainsKey(DbConnectionStringSynonyms.Pwd)) {
238 descriptor = new DbConnectionStringBuilderDescriptor(DbConnectionStringSynonyms.Pwd,
239 this.GetType(), typeof(string), true, attributes);
240 propertyDescriptors[DbConnectionStringSynonyms.Pwd] = descriptor;
242 if (ContainsKey(DbConnectionStringSynonyms.UID)) {
243 descriptor = new DbConnectionStringBuilderDescriptor(DbConnectionStringSynonyms.UID,
244 this.GetType(), typeof(string), true, attributes);
245 propertyDescriptors[DbConnectionStringSynonyms.UID] = descriptor;
249 base.GetProperties(propertyDescriptors);
253 public override bool Remove(string keyword) {
254 ADP.CheckArgumentNull(keyword, "keyword");
255 if (base.Remove(keyword)) {
257 if (_keywords.TryGetValue(keyword, out index)) {
261 ClearPropertyDescriptors();
262 _knownKeywords = null;
268 private void Reset(Keywords index) {
270 case Keywords.Driver:
271 _driver = DbConnectionStringDefaults.Driver;
274 _dsn = DbConnectionStringDefaults.Dsn;
276 // case Keywords.NamedConnection:
277 // _namedConnection = DbConnectionStringDefaults.NamedConnection;
280 Debug.Assert(false, "unexpected keyword");
281 throw ADP.KeywordNotSupported(_validKeywords[(int)index]);
285 private void SetValue(string keyword, string value) {
286 ADP.CheckArgumentNull(value, keyword);
287 base[keyword] = value;
290 public override bool TryGetValue(string keyword, out object value) {
291 ADP.CheckArgumentNull(keyword, "keyword");
293 if (_keywords.TryGetValue(keyword, out index)) {
294 value = GetAt(index);
297 return base.TryGetValue(keyword, out value);
300 sealed internal class OdbcConnectionStringBuilderConverter : ExpandableObjectConverter {
302 // converter classes should have public ctor
303 public OdbcConnectionStringBuilderConverter() {
306 override public bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) {
307 if (typeof(System.ComponentModel.Design.Serialization.InstanceDescriptor) == destinationType) {
310 return base.CanConvertTo(context, destinationType);
313 override public object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType) {
314 if (destinationType == null) {
315 throw ADP.ArgumentNull("destinationType");
317 if (typeof(System.ComponentModel.Design.Serialization.InstanceDescriptor) == destinationType) {
318 OdbcConnectionStringBuilder obj = (value as OdbcConnectionStringBuilder);
320 return ConvertToInstanceDescriptor(obj);
323 return base.ConvertTo(context, culture, value, destinationType);
326 private System.ComponentModel.Design.Serialization.InstanceDescriptor ConvertToInstanceDescriptor(OdbcConnectionStringBuilder options) {
327 Type[] ctorParams = new Type[] { typeof(string) };
328 object[] ctorValues = new object[] { options.ConnectionString };
329 System.Reflection.ConstructorInfo ctor = typeof(OdbcConnectionStringBuilder).GetConstructor(ctorParams);
330 return new System.ComponentModel.Design.Serialization.InstanceDescriptor(ctor, ctorValues);