Bug #13991 oldsyntax configuration and ParameterMarker value bug
Submitted: 13 Oct 2005 6:28 Modified: 13 Nov 2007 12:43
Reporter: Matt Petteys
Status: Closed
Category:Connector/Net Severity:S4 (Feature request)
Version:1.0.6 OS:Linux (Linux/Windows)
Assigned to: Target Version:
Triage: D5 (Feature request)

[13 Oct 2005 6:28] Matt Petteys
Description:

I use mssql data access classes build in vs.net that are converted over to mysql data
access classes using the MysqlClient namespace.  Since this classes are built for mssql
and then converted to mysql, it requires use of the @ parameters and therefore requires
the oldsyntax directive.  The component classes create and configure the objects
(Connections, Commands, etc) first (without the dsn) and then set the appropriate dsn
right before the commands are executed.   Since all classes are initalized first the
MySqlParameterCollection class is initalized using the ? ParameterMarker.  Once the
connection is initialized with the dsn, the connection class is referencing the correct
ParameterMarker @ but the MySqlParameterCollection is still referencing the
ParameterMarker of ?.  Of couse the queries then fail.

How to repeat:

Initialize a command using a connection that is not using the oldsyntax directive. 
Update the command text with a statement that uses @ parameters.  Update the dsn of the
connection to use the oldsyntax configuration in the dsn.  Attempt to execute the Command
and it should fail because the Command still references the ParameterMarker of ?.

Suggested fix:

This removes the paramMarker value from the parameter collection object in favor of a
reference to the MySqlConnection object.  If the connection object is updated, the
parameter collection knows about the change through the reference to the
MySqlConnection.

--- C:\Documents and
Settings\mpetteys\Desktop\mysqlclient.1.0.6\parameter_collection.cs	Thu Jul 14 09:43:20
2005
+++ C:\Program Files\mysql\MySQL Connector Net
1.0.6\src\MySqlClient\parameter_collection.cs	Wed Oct 12 23:58:44 2005
@@ -36,6 +36,7 @@
 	{
 		private ArrayList	_parms = new ArrayList();
 		private char		paramMarker = '?';
+		private MySqlConnection _connection;
 
 		internal char ParameterMarker 
 		{
@@ -43,6 +44,12 @@
 			set { paramMarker = value; }
 		}
 
+		public MySqlConnection Connection
+		{
+			get { return _connection;  }
+			set { _connection = value; }
+		}
+
 		private int InternalIndexOf(string name)
 		{
 			int index = IndexOf(name);
@@ -202,14 +209,14 @@
 		/// <returns>The zero-based location of the <see cref="MySqlParameter"/> in the
collection.</returns>
 		public int IndexOf(string parameterName)
 		{
-			if (parameterName[0] == paramMarker)
+			if (parameterName[0] == this.Connection.ParameterMarker)
 				parameterName = parameterName.Substring(1, parameterName.Length-1);
 			parameterName = parameterName.ToLower();
 			for (int x=0; x < _parms.Count; x++) 
 			{
 				MySqlParameter p = (MySqlParameter)_parms[x];
 				string listName = p.ParameterName;
-				if (listName[0] == paramMarker)
+				if (listName[0] == this.Connection.ParameterMarker)
 					listName = listName.Substring(1, listName.Length-1);
 				if (listName.ToLower() == parameterName) return x;
 			}
--- C:\Documents and Settings\mpetteys\Desktop\mysqlclient.1.0.6\command.cs	Fri Aug 19
15:47:52 2005
+++ C:\Program Files\mysql\MySQL Connector Net 1.0.6\src\MySqlClient\command.cs	Wed Oct
12 23:57:17 2005
@@ -67,8 +67,6 @@
 		public MySqlCommand(string cmdText, MySqlConnection connection) : this(cmdText)
 		{
 			Connection = connection;
-			if (connection != null)
-				parameters.ParameterMarker = connection.ParameterMarker;
 		}
 
 		/// <include file='docs/mysqlcommand.xml' path='docs/ctor4/*'/>
@@ -145,8 +143,7 @@
 					this.Transaction = null;
 
 				connection = (MySqlConnection)value;
-				if (connection != null)
-					parameters.ParameterMarker = connection.ParameterMarker;
+				parameters.Connection = connection;
 			}
 		}
 
@@ -555,12 +552,12 @@
 
 			foreach (string token in tokens)
 			{
-				if ( token[0] != parameters.ParameterMarker )
+				if ( token[0] != this.Connection.ParameterMarker )
 					newSQL.Append( token );
 				else
 				{
 					parameterMap.Add( token );
-					newSQL.Append( parameters.ParameterMarker );
+					newSQL.Append( this.Connection.ParameterMarker );
 				}
 			}
 
@@ -601,12 +598,12 @@
 					delim=c;
 				else if (c == '\\') 
 					escaped = ! escaped;
-				else if (c == parameters.ParameterMarker && delim == Char.MinValue && ! escaped) 
+				else if (c == this.Connection.ParameterMarker && delim == Char.MinValue && !
escaped) 
 				{
 					tokens.Add( sqlPart.ToString() );
 					sqlPart.Remove( 0, sqlPart.Length ); 
 				}
-				else if (sqlPart.Length > 0 && sqlPart[0] == parameters.ParameterMarker && 
+				else if (sqlPart.Length > 0 && sqlPart[0] == this.Connection.ParameterMarker && 
 					! Char.IsLetterOrDigit(c) && c != '_' && c != '.' && c != '$')
 				{
 					tokens.Add( sqlPart.ToString() );
[13 Oct 2005 6:30] Matt Petteys
parameter_collection.1.0.6.diff

Attachment: parameter_collection.1.0.6.diff (text/x-patch), 1.43 KiB.

[13 Oct 2005 6:30] Matt Petteys
command.1.0.6.diff

Attachment: command.1.0.6.diff (text/x-patch), 1.78 KiB.

[6 Nov 2007 17:09] Bugs System
A patch for this bug has been committed. After review, it may
be pushed to the relevant source trees for release in the next
version. You can access the patch from:

  http://lists.mysql.com/commits/37194
[6 Nov 2007 17:15] Bugs System
A patch for this bug has been committed. After review, it may
be pushed to the relevant source trees for release in the next
version. You can access the patch from:

  http://lists.mysql.com/commits/37196
[6 Nov 2007 17:20] Bugs System
A patch for this bug has been committed. After review, it may
be pushed to the relevant source trees for release in the next
version. You can access the patch from:

  http://lists.mysql.com/commits/37197
[6 Nov 2007 17:20] Reggie Burnett
Fixed in 1.0.11, 5.0.9, and 5.1.4+
[13 Nov 2007 12:43] MC Brown
A note has been added to the 1.0.11, 5.0.9 and 5.1.4 changelogs: 

        Changing the connection string of a connection to one that
        changes the parameter marker after the connection had been
        assigned to a command but before the connection is opened could
        cause parameters to not be found.