我有一个应用程序触发mysql命令(查询)“显示数据库”,查询工作并正确返回但我无法关闭我的连接。我使用的用户同时允许24个连接,所以问题突然出现在我的程序中,但是将允许的连接减少到2表明我甚至无法关闭第一个查询(不在循环中)。代码如下:
protected override Dictionary<string, Jerow_class_generator.Database> loadDatabases()
{
MySqlConnection sqlCon = new MySqlConnection(this.ConnectionString);
sqlCon.Open();
MySqlCommand sqlCom = new MySqlCommand();
sqlCom.Connection = sqlCon;
sqlCom.CommandType = CommandType.Text;
sqlCom.CommandText = "show databases;";
MySqlDataReader sqlDR;
sqlDR = sqlCom.ExecuteReader();
Dictionary<string, Jerow_class_generator.Database> databases = new Dictionary<string, Jerow_class_generator.Database>();
string[] systemDatabases = new string[] { "information_schema", "mysql" };
while (sqlDR.Read())
{
string dbName = sqlDR.GetString(0);
if (!systemDatabases.Contains(dbName))
{
databases.Add(sqlDR.GetString(0), new MySQL.Database(dbName, this));
}
}
sqlCom.Dispose();
sqlDR.Close();
sqlCon.Close();
sqlCon.Dispose();
return databases;
}
P.S。 'New MySQL.Database(dbName,this));'是我自己制作的只存储数据库结构的类,可以认为是不相关的。
我得到的确切错误是'max_user_connections'。在下次需要触发查询时的connection.open行上。
答案 0 :(得分:7)
我建议您只使用using
statements替换所有内容,而不是跟踪所有Open
/ Close
/ Dispose
来电。这将确保每个对象的预期范围是明确的,并且在退出该范围时将被销毁/处置。
答案 1 :(得分:2)
Close()
或using
将单独解决您的问题,因为ADO.NET正在使用自己的连接池,默认情况下连接在程序关闭之前不会关闭。解决这个问题的方法很少,但考虑到性能影响,这是您的应用程序真正需要的行为。
有关详细信息,请参阅:SQL Server Connection Pooling (ADO.NET)
答案 2 :(得分:1)
除了上面的using
建议,在创建sqlDR
变量时,如果这是您的预期操作,则应使用CloseConnection
命令行为关闭实际连接。如文档here中所述。
When the command is executed, the associated Connection object is closed when the associated DataReader object is closed.
因此,实例化读者的代码如下所示:
//to instantiate your variable
MySqlDataReader sqlDR;
sqlDR = sqlCom.ExecuteReader(CommandBehavior.CloseConnection);
//closing your datareader reference here will close the connection as well
sqlDR.Close();
如果您使用上述方法将所有代码包装在using
块中,则除了Close()
之外,您不需要任何Dispose()
或sqlDR.Close();
方法
答案 3 :(得分:0)
当使用“使用”关键词时会发生什么事情。当垃圾收集器激活它时,首先处理使用语句删除的对象。
答案 4 :(得分:0)
我建议将连接池与MySqlHelper类结合使用,将连接字符串作为第一个参数传递。这允许MySQL在必要时打开连接,或者根据池化cfg保持打开状态,而不必了解它。
答案 5 :(得分:0)
我将我的代码更改为使用1个连接并保持打开状态,并且在测试时遇到了一个错误,即应关闭datareader。现在因为我的所有查询都没有关闭dataReader对象(我使用了dataTable.Load(cmd.ExecuteReader())。)我认为问题可能就在那里。
保持1个开放式连接工作正常,所以我不知道是什么原因导致了未关闭的问题。我猜这是dataReader本身没有关闭。