#region Apache License
//
// Licensed to the Apache Software Foundation (ASF) under one or more 
// contributor license agreements. See the NOTICE file distributed with
// this work for additional information regarding copyright ownership. 
// The ASF licenses this file to you under the Apache License, Version 2.0
// (the "License"); you may not use this file except in compliance with 
// the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
#endregion

// SSCLI 1.0 has no support for ADO.NET
#if !SSCLI

using System;
using System.Collections;
using System.Configuration;
using System.Data;
using System.IO;

using log4net.Util;
using log4net.Layout;
using log4net.Core;

namespace log4net.Appender
{
	/// <summary>
	/// Appender that logs to a database.
	/// </summary>
	/// <remarks>
	/// <para>
	/// <see cref="AdoNetAppender"/> appends logging events to a table within a
	/// database. The appender can be configured to specify the connection 
	/// string by setting the <see cref="ConnectionString"/> property. 
	/// The connection type (provider) can be specified by setting the <see cref="ConnectionType"/>
	/// property. For more information on database connection strings for
	/// your specific database see <a href="http://www.connectionstrings.com/">http://www.connectionstrings.com/</a>.
	/// </para>
	/// <para>
	/// Records are written into the database either using a prepared
	/// statement or a stored procedure. The <see cref="CommandType"/> property
	/// is set to <see cref="System.Data.CommandType.Text"/> (<c>System.Data.CommandType.Text</c>) to specify a prepared statement
	/// or to <see cref="System.Data.CommandType.StoredProcedure"/> (<c>System.Data.CommandType.StoredProcedure</c>) to specify a stored
	/// procedure.
	/// </para>
	/// <para>
	/// The prepared statement text or the name of the stored procedure
	/// must be set in the <see cref="CommandText"/> property.
	/// </para>
	/// <para>
	/// The prepared statement or stored procedure can take a number
	/// of parameters. Parameters are added using the <see cref="AddParameter"/>
	/// method. This adds a single <see cref="AdoNetAppenderParameter"/> to the
	/// ordered list of parameters. The <see cref="AdoNetAppenderParameter"/>
	/// type may be subclassed if required to provide database specific
	/// functionality. The <see cref="AdoNetAppenderParameter"/> specifies
	/// the parameter name, database type, size, and how the value should
	/// be generated using a <see cref="ILayout"/>.
	/// </para>
	/// </remarks>
	/// <example>
	/// An example of a SQL Server table that could be logged to:
	/// <code lang="SQL">
	/// CREATE TABLE [dbo].[Log] ( 
	///   [ID] [int] IDENTITY (1, 1) NOT NULL ,
	///   [Date] [datetime] NOT NULL ,
	///   [Thread] [varchar] (255) NOT NULL ,
	///   [Level] [varchar] (20) NOT NULL ,
	///   [Logger] [varchar] (255) NOT NULL ,
	///   [Message] [varchar] (4000) NOT NULL 
	/// ) ON [PRIMARY]
	/// </code>
	/// </example>
	/// <example>
	/// An example configuration to log to the above table:
	/// <code lang="XML" escaped="true">
	/// <appender name="AdoNetAppender_SqlServer" type="log4net.Appender.AdoNetAppender" >
	///   <connectionType value="System.Data.SqlClient.SqlConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
	///   <connectionString value="data source=SQLSVR;initial catalog=test_log4net;integrated security=false;persist security info=True;User ID=sa;Password=sa" />
	///   <commandText value="INSERT INTO Log ([Date],[Thread],[Level],[Logger],[Message]) VALUES (@log_date, @thread, @log_level, @logger, @message)" />
	///   <parameter>
	///     <parameterName value="@log_date" />
	///     <dbType value="DateTime" />
	///     <layout type="log4net.Layout.PatternLayout" value="%date{yyyy'-'MM'-'dd HH':'mm':'ss'.'fff}" />
	///   </parameter>
	///   <parameter>
	///     <parameterName value="@thread" />
	///     <dbType value="String" />
	///     <size value="255" />
	///     <layout type="log4net.Layout.PatternLayout" value="%thread" />
	///   </parameter>
	///   <parameter>
	///     <parameterName value="@log_level" />
	///     <dbType value="String" />
	///     <size value="50" />
	///     <layout type="log4net.Layout.PatternLayout" value="%level" />
	///   </parameter>
	///   <parameter>
	///     <parameterName value="@logger" />
	///     <dbType value="String" />
	///     <size value="255" />
	///     <layout type="log4net.Layout.PatternLayout" value="%logger" />
	///   </parameter>
	///   <parameter>
	///     <parameterName value="@message" />
	///     <dbType value="String" />
	///     <size value="4000" />
	///     <layout type="log4net.Layout.PatternLayout" value="%message" />
	///   </parameter>
	/// </appender>
	/// </code>
	/// </example>
	/// <author>Julian Biddle</author>
	/// <author>Nicko Cadell</author>
	/// <author>Gert Driesen</author>
	/// <author>Lance Nehring</author>
	public class AdoNetAppender : BufferingAppenderSkeleton
	{
		#region Public Instance Constructors

		/// <summary> 
		/// Initializes a new instance of the <see cref="AdoNetAppender" /> class.
		/// </summary>
		/// <remarks>
		/// Public default constructor to initialize a new instance of this class.
		/// </remarks>
		public AdoNetAppender()
		{
			ConnectionType = "System.Data.OleDb.OleDbConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089";
			UseTransactions = true;
			CommandType = System.Data.CommandType.Text;
			m_parameters = new ArrayList();
			ReconnectOnError = false;
		}

		#endregion // Public Instance Constructors

		#region Public Instance Properties

		/// <summary>
		/// Gets or sets the database connection string that is used to connect to 
		/// the database.
		/// </summary>
		/// <value>
		/// The database connection string used to connect to the database.
		/// </value>
		/// <remarks>
		/// <para>
		/// The connections string is specific to the connection type.
		/// See <see cref="ConnectionType"/> for more information.
		/// </para>
		/// </remarks>
		/// <example>Connection string for MS Access via ODBC:
		/// <code>"DSN=MS Access Database;UID=admin;PWD=;SystemDB=C:\data\System.mdw;SafeTransactions = 0;FIL=MS Access;DriverID = 25;DBQ=C:\data\train33.mdb"</code>
		/// </example>
		/// <example>Another connection string for MS Access via ODBC:
		/// <code>"Driver={Microsoft Access Driver (*.mdb)};DBQ=C:\Work\cvs_root\log4net-1.2\access.mdb;UID=;PWD=;"</code>
		/// </example>
		/// <example>Connection string for MS Access via OLE DB:
		/// <code>"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\Work\cvs_root\log4net-1.2\access.mdb;User Id=;Password=;"</code>
		/// </example>
		public string ConnectionString
		{
			get { return m_connectionString; }
			set { m_connectionString = value; }
		}

		/// <summary>
		/// The appSettings key from App.Config that contains the connection string.
		/// </summary>
		public string AppSettingsKey
		{
			get { return m_appSettingsKey; }
			set { m_appSettingsKey = value; }
		}

#if NET_2_0
		/// <summary>
		/// The connectionStrings key from App.Config that contains the connection string.
		/// </summary>
		/// <remarks>
		/// This property requires at least .NET 2.0.
		/// </remarks>
		public string ConnectionStringName
		{
			get { return m_connectionStringName; }
			set { m_connectionStringName = value; }
		}
#endif

		/// <summary>
		/// Gets or sets the type name of the <see cref="IDbConnection"/> connection
		/// that should be created.
		/// </summary>
		/// <value>
		/// The type name of the <see cref="IDbConnection"/> connection.
		/// </value>
		/// <remarks>
		/// <para>
		/// The type name of the ADO.NET provider to use.
		/// </para>
		/// <para>
		/// The default is to use the OLE DB provider.
		/// </para>
		/// </remarks>
		/// <example>Use the OLE DB Provider. This is the default value.
		/// <code>System.Data.OleDb.OleDbConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</code>
		/// </example>
		/// <example>Use the MS SQL Server Provider. 
		/// <code>System.Data.SqlClient.SqlConnection, System.Data, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</code>
		/// </example>
		/// <example>Use the ODBC Provider. 
		/// <code>Microsoft.Data.Odbc.OdbcConnection,Microsoft.Data.Odbc,version=1.0.3300.0,publicKeyToken=b77a5c561934e089,culture=neutral</code>
		/// This is an optional package that you can download from 
		/// <a href="http://msdn.microsoft.com/downloads">http://msdn.microsoft.com/downloads</a> 
		/// search for <b>ODBC .NET Data Provider</b>.
		/// </example>
		/// <example>Use the Oracle Provider. 
		/// <code>System.Data.OracleClient.OracleConnection, System.Data.OracleClient, Version=1.0.3300.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</code>
		/// This is an optional package that you can download from 
		/// <a href="http://msdn.microsoft.com/downloads">http://msdn.microsoft.com/downloads</a> 
		/// search for <b>.NET Managed Provider for Oracle</b>.
		/// </example>
		public string ConnectionType
		{
			get { return m_connectionType; }
			set { m_connectionType = value; }
		}

		/// <summary>
		/// Gets or sets the command text that is used to insert logging events
		/// into the database.
		/// </summary>
		/// <value>
		/// The command text used to insert logging events into the database.
		/// </value>
		/// <remarks>
		/// <para>
		/// Either the text of the prepared statement or the
		/// name of the stored procedure to execute to write into
		/// the database.
		/// </para>
		/// <para>
		/// The <see cref="CommandType"/> property determines if
		/// this text is a prepared statement or a stored procedure.
		/// </para>
		/// <para>
		/// If this property is not set, the command text is retrieved by invoking
		/// <see cref="GetLogStatement(LoggingEvent)"/>.
		/// </para>
		/// </remarks>
		public string CommandText
		{
			get { return m_commandText; }
			set { m_commandText = value; }
		}

		/// <summary>
		/// Gets or sets the command type to execute.
		/// </summary>
		/// <value>
		/// The command type to execute.
		/// </value>
		/// <remarks>
		/// <para>
		/// This value may be either <see cref="System.Data.CommandType.Text"/> (<c>System.Data.CommandType.Text</c>) to specify
		/// that the <see cref="CommandText"/> is a prepared statement to execute, 
		/// or <see cref="System.Data.CommandType.StoredProcedure"/> (<c>System.Data.CommandType.StoredProcedure</c>) to specify that the
		/// <see cref="CommandText"/> property is the name of a stored procedure
		/// to execute.
		/// </para>
		/// <para>
		/// The default value is <see cref="System.Data.CommandType.Text"/> (<c>System.Data.CommandType.Text</c>).
		/// </para>
		/// </remarks>
		public CommandType CommandType
		{
			get { return m_commandType; }
			set { m_commandType = value; }
		}

		/// <summary>
		/// Should transactions be used to insert logging events in the database.
		/// </summary>
		/// <value>
		/// <c>true</c> if transactions should be used to insert logging events in
		/// the database, otherwise <c>false</c>. The default value is <c>true</c>.
		/// </value>
		/// <remarks>
		/// <para>
		/// Gets or sets a value that indicates whether transactions should be used
		/// to insert logging events in the database.
		/// </para>
		/// <para>
		/// When set a single transaction will be used to insert the buffered events
		/// into the database. Otherwise each event will be inserted without using
		/// an explicit transaction.
		/// </para>
		/// </remarks>
		public bool UseTransactions
		{
			get { return m_useTransactions; }
			set { m_useTransactions = value; }
		}

		/// <summary>
		/// Gets or sets the <see cref="SecurityContext"/> used to call the NetSend method.
		/// </summary>
		/// <value>
		/// The <see cref="SecurityContext"/> used to call the NetSend method.
		/// </value>
		/// <remarks>
		/// <para>
		/// Unless a <see cref="SecurityContext"/> specified here for this appender
		/// the <see cref="SecurityContextProvider.DefaultProvider"/> is queried for the
		/// security context to use. The default behavior is to use the security context
		/// of the current thread.
		/// </para>
		/// </remarks>
		public SecurityContext SecurityContext
		{
			get { return m_securityContext; }
			set { m_securityContext = value; }
		}

		/// <summary>
		/// Should this appender try to reconnect to the database on error.
		/// </summary>
		/// <value>
		/// <c>true</c> if the appender should try to reconnect to the database after an
		/// error has occurred, otherwise <c>false</c>. The default value is <c>false</c>, 
		/// i.e. not to try to reconnect.
		/// </value>
		/// <remarks>
		/// <para>
		/// The default behaviour is for the appender not to try to reconnect to the
		/// database if an error occurs. Subsequent logging events are discarded.
		/// </para>
		/// <para>
		/// To force the appender to attempt to reconnect to the database set this
		/// property to <c>true</c>.
		/// </para>
		/// <note>
		/// When the appender attempts to connect to the database there may be a
		/// delay of up to the connection timeout specified in the connection string.
		/// This delay will block the calling application's thread. 
		/// Until the connection can be reestablished this potential delay may occur multiple times.
		/// </note>
		/// </remarks>
		public bool ReconnectOnError
		{
			get { return m_reconnectOnError; }
			set { m_reconnectOnError = value; }
		}

		#endregion // Public Instance Properties

		#region Protected Instance Properties

		/// <summary>
		/// Gets or sets the underlying <see cref="IDbConnection" />.
		/// </summary>
		/// <value>
		/// The underlying <see cref="IDbConnection" />.
		/// </value>
		/// <remarks>
		/// <see cref="AdoNetAppender" /> creates a <see cref="IDbConnection" /> to insert 
		/// logging events into a database.  Classes deriving from <see cref="AdoNetAppender" /> 
		/// can use this property to get or set this <see cref="IDbConnection" />.  Use the 
		/// underlying <see cref="IDbConnection" /> returned from <see cref="Connection" /> if 
		/// you require access beyond that which <see cref="AdoNetAppender" /> provides.
		/// </remarks>
		protected IDbConnection Connection
		{
			get { return m_dbConnection; }
			set { m_dbConnection = value; }
		}

		#endregion // Protected Instance Properties

		#region Implementation of IOptionHandler

		/// <summary>
		/// Initialize the appender based on the options set
		/// </summary>
		/// <remarks>
		/// <para>
		/// This is part of the <see cref="IOptionHandler"/> delayed object
		/// activation scheme. The <see cref="ActivateOptions"/> method must 
		/// be called on this object after the configuration properties have
		/// been set. Until <see cref="ActivateOptions"/> is called this
		/// object is in an undefined state and must not be used. 
		/// </para>
		/// <para>
		/// If any of the configuration properties are modified then 
		/// <see cref="ActivateOptions"/> must be called again.
		/// </para>
		/// </remarks>
		override public void ActivateOptions()
		{
			base.ActivateOptions();

			if (SecurityContext == null)
			{
				SecurityContext = SecurityContextProvider.DefaultProvider.CreateSecurityContext(this);
			}

			InitializeDatabaseConnection();
		}

		#endregion

		#region Override implementation of AppenderSkeleton

		/// <summary>
		/// Override the parent method to close the database
		/// </summary>
		/// <remarks>
		/// <para>
		/// Closes the database command and database connection.
		/// </para>
		/// </remarks>
		override protected void OnClose()
		{
			base.OnClose();
			DiposeConnection();
		}

		#endregion

		#region Override implementation of BufferingAppenderSkeleton

		/// <summary>
		/// Inserts the events into the database.
		/// </summary>
		/// <param name="events">The events to insert into the database.</param>
		/// <remarks>
		/// <para>
		/// Insert all the events specified in the <paramref name="events"/>
		/// array into the database.
		/// </para>
		/// </remarks>
		override protected void SendBuffer(LoggingEvent[] events)
		{
			if (ReconnectOnError && (Connection == null || Connection.State != ConnectionState.Open))
			{
				LogLog.Debug(declaringType, "Attempting to reconnect to database. Current Connection State: " + ((Connection == null) ? SystemInfo.NullText : Connection.State.ToString()));

				InitializeDatabaseConnection();
			}

			// Check that the connection exists and is open
			if (Connection != null && Connection.State == ConnectionState.Open)
			{
				if (UseTransactions)
				{
					// Create transaction
					// NJC - Do this on 2 lines because it can confuse the debugger
					using (IDbTransaction dbTran = Connection.BeginTransaction())
					{
						try
						{
							SendBuffer(dbTran, events);

							// commit transaction
							dbTran.Commit();
						}
						catch (Exception ex)
						{
							// rollback the transaction
							try
							{
								dbTran.Rollback();
							}
							catch (Exception)
							{
								// Ignore exception
							}

							// Can't insert into the database. That's a bad thing
							ErrorHandler.Error("Exception while writing to database", ex);
						}
					}
				}
				else
				{
					// Send without transaction
					SendBuffer(null, events);
				}
			}
		}

		#endregion // Override implementation of BufferingAppenderSkeleton

		#region Public Instance Methods

		/// <summary>
		/// Adds a parameter to the command.
		/// </summary>
		/// <param name="parameter">The parameter to add to the command.</param>
		/// <remarks>
		/// <para>
		/// Adds a parameter to the ordered list of command parameters.
		/// </para>
		/// </remarks>
		public void AddParameter(AdoNetAppenderParameter parameter)
		{
			m_parameters.Add(parameter);
		}


		#endregion // Public Instance Methods

		#region Protected Instance Methods

		/// <summary>
		/// Writes the events to the database using the transaction specified.
		/// </summary>
		/// <param name="dbTran">The transaction that the events will be executed under.</param>
		/// <param name="events">The array of events to insert into the database.</param>
		/// <remarks>
		/// <para>
		/// The transaction argument can be <c>null</c> if the appender has been
		/// configured not to use transactions. See <see cref="UseTransactions"/>
		/// property for more information.
		/// </para>
		/// </remarks>
		virtual protected void SendBuffer(IDbTransaction dbTran, LoggingEvent[] events)
		{
			// string.IsNotNullOrWhiteSpace() does not exist in ancient .NET frameworks
			if (CommandText != null && CommandText.Trim() != "")
			{
				using (IDbCommand dbCmd = Connection.CreateCommand())
				{
					// Set the command string
					dbCmd.CommandText = CommandText;

					// Set the command type
					dbCmd.CommandType = CommandType;
					// Send buffer using the prepared command object
					if (dbTran != null)
					{
						dbCmd.Transaction = dbTran;
					}
					// prepare the command, which is significantly faster
					dbCmd.Prepare();
					// run for all events
					foreach (LoggingEvent e in events)
					{
						// clear parameters that have been set
						dbCmd.Parameters.Clear();

						// Set the parameter values
						foreach (AdoNetAppenderParameter param in m_parameters)
						{
							param.Prepare(dbCmd);
							param.FormatValue(dbCmd, e);
						}

						// Execute the query
						dbCmd.ExecuteNonQuery();
					}
				}
			}
			else
			{
				// create a new command
				using (IDbCommand dbCmd = Connection.CreateCommand())
				{
					if (dbTran != null)
					{
						dbCmd.Transaction = dbTran;
					}
					// run for all events
					foreach (LoggingEvent e in events)
					{
						// Get the command text from the Layout
						string logStatement = GetLogStatement(e);

						LogLog.Debug(declaringType, "LogStatement [" + logStatement + "]");

						dbCmd.CommandText = logStatement;
						dbCmd.ExecuteNonQuery();
					}
				}
			}
		}

		/// <summary>
		/// Formats the log message into database statement text.
		/// </summary>
		/// <param name="logEvent">The event being logged.</param>
		/// <remarks>
		/// This method can be overridden by subclasses to provide 
		/// more control over the format of the database statement.
		/// </remarks>
		/// <returns>
		/// Text that can be passed to a <see cref="System.Data.IDbCommand"/>.
		/// </returns>
		virtual protected string GetLogStatement(LoggingEvent logEvent)
		{
			if (Layout == null)
			{
				ErrorHandler.Error("AdoNetAppender: No Layout specified.");
				return "";
			}
			else
			{
				StringWriter writer = new StringWriter(System.Globalization.CultureInfo.InvariantCulture);
				Layout.Format(writer, logEvent);
				return writer.ToString();
			}
		}

		/// <summary>
		/// Creates an <see cref="IDbConnection"/> instance used to connect to the database.
		/// </summary>
		/// <remarks>
		/// This method is called whenever a new IDbConnection is needed (i.e. when a reconnect is necessary).
		/// </remarks>
		/// <param name="connectionType">The <see cref="Type"/> of the <see cref="IDbConnection"/> object.</param>
		/// <param name="connectionString">The connectionString output from the ResolveConnectionString method.</param>
		/// <returns>An <see cref="IDbConnection"/> instance with a valid connection string.</returns>
		virtual protected IDbConnection CreateConnection(Type connectionType, string connectionString)
		{
			IDbConnection connection = (IDbConnection)Activator.CreateInstance(connectionType);
			connection.ConnectionString = connectionString;
			return connection;
		}

		/// <summary>
		/// Resolves the connection string from the ConnectionString, ConnectionStringName, or AppSettingsKey
		/// property.
		/// </summary>
		/// <remarks>
		/// ConnectiongStringName is only supported on .NET 2.0 and higher.
		/// </remarks>
		/// <param name="connectionStringContext">Additional information describing the connection string.</param>
		/// <returns>A connection string used to connect to the database.</returns>
		virtual protected string ResolveConnectionString(out string connectionStringContext)
		{
			if (ConnectionString != null && ConnectionString.Length > 0)
			{
				connectionStringContext = "ConnectionString";
				return ConnectionString;
			}

#if NET_2_0
			if (!String.IsNullOrEmpty(ConnectionStringName))
			{
				ConnectionStringSettings settings = ConfigurationManager.ConnectionStrings[ConnectionStringName];
				if (settings != null)
				{
					connectionStringContext = "ConnectionStringName";
					return settings.ConnectionString;
				}
				else
				{
					throw new LogException("Unable to find [" + ConnectionStringName + "] ConfigurationManager.ConnectionStrings item");
				}
			}
#endif

			if (AppSettingsKey != null && AppSettingsKey.Length > 0)
			{
				connectionStringContext = "AppSettingsKey";
				string appSettingsConnectionString = SystemInfo.GetAppSetting(AppSettingsKey);
				if (appSettingsConnectionString == null || appSettingsConnectionString.Length == 0)
				{
					throw new LogException("Unable to find [" + AppSettingsKey + "] AppSettings key.");
				}
				return appSettingsConnectionString;
			}

			connectionStringContext = "Unable to resolve connection string from ConnectionString, ConnectionStrings, or AppSettings.";
			return string.Empty;
		}

		/// <summary>
		/// Retrieves the class type of the ADO.NET provider.
		/// </summary>
		/// <remarks>
		/// <para>
		/// Gets the Type of the ADO.NET provider to use to connect to the
		/// database. This method resolves the type specified in the 
		/// <see cref="ConnectionType"/> property.
		/// </para>
		/// <para>
		/// Subclasses can override this method to return a different type
		/// if necessary.
		/// </para>
		/// </remarks>
		/// <returns>The <see cref="Type"/> of the ADO.NET provider</returns>
		virtual protected Type ResolveConnectionType()
		{
			try
			{
				return SystemInfo.GetTypeFromString(ConnectionType, true, false);
			}
			catch (Exception ex)
			{
				ErrorHandler.Error("Failed to load connection type [" + ConnectionType + "]", ex);
				throw;
			}
		}

		#endregion // Protected Instance Methods

		#region Private Instance Methods

		/// <summary>
		/// Connects to the database.
		/// </summary>		
		private void InitializeDatabaseConnection()
		{
			string connectionStringContext = "Unable to determine connection string context.";
			string resolvedConnectionString = string.Empty;

			try
			{
				DiposeConnection();

				// Set the connection string
				resolvedConnectionString = ResolveConnectionString(out connectionStringContext);

				Connection = CreateConnection(ResolveConnectionType(), resolvedConnectionString);

				using (SecurityContext.Impersonate(this))
				{
					// Open the database connection
					Connection.Open();
				}
			}
			catch (Exception e)
			{
				// Sadly, your connection string is bad.
				ErrorHandler.Error("Could not open database connection [" + resolvedConnectionString + "]. Connection string context [" + connectionStringContext + "].", e);

				Connection = null;
			}
		}

		/// <summary>
		/// Cleanup the existing connection.
		/// </summary>
		/// <remarks>
		/// Calls the IDbConnection's <see cref="IDbConnection.Close"/> method.
		/// </remarks>
		private void DiposeConnection()
		{
			if (Connection != null)
			{
				try
				{
					Connection.Close();
				}
				catch (Exception ex)
				{
					LogLog.Warn(declaringType, "Exception while disposing cached connection object", ex);
				}
				Connection = null;
			}
		}

		#endregion // Private Instance Methods

		#region Protected Instance Fields

		/// <summary>
		/// The list of <see cref="AdoNetAppenderParameter"/> objects.
		/// </summary>
		/// <remarks>
		/// <para>
		/// The list of <see cref="AdoNetAppenderParameter"/> objects.
		/// </para>
		/// </remarks>
		protected ArrayList m_parameters;

		#endregion // Protected Instance Fields

		#region Private Instance Fields

		/// <summary>
		/// The security context to use for privileged calls
		/// </summary>
		private SecurityContext m_securityContext;

		/// <summary>
		/// The <see cref="IDbConnection" /> that will be used
		/// to insert logging events into a database.
		/// </summary>
		private IDbConnection m_dbConnection;

		/// <summary>
		/// Database connection string.
		/// </summary>
		private string m_connectionString;

		/// <summary>
		/// The appSettings key from App.Config that contains the connection string.
		/// </summary>
		private string m_appSettingsKey;

#if NET_2_0
		/// <summary>
		/// The connectionStrings key from App.Config that contains the connection string.
		/// </summary>
		private string m_connectionStringName;
#endif

		/// <summary>
		/// String type name of the <see cref="IDbConnection"/> type name.
		/// </summary>
		private string m_connectionType;

		/// <summary>
		/// The text of the command.
		/// </summary>
		private string m_commandText;

		/// <summary>
		/// The command type.
		/// </summary>
		private CommandType m_commandType;

		/// <summary>
		/// Indicates whether to use transactions when writing to the database.
		/// </summary>
		private bool m_useTransactions;

		/// <summary>
		/// Indicates whether to reconnect when a connection is lost.
		/// </summary>
		private bool m_reconnectOnError;

		#endregion // Private Instance Fields

		#region Private Static Fields

		/// <summary>
		/// The fully qualified type of the AdoNetAppender class.
		/// </summary>
		/// <remarks>
		/// Used by the internal logger to record the Type of the
		/// log message.
		/// </remarks>
		private readonly static Type declaringType = typeof(AdoNetAppender);

		#endregion Private Static Fields
	}

	/// <summary>
	/// Parameter type used by the <see cref="AdoNetAppender"/>.
	/// </summary>
	/// <remarks>
	/// <para>
	/// This class provides the basic database parameter properties
	/// as defined by the <see cref="System.Data.IDbDataParameter"/> interface.
	/// </para>
	/// <para>This type can be subclassed to provide database specific
	/// functionality. The two methods that are called externally are
	/// <see cref="Prepare"/> and <see cref="FormatValue"/>.
	/// </para>
	/// </remarks>
	public class AdoNetAppenderParameter
	{
		#region Public Instance Constructors

		/// <summary>
		/// Initializes a new instance of the <see cref="AdoNetAppenderParameter" /> class.
		/// </summary>
		/// <remarks>
		/// Default constructor for the AdoNetAppenderParameter class.
		/// </remarks>
		public AdoNetAppenderParameter()
		{
			Precision = 0;
			Scale = 0;
			Size = 0;
		}

		#endregion // Public Instance Constructors

		#region Public Instance Properties

		/// <summary>
		/// Gets or sets the name of this parameter.
		/// </summary>
		/// <value>
		/// The name of this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The name of this parameter. The parameter name
		/// must match up to a named parameter to the SQL stored procedure
		/// or prepared statement.
		/// </para>
		/// </remarks>
		public string ParameterName
		{
			get { return m_parameterName; }
			set { m_parameterName = value; }
		}

		/// <summary>
		/// Gets or sets the database type for this parameter.
		/// </summary>
		/// <value>
		/// The database type for this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The database type for this parameter. This property should
		/// be set to the database type from the <see cref="DbType"/>
		/// enumeration. See <see cref="IDataParameter.DbType"/>.
		/// </para>
		/// <para>
		/// This property is optional. If not specified the ADO.NET provider 
		/// will attempt to infer the type from the value.
		/// </para>
		/// </remarks>
		/// <seealso cref="IDataParameter.DbType" />
		public DbType DbType
		{
			get { return m_dbType; }
			set
			{
				m_dbType = value;
				m_inferType = false;
			}
		}

		/// <summary>
		/// Gets or sets the precision for this parameter.
		/// </summary>
		/// <value>
		/// The precision for this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The maximum number of digits used to represent the Value.
		/// </para>
		/// <para>
		/// This property is optional. If not specified the ADO.NET provider 
		/// will attempt to infer the precision from the value.
		/// </para>
		/// </remarks>
		/// <seealso cref="IDbDataParameter.Precision" />
		public byte Precision
		{
			get { return m_precision; }
			set { m_precision = value; }
		}

		/// <summary>
		/// Gets or sets the scale for this parameter.
		/// </summary>
		/// <value>
		/// The scale for this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The number of decimal places to which Value is resolved.
		/// </para>
		/// <para>
		/// This property is optional. If not specified the ADO.NET provider 
		/// will attempt to infer the scale from the value.
		/// </para>
		/// </remarks>
		/// <seealso cref="IDbDataParameter.Scale" />
		public byte Scale
		{
			get { return m_scale; }
			set { m_scale = value; }
		}

		/// <summary>
		/// Gets or sets the size for this parameter.
		/// </summary>
		/// <value>
		/// The size for this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The maximum size, in bytes, of the data within the column.
		/// </para>
		/// <para>
		/// This property is optional. If not specified the ADO.NET provider 
		/// will attempt to infer the size from the value.
		/// </para>
		/// <para>
		/// For BLOB data types like VARCHAR(max) it may be impossible to infer the value automatically, use -1 as the size in this case.
		/// </para>
		/// </remarks>
		/// <seealso cref="IDbDataParameter.Size" />
		public int Size
		{
			get { return m_size; }
			set { m_size = value; }
		}

		/// <summary>
		/// Gets or sets the <see cref="IRawLayout"/> to use to 
		/// render the logging event into an object for this 
		/// parameter.
		/// </summary>
		/// <value>
		/// The <see cref="IRawLayout"/> used to render the
		/// logging event into an object for this parameter.
		/// </value>
		/// <remarks>
		/// <para>
		/// The <see cref="IRawLayout"/> that renders the value for this
		/// parameter.
		/// </para>
		/// <para>
		/// The <see cref="RawLayoutConverter"/> can be used to adapt
		/// any <see cref="ILayout"/> into a <see cref="IRawLayout"/>
		/// for use in the property.
		/// </para>
		/// </remarks>
		public IRawLayout Layout
		{
			get { return m_layout; }
			set { m_layout = value; }
		}

		#endregion // Public Instance Properties

		#region Public Instance Methods

		/// <summary>
		/// Prepare the specified database command object.
		/// </summary>
		/// <param name="command">The command to prepare.</param>
		/// <remarks>
		/// <para>
		/// Prepares the database command object by adding
		/// this parameter to its collection of parameters.
		/// </para>
		/// </remarks>
		virtual public void Prepare(IDbCommand command)
		{
			// Create a new parameter
			IDbDataParameter param = command.CreateParameter();

			// Set the parameter properties
			param.ParameterName = ParameterName;

			if (!m_inferType)
			{
				param.DbType = DbType;
			}
			if (Precision != 0)
			{
				param.Precision = Precision;
			}
			if (Scale != 0)
			{
				param.Scale = Scale;
			}
			if (Size != 0)
			{
				param.Size = Size;
			}

			// Add the parameter to the collection of params
			command.Parameters.Add(param);
		}

		/// <summary>
		/// Renders the logging event and set the parameter value in the command.
		/// </summary>
		/// <param name="command">The command containing the parameter.</param>
		/// <param name="loggingEvent">The event to be rendered.</param>
		/// <remarks>
		/// <para>
		/// Renders the logging event using this parameters layout
		/// object. Sets the value of the parameter on the command object.
		/// </para>
		/// </remarks>
		virtual public void FormatValue(IDbCommand command, LoggingEvent loggingEvent)
		{
			// Lookup the parameter
			IDbDataParameter param = (IDbDataParameter)command.Parameters[ParameterName];

			// Format the value
			object formattedValue = Layout.Format(loggingEvent);

			// If the value is null then convert to a DBNull
			if (formattedValue == null)
			{
				formattedValue = DBNull.Value;
			}

			param.Value = formattedValue;
		}

		#endregion // Public Instance Methods

		#region Private Instance Fields

		/// <summary>
		/// The name of this parameter.
		/// </summary>
		private string m_parameterName;

		/// <summary>
		/// The database type for this parameter.
		/// </summary>
		private DbType m_dbType;

		/// <summary>
		/// Flag to infer type rather than use the DbType
		/// </summary>
		private bool m_inferType = true;

		/// <summary>
		/// The precision for this parameter.
		/// </summary>
		private byte m_precision;

		/// <summary>
		/// The scale for this parameter.
		/// </summary>
		private byte m_scale;

		/// <summary>
		/// The size for this parameter.
		/// </summary>
		private int m_size;

		/// <summary>
		/// The <see cref="IRawLayout"/> to use to render the
		/// logging event into an object for this parameter.
		/// </summary>
		private IRawLayout m_layout;

		#endregion // Private Instance Fields
	}
}

#endif // !SSCLI