连接状态 MySql Connector/NET
Posted
技术标签:
【中文标题】连接状态 MySql Connector/NET【英文标题】:Connection state MySql Connector/NET 【发布时间】:2012-04-29 17:01:24 【问题描述】:我正在使用最新的稳定版 mysql Connector/NET 6.5.4.0。
我打开一个到 MySQL 数据库的连接。在 C# 代码中,Connection.State
属性为Open
。
我做了一些神奇的事情,当我这样做的时候,我杀死了连接服务器端。但是,在代码中,State 仍然是Open
。
我遇到了这个问题,因为我将数据库类的实例保存在每个会话的静态变量(字典)中。 如果用户发出请求,则从该变量中提取数据库类,并向其触发查询。 但是,如果连接关闭服务器端(被 de sysadmin 杀死,等待超时),则不会更新状态。
是否有解决此问题的方法?我的同事已经为它提交了错误报告 (http://bugs.mysql.com/bug.php?id=64991)。
在执行前关闭和打开,对性能非常不利,所以没有选择。
【问题讨论】:
你看过connection.Ping方法了吗?如果为假,则连接关闭。 dev.mysql.com/doc/refman/5.0/en/… 您可能还想订阅连接上的 StateChange 事件以检查发生了什么。作为一般建议,您可能不应该将连接缓存为静态成员;只要连接池处于打开状态,您就不会通过保持连接实例看到任何有意义的性能提升。另外,如果出现错误怎么办? 在这种情况下连接池被关闭,我将研究 Ping 方法。如果此连接关闭,我会收到“命令执行期间遇到致命错误” Ping() 方法有效,但需要很长时间(每次调用 0.020 秒)。 StateChange 事件触发得太晚(调用执行阅读器时)。 【参考方案1】:搁置设计问题(应该是池化),根据您的评论:
在这种情况下连接池已关闭,我将查看 Ping 方法。如果此连接关闭,我会收到“致命错误” 在命令执行过程中遇到'
如果 ping 失败,您是否有任何原因不重新创建连接?
private static MySqlConnection conn;
private static int maxRetries;
private static void connect()
conn = <connect code>;
private static MySqlConection GetConnectionRetry(int count)
if (conn != null && conn.State == Open)
try
conn.Ping();
return conn;
catch (Exception e) // better be specific here
if (count <= maxRetries)
connect();
return GetConnectionRetry(count + 1);
else throw e;
else
connect();
return GetConnectionRetry(count + 1);
static MySqlConnection GetConnection()
return GetConnectionRetry(1);
【讨论】:
Ping
方法需要很多时间。如果我必须在每个命令之前 ping,这是一个巨大的性能问题
没有 ping 怎么办?它仍然会抛出异常,其余逻辑将接管。
是的,我可以做到这一点,但在我看来这仍然是一个丑陋的解决方法
它处于异常场景中,它隐藏在 API 后面。但你的选择!
该解决方案的另一点是事务。如果有一个打开的事务,并且查询失败,我必须关闭并打开连接。事务回滚,但新执行的命令被执行,而它应该在同一个事务中..【参考方案2】:
我建议您使用单点模式进行连接。因此,您可以确保始终只打开一个连接,并且您只需管理这个连接。
【讨论】:
在这种情况下,我们不希望所有用户都有一个连接,而是每个用户有一个连接。以上是关于连接状态 MySql Connector/NET的主要内容,如果未能解决你的问题,请参考以下文章