MySQL ODBC 存储过程结果缺少列

Posted

技术标签:

【中文标题】MySQL ODBC 存储过程结果缺少列【英文标题】:MySQL ODBC Stored Procedure result is missing columns 【发布时间】:2010-12-07 04:13:19 【问题描述】:

我有一组用于填充 ASP.Net CheckBoxList 的存储过程。从代码运行此过程时, CALL ProcedureName(params);将类型设置为存储过程,我似乎只得到了部分结果(即实际结果中的许多列都丢失了。)

如果我从查询中复制 CommandText(使用断点来获取发送的确切文本)并直接在 Navicat(或任何其他 mysql GUI)中运行它,我会得到所有预期的列。

这是不工作的代码:

using (OdbcCommand command = OdbcConnection.CreateCommand())

    command.CommandType = CommandType.StoredProcedure;
    command.CommandText = " " + string.Format(StoredProcedureCall, foundationId, fpids, "", "", "NULL", "2001/01/02", "2001/01/01", "*") +
                          " ";
    using (OdbcDataReader reader = command.ExecuteReader())
    

        for (int i = 0; i < reader.FieldCount; i++)
        
            columns.Add(reader.GetName(i));
        
    

如果我将代码更改为以下代码,但它开始工作(仅添加其他使用):

using (OdbcConnection)
using (OdbcCommand command = OdbcConnection.CreateCommand())

    command.CommandType = CommandType.StoredProcedure;
    command.CommandText = " " + string.Format(StoredProcedureCall, foundationId, fpids, "", "", "NULL", "2001/01/02", "2001/01/01", "*") +
                          " ";
    using (OdbcDataReader reader = command.ExecuteReader())
    

        for (int i = 0; i < reader.FieldCount; i++)
        
            columns.Add(reader.GetName(i));
        
    

这是怎么回事?

这里是 OdbcConnection 属性供参考:

public static OdbcConnection OdbcConnection

    get
    
        // If we have no connection or our connection isn't open
        if (null == odbcConnection || ConnectionState.Open != odbcConnection.State)
        
            odbcConnection = new OdbcConnection(BaseAccess.DBConnectionString);
            odbcConnection.Open();
        

        return odbcConnection;
    

【问题讨论】:

如果您的应用程序使用与 Navicat 相同的登录凭据? 是的,它们使用相同的用户/密码运行 您是如何发现缺少列的?你用什么来存储SP发送的数据? 将 C# 代码中 ODBC 阅读器中的结果读入列表。这个列表是缺少许多列的地方(以及用作 CheckBoxList 的数据源的地方) 这可能是 ODBC/MySql 中的错误。缺少的列是否具有相同的类型?还是其他共同点?您可以使用 ADO.NET Driver for MySQL 代替 ODBC 并查看结果吗? 【参考方案1】:

这可能是 Odbc MySql 驱动程序中的错误。尝试使用ADO.NET driver。另外,我建议您不要在静态属性中手动处理连接。将此任务留给 ADO.NET,它将有效地处理连接池:

using (var conn = new MySqlConnection(DBConnectionString))
using (var cmd = conn.CreateCommand())

    conn.Open();
    cmd.CommandType = CommandType.StoredProcedure;
    cmd.CommandText = "sp_name";

    cmd.Parameters.Add(new SqlParameter("@foundationId", foundationId));
    cmd.Parameters.Add(new SqlParameter("@fpids", fpids));
    ...

    using (var reader = cmd.ExecuteReader())
    
        for (int i = 0; i < reader.FieldCount; i++)
        
            columns.Add(reader.GetName(i));
        
    

【讨论】:

ADO.Net 驱动程序实际上使问题变得更糟。如果没有额外的 using 语句,它不会返回所有带有 OR 的列。【参考方案2】:

确保您的列都有唯一的名称。

【讨论】:

非唯一命名的列会抛出 MySQL 异常。没有这样的例外。更不用说该过程强制将唯一的列名作为代码的一部分,因为它们都是编号的(q1:blah,q2:blah,等等)【参考方案3】:

这在某种程度上与重用连接和存储过程中的某些 @ 变量在运行之间未重置有关。更改为正确关闭/处理的池连接是解决我的问题的原因。

【讨论】:

以上是关于MySQL ODBC 存储过程结果缺少列的主要内容,如果未能解决你的问题,请参考以下文章

SQL 2005 存储过程结果集的 ODBC 执行/获取不能使用表 @variable

存储过程抛出“缺少列规范”

如何在存储过程中直接使用另一个存储过程返回的数据集

在MySQL中如何创建一个带输出参数为一个表类型的存储过程

mysql为四个表创建储存过程或者储存函数

SQL SERVER里面如何在存储过程里面获取另一个存储过程所返回的表的数据?