/******************************************************** * ADO.NET 2.0 Data Provider for SQLite Version 3.X * Written by Robert Simpson (robert@blackcastlesoft.com) * * Released to the public domain, use at your own risk! ********************************************************/ namespace System.Data.SQLite { using System; using System.Data.Common; using System.ComponentModel; using System.Collections; using System.Globalization; using System.Reflection; #if !PLATFORM_COMPACTFRAMEWORK /// /// SQLite implementation of DbConnectionStringBuilder. /// [DefaultProperty("DataSource")] [DefaultMember("Item")] public sealed class SQLiteConnectionStringBuilder : DbConnectionStringBuilder { /// /// Properties of this class /// private Hashtable _properties; /// /// Constructs a new instance of the class /// /// /// Default constructor /// public SQLiteConnectionStringBuilder() { Initialize(null); } /// /// Constructs a new instance of the class using the specified connection string. /// /// The connection string to parse public SQLiteConnectionStringBuilder(string connectionString) { Initialize(connectionString); } /// /// Private initializer, which assigns the connection string and resets the builder /// /// The connection string to assign private void Initialize(string cnnString) { _properties = new Hashtable(StringComparer.OrdinalIgnoreCase); try { base.GetProperties(_properties); } catch(NotImplementedException) { FallbackGetProperties(_properties); } if (String.IsNullOrEmpty(cnnString) == false) ConnectionString = cnnString; } /// /// Gets/Sets the default version of the SQLite engine to instantiate. Currently the only valid value is 3, indicating version 3 of the sqlite library. /// [Browsable(true)] [DefaultValue(3)] public int Version { get { object value; TryGetValue("version", out value); return Convert.ToInt32(value, CultureInfo.CurrentCulture); } set { if (value != 3) throw new NotSupportedException(); this["version"] = value; } } /// /// Gets/Sets the synchronization mode (file flushing) of the connection string. Default is "Normal". /// [DisplayName("Synchronous")] [Browsable(true)] [DefaultValue(SynchronizationModes.Normal)] public SynchronizationModes SyncMode { get { object value; TryGetValue("synchronous", out value); if (value is string) return (SynchronizationModes)TypeDescriptor.GetConverter(typeof(SynchronizationModes)).ConvertFrom(value); else return (SynchronizationModes)value; } set { this["synchronous"] = value; } } /// /// Gets/Sets the encoding for the connection string. The default is "False" which indicates UTF-8 encoding. /// [DisplayName("Use UTF-16 Encoding")] [Browsable(true)] [DefaultValue(false)] public bool UseUTF16Encoding { get { object value; TryGetValue("useutf16encoding", out value); return SQLiteConvert.ToBoolean(value); } set { this["useutf16encoding"] = value; } } /// /// Gets/Sets whether or not to use connection pooling. The default is "False" /// [Browsable(true)] [DefaultValue(false)] public bool Pooling { get { object value; TryGetValue("pooling", out value); return SQLiteConvert.ToBoolean(value); } set { this["pooling"] = value; } } /// /// Gets/Sets whethor not to store GUID's in binary format. The default is True /// which saves space in the database. /// [DisplayName("Binary GUID")] [Browsable(true)] [DefaultValue(true)] public bool BinaryGUID { get { object value; TryGetValue("binaryguid", out value); return SQLiteConvert.ToBoolean(value); } set { this["binaryguid"] = value; } } /// /// Gets/Sets the filename to open on the connection string. /// [DisplayName("Data Source")] [Browsable(true)] [DefaultValue("")] public string DataSource { get { object value; TryGetValue("data source", out value); return value.ToString(); } set { this["data source"] = value; } } /// /// An alternate to the data source property /// [DisplayName("URI")] [Browsable(true)] [DefaultValue(null)] public string Uri { get { object value; TryGetValue("uri", out value); return value.ToString(); } set { this["uri"] = value; } } /// /// An alternate to the data source property that uses the SQLite URI syntax. /// [DisplayName("Full URI")] [Browsable(true)] [DefaultValue(null)] public string FullUri { get { object value; TryGetValue("fulluri", out value); return value.ToString(); } set { this["fulluri"] = value; } } /// /// Gets/sets the default command timeout for newly-created commands. This is especially useful for /// commands used internally such as inside a SQLiteTransaction, where setting the timeout is not possible. /// [DisplayName("Default Timeout")] [Browsable(true)] [DefaultValue(30)] public int DefaultTimeout { get { object value; TryGetValue("default timeout", out value); return Convert.ToInt32(value, CultureInfo.CurrentCulture); } set { this["default timeout"] = value; } } /// /// Determines whether or not the connection will automatically participate /// in the current distributed transaction (if one exists) /// [Browsable(true)] [DefaultValue(true)] public bool Enlist { get { object value; TryGetValue("enlist", out value); return SQLiteConvert.ToBoolean(value); } set { this["enlist"] = value; } } /// /// If set to true, will throw an exception if the database specified in the connection /// string does not exist. If false, the database will be created automatically. /// [DisplayName("Fail If Missing")] [Browsable(true)] [DefaultValue(false)] public bool FailIfMissing { get { object value; TryGetValue("failifmissing", out value); return SQLiteConvert.ToBoolean(value); } set { this["failifmissing"] = value; } } /// /// If enabled, uses the legacy 3.xx format for maximum compatibility, but results in larger /// database sizes. /// [DisplayName("Legacy Format")] [Browsable(true)] [DefaultValue(false)] public bool LegacyFormat { get { object value; TryGetValue("legacy format", out value); return SQLiteConvert.ToBoolean(value); } set { this["legacy format"] = value; } } /// /// When enabled, the database will be opened for read-only access and writing will be disabled. /// [DisplayName("Read Only")] [Browsable(true)] [DefaultValue(false)] public bool ReadOnly { get { object value; TryGetValue("read only", out value); return SQLiteConvert.ToBoolean(value); } set { this["read only"] = value; } } /// /// Gets/sets the database encryption password /// [Browsable(true)] [PasswordPropertyText(true)] [DefaultValue("")] public string Password { get { object value; TryGetValue("password", out value); return value.ToString(); } set { this["password"] = value; } } /// /// Gets/sets the database encryption hexadecimal password /// [DisplayName("Hexadecimal Password")] [Browsable(true)] [PasswordPropertyText(true)] [DefaultValue(null)] public byte[] HexPassword { get { object value; if (TryGetValue("hexpassword", out value)) { if (value is string) return SQLiteConnection.FromHexString((string)value); else if (value != null) return (byte[])value; } return null; } set { this["hexpassword"] = SQLiteConnection.ToHexString(value); } } /// /// Gets/Sets the page size for the connection. /// [DisplayName("Page Size")] [Browsable(true)] [DefaultValue(1024)] public int PageSize { get { object value; TryGetValue("page size", out value); return Convert.ToInt32(value, CultureInfo.CurrentCulture); } set { this["page size"] = value; } } /// /// Gets/Sets the maximum number of pages the database may hold /// [DisplayName("Maximum Page Count")] [Browsable(true)] [DefaultValue(0)] public int MaxPageCount { get { object value; TryGetValue("max page count", out value); return Convert.ToInt32(value, CultureInfo.CurrentCulture); } set { this["max page count"] = value; } } /// /// Gets/Sets the cache size for the connection. /// [DisplayName("Cache Size")] [Browsable(true)] [DefaultValue(2000)] public int CacheSize { get { object value; TryGetValue("cache size", out value); return Convert.ToInt32(value, CultureInfo.CurrentCulture); } set { this["cache size"] = value; } } /// /// Gets/Sets the DateTime format for the connection. /// [DisplayName("DateTime Format")] [Browsable(true)] [DefaultValue(SQLiteDateFormats.Default)] public SQLiteDateFormats DateTimeFormat { get { object value; if (TryGetValue("datetimeformat", out value)) { if (value is SQLiteDateFormats) return (SQLiteDateFormats)value; else if (value != null) return (SQLiteDateFormats)TypeDescriptor.GetConverter( typeof(SQLiteDateFormats)).ConvertFrom(value); } return SQLiteDateFormats.Default; } set { this["datetimeformat"] = value; } } /// /// Gets/Sets the DateTime kind for the connection. /// [DisplayName("DateTime Kind")] [Browsable(true)] [DefaultValue(DateTimeKind.Unspecified)] public DateTimeKind DateTimeKind { get { object value; if (TryGetValue("datetimekind", out value)) { if (value is DateTimeKind) return (DateTimeKind)value; else if (value != null) return (DateTimeKind)TypeDescriptor.GetConverter( typeof(DateTimeKind)).ConvertFrom(value); } return DateTimeKind.Unspecified; } set { this["datetimekind"] = value; } } /// /// Gets/sets the DateTime format string used for formatting /// and parsing purposes. /// [DisplayName("DateTime Format String")] [Browsable(true)] [DefaultValue(null)] public string DateTimeFormatString { get { object value; if (TryGetValue("datetimeformatstring", out value)) { if (value is string) return (string)value; else if (value != null) return value.ToString(); } return null; } set { this["datetimeformatstring"] = value; } } /// /// Gets/Sets the placeholder base schema name used for /// .NET Framework compatibility purposes. /// [DisplayName("Base Schema Name")] [Browsable(true)] [DefaultValue(SQLiteConnection.DefaultBaseSchemaName)] public string BaseSchemaName { get { object value; if (TryGetValue("baseschemaname", out value)) { if (value is string) return (string)value; else if (value != null) return value.ToString(); } return null; } set { this["baseschemaname"] = value; } } /// /// Determines how SQLite handles the transaction journal file. /// [Browsable(true)] [DefaultValue(SQLiteJournalModeEnum.Default)] [DisplayName("Journal Mode")] public SQLiteJournalModeEnum JournalMode { get { object value; TryGetValue("journal mode", out value); if (value is string) return (SQLiteJournalModeEnum)TypeDescriptor.GetConverter(typeof(SQLiteJournalModeEnum)).ConvertFrom(value); else return (SQLiteJournalModeEnum)value; } set { this["journal mode"] = value; } } /// /// Sets the default isolation level for transactions on the connection. /// [Browsable(true)] [DefaultValue(IsolationLevel.Serializable)] [DisplayName("Default Isolation Level")] public IsolationLevel DefaultIsolationLevel { get { object value; TryGetValue("default isolationlevel", out value); if (value is string) return (IsolationLevel)TypeDescriptor.GetConverter(typeof(IsolationLevel)).ConvertFrom(value); else return (IsolationLevel)value; } set { this["default isolationlevel"] = value; } } /// /// Gets/sets the default database type for the connection. /// [DisplayName("Default Database Type")] [Browsable(true)] [DefaultValue(SQLiteConnection.BadDbType)] public DbType DefaultDbType { get { object value; if (TryGetValue("defaultdbtype", out value)) { if (value is string) return (DbType)TypeDescriptor.GetConverter( typeof(DbType)).ConvertFrom(value); else if (value != null) return (DbType)value; } return SQLiteConnection.BadDbType; } set { this["defaultdbtype"] = value; } } /// /// Gets/sets the default type name for the connection. /// [DisplayName("Default Type Name")] [Browsable(true)] [DefaultValue(null)] public string DefaultTypeName { get { object value; TryGetValue("defaulttypename", out value); return value.ToString(); } set { this["defaulttypename"] = value; } } /// /// If enabled, use foreign key constraints /// [DisplayName("Foreign Keys")] [Browsable(true)] [DefaultValue(false)] public bool ForeignKeys { get { object value; TryGetValue("foreign keys", out value); return SQLiteConvert.ToBoolean(value); } set { this["foreign keys"] = value; } } /// /// Gets/Sets the extra behavioral flags. /// [Browsable(true)] [DefaultValue(SQLiteConnectionFlags.Default)] public SQLiteConnectionFlags Flags { get { object value; if (TryGetValue("flags", out value)) { if (value is SQLiteConnectionFlags) return (SQLiteConnectionFlags)value; else if (value != null) return (SQLiteConnectionFlags)TypeDescriptor.GetConverter( typeof(SQLiteConnectionFlags)).ConvertFrom(value); } return SQLiteConnectionFlags.Default; } set { this["flags"] = value; } } /// /// If enabled, apply the default connection settings to opened databases. /// [DisplayName("Set Defaults")] [Browsable(true)] [DefaultValue(true)] public bool SetDefaults { get { object value; TryGetValue("setdefaults", out value); return SQLiteConvert.ToBoolean(value); } set { this["setdefaults"] = value; } } /// /// If enabled, attempt to resolve the provided data source file name to a /// full path before opening. /// [DisplayName("To Full Path")] [Browsable(true)] [DefaultValue(true)] public bool ToFullPath { get { object value; TryGetValue("tofullpath", out value); return SQLiteConvert.ToBoolean(value); } set { this["tofullpath"] = value; } } /// /// If enabled, skip using the configured shared connection flags. /// [DisplayName("No Shared Flags")] [Browsable(true)] [DefaultValue(false)] public bool NoSharedFlags { get { object value; TryGetValue("nosharedflags", out value); return SQLiteConvert.ToBoolean(value); } set { this["nosharedflags"] = value; } } /// /// Helper function for retrieving values from the connectionstring /// /// The keyword to retrieve settings for /// The resulting parameter value /// Returns true if the value was found and returned public override bool TryGetValue(string keyword, out object value) { bool b = base.TryGetValue(keyword, out value); if (!_properties.ContainsKey(keyword)) return b; PropertyDescriptor pd = _properties[keyword] as PropertyDescriptor; if (pd == null) return b; // Attempt to coerce the value into something more solid if (b) { if (pd.PropertyType == typeof(Boolean)) value = SQLiteConvert.ToBoolean(value); else if (pd.PropertyType != typeof(byte[])) value = TypeDescriptor.GetConverter(pd.PropertyType).ConvertFrom(value); } else { DefaultValueAttribute att = pd.Attributes[typeof(DefaultValueAttribute)] as DefaultValueAttribute; if (att != null) { value = att.Value; b = true; } } return b; } /// /// Fallback method for MONO, which doesn't implement DbConnectionStringBuilder.GetProperties() /// /// The hashtable to fill with property descriptors private void FallbackGetProperties(Hashtable propertyList) { foreach (PropertyDescriptor descriptor in TypeDescriptor.GetProperties(this, true)) { if (descriptor.Name != "ConnectionString" && propertyList.ContainsKey(descriptor.DisplayName) == false) { propertyList.Add(descriptor.DisplayName, descriptor); } } } } #endif }