1 message in com.mysql.lists.dotnetConnector/NET commit: r121 - in branc...
FromSent OnAttachments
rbur...@mysql.com10 Aug 2005 11:02 
Subject:Connector/NET commit: r121 - in branches/1.0: . TestSuite mysqlclient
From:rbur...@mysql.com (rbur@mysql.com)
Date:08/10/2005 11:02:50 AM
List:com.mysql.lists.dotnet

Modified: branches/1.0/CHANGES branches/1.0/TestSuite/CommandTests.cs branches/1.0/TestSuite/LanguageTests.cs branches/1.0/mysqlclient/PreparedStatement.cs branches/1.0/mysqlclient/command.cs branches/1.0/mysqlclient/nativedriver.cs Log: fixed Bug #12245 using Prepare() on an insert command causes null parameters
to convert to "0"

Modified: branches/1.0/CHANGES =================================================================== --- branches/1.0/CHANGES 2005-08-10 16:39:59 UTC (rev 120) +++ branches/1.0/CHANGES 2005-08-10 18:03:11 UTC (rev 121) @@ -37,7 +37,8 @@ Bug #11873 Invalid timestamp in query produces incorrect reader exception
[added test case, already fixed] Bug�#10454 incorrect return type documented for parameter collection Add
methods [fixed] Bug #12163 Insert using prepared statement causes double insert - + Bug #12245 using Prepare() on an insert command causes null parameters to
convert to "0" + Other changes ------------- Fixed problem parsing stored procedure parameter defs such as OUT val INT
UNSIGNED

Modified: branches/1.0/TestSuite/CommandTests.cs =================================================================== --- branches/1.0/TestSuite/CommandTests.cs 2005-08-10 16:39:59 UTC (rev 120) +++ branches/1.0/TestSuite/CommandTests.cs 2005-08-10 18:03:11 UTC (rev 121) @@ -224,6 +224,38 @@ }

/// <summary> + /// Bug #12245 using Prepare() on an insert command causes null parameters
to convert to "0" + /// </summary> + [Test] + public void InsertingPreparedNulls() + { + execSQL("TRUNCATE TABLE test"); + MySqlCommand cmd = new MySqlCommand("INSERT INTO test VALUES(1, ?str)",
conn); + cmd.Parameters.Add("?str", MySqlDbType.VarChar); + cmd.Prepare(); + + cmd.Parameters[0].Value = null; + cmd.ExecuteNonQuery(); + + cmd.CommandText = "SELECT * FROM test"; + MySqlDataReader reader = null; + try + { + reader = cmd.ExecuteReader(); + Assert.IsTrue(reader.Read()); + Assert.AreEqual(DBNull.Value, reader[1]); + } + catch (Exception ex) + { + Assert.Fail(ex.Message); + } + finally + { + if (reader != null) reader.Close(); + } + } + + /// <summary> /// MySQL Bugs: #12163: Insert using prepared statement causes double insert /// </summary> [Test] @@ -236,11 +268,22 @@ reader.Close();

cmd.CommandText = "SELECT * FROM test"; - reader = cmd.ExecuteReader(); - Assert.IsTrue(reader.Read()); - Assert.IsFalse(reader.Read()); - Assert.IsFalse(reader.NextResult()); - reader.Close(); + reader = null; + try + { + reader = cmd.ExecuteReader(); + Assert.IsTrue(reader.Read()); + Assert.IsFalse(reader.Read()); + Assert.IsFalse(reader.NextResult()); + } + catch (Exception ex) + { + Assert.Fail(ex.Message); + } + finally + { + if (reader != null) reader.Close(); + } }

/// <summary>

Modified: branches/1.0/TestSuite/LanguageTests.cs =================================================================== --- branches/1.0/TestSuite/LanguageTests.cs 2005-08-10 16:39:59 UTC (rev 120) +++ branches/1.0/TestSuite/LanguageTests.cs 2005-08-10 18:03:11 UTC (rev 121) @@ -146,6 +146,78 @@ }

[Test()] + public void UTF8PreparedAndUsingParameters() + { + if (!Is41 && !Is50) return; + + execSQL("DROP TABLE IF EXISTS Test"); + execSQL("CREATE TABLE Test (name VARCHAR(200) CHAR SET utf8)"); + + MySqlConnection c = new MySqlConnection( conn.ConnectionString +
";charset=utf8" ); + c.Open(); + + MySqlCommand cmd = new MySqlCommand( "INSERT INTO Test VALUES(?val)", c); + cmd.Parameters.Add("?val", MySqlDbType.VarChar); + cmd.Prepare(); + + cmd.Parameters[0].Value = "ЁЄЉҖҚ"; // Russian + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "兣冘凥凷冋"; // simplified Chinese + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "困巫忘否役"; // traditional Chinese + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "涯割晦叶角"; // Japanese + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "ברחפע"; // Hebrew + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "ψόβΩΞ"; // Greek + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "þðüçöÝÞÐÜÇÖ"; // Turkish + cmd.ExecuteNonQuery(); + + cmd.Parameters[0].Value = "ฅๆษ"; // Thai + cmd.ExecuteNonQuery(); + + cmd.CommandText = "SELECT * FROM Test"; + MySqlDataReader reader = null; + try + { + reader = cmd.ExecuteReader(); + reader.Read(); + Assert.AreEqual("ЁЄЉҖҚ", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("兣冘凥凷冋", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("困巫忘否役", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("涯割晦叶角", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("ברחפע", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("ψόβΩΞ", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("þðüçöÝÞÐÜÇÖ", reader.GetString(0)); + reader.Read(); + Assert.AreEqual("ฅๆษ", reader.GetString(0)); + } + catch (Exception ex) + { + Assert.Fail( ex.Message ); + } + finally + { + if (reader != null) reader.Close(); + c.Close(); + } + } + + [Test()] public void Chinese() { if (!Is41 && !Is50) return;

Modified: branches/1.0/mysqlclient/PreparedStatement.cs =================================================================== --- branches/1.0/mysqlclient/PreparedStatement.cs 2005-08-10 16:39:59 UTC (rev
120) +++ branches/1.0/mysqlclient/PreparedStatement.cs 2005-08-10 18:03:11 UTC (rev
121) @@ -57,6 +57,7 @@ public int ExecutionCount { get { return executionCount; } + set { executionCount = value; } }

#endregion @@ -74,7 +75,8 @@ BitArray nullMap = new BitArray( parameters.Count ); //metaData.Length ); for (int x=0; x < parameters.Count; x++) { - if (parameters[x].Value == DBNull.Value) + if (parameters[x].Value == DBNull.Value || + parameters[x].Value == null) nullMap[x] = true; } byte[] nullMapBytes = new byte[ (parameters.Count + 7)/8 ]; @@ -85,10 +87,10 @@ packet.WriteByte( 0 ); // flags; always 0 for 4.1 packet.WriteInteger( 1, 4 ); // interation count; 1 for 4.1 packet.Write( nullMapBytes ); - if (parameters != null && parameters.Count > 0) + //if (parameters != null && parameters.Count > 0) packet.WriteByte( 1 ); // rebound flag - else - packet.WriteByte( 0 ); + //else + // packet.WriteByte( 0 ); //TODO: only send rebound if parms change

// write out the parameter types @@ -102,13 +104,13 @@ foreach ( MySqlField param in paramList ) { MySqlParameter parm = parameters[ param.ColumnName ]; - if (parm.Value == DBNull.Value) continue; + if (parm.Value == DBNull.Value || parm.Value == null) continue;

packet.Encoding = param.Encoding; parm.Serialize( packet, true ); }

-// executionCount ++; + executionCount ++; // send the data packet and return the CommandResult return driver.ExecuteStatement(
((System.IO.MemoryStream)packet.Stream).ToArray() ); }

Modified: branches/1.0/mysqlclient/command.cs =================================================================== --- branches/1.0/mysqlclient/command.cs 2005-08-10 16:39:59 UTC (rev 120) +++ branches/1.0/mysqlclient/command.cs 2005-08-10 18:03:11 UTC (rev 121) @@ -237,8 +237,12 @@ /// </summary> internal void Consume() { - // if we are using prepared statements, then nothing to clean up - //if (preparedStatement != null) return; + // if we are using prepared statements, we have executed the statement at + // least once, and we did not get an active resultset from it + // then we don't need to check for another resultset + if (preparedStatement != null && preparedStatement.ExecutionCount > 0 && + lastResult == null) + return;

CommandResult result = GetNextResultSet(null); while (result != null) @@ -266,8 +270,6 @@ (reader.Behavior & CommandBehavior.SingleResult) != 0 && lastResult != null) return null;

- bool firstTime = lastResult == null; - // if the last result we returned has more results if (lastResult != null && lastResult.ReadNextResult(false) ) return lastResult; @@ -283,15 +285,12 @@ // if we have a prepared statement, we execute it instead if (preparedStatement != null) { - if (! firstTime) return null; -// if (preparedStatement.ExecutionCount != 0) return null; result = preparedStatement.Execute( parameters );

if (! result.IsResultSet) { if (updateCount == -1) updateCount = 0; updateCount += (long)result.AffectedRows; - preparedStatement = null; } } else @@ -349,6 +348,8 @@

if (preparedStatement == null) sqlBuffers = PrepareSqlBuffers(CommandText); + else + preparedStatement.ExecutionCount = 0;

try { @@ -403,6 +404,8 @@ // if we don't have a prepared statement, then prepare our sql for execution if (preparedStatement == null) sqlBuffers = PrepareSqlBuffers(sql); + else + preparedStatement.ExecutionCount = 0;

reader.NextResult(); connection.Reader = reader;

Modified: branches/1.0/mysqlclient/nativedriver.cs =================================================================== --- branches/1.0/mysqlclient/nativedriver.cs 2005-08-10 16:39:59 UTC (rev 120) +++ branches/1.0/mysqlclient/nativedriver.cs 2005-08-10 18:03:11 UTC (rev 121) @@ -636,6 +636,11 @@ { ReadFieldMetadata( numParams, ref parameters );

+ // we set the encoding for each parameter back to our connection encoding + // since we can't trust what is coming back from the server + for (int i=0; i < parameters.Length; i++) + parameters[i].Encoding = encoding; + if (parmNames.Length != parameters.Length) throw new MySqlException("Incorrect number of parameters received for
prepared statement");