问题 什么时候SqlCommand.ExecuteReader()会返回null?


当使用呼叫时 SqlCommand.ExecuteReader() 方法,ReSharper告诉我,当我之后使用SqlDataReader对象时,我有一个可能的NullReference异常。

所以使用以下代码:

using (SqlConnection connection = GetConnection())
{
    using (SqlCommand cmd = connection.CreateCommand())
    {
        cmd.CommandText = ; //snip

        using (SqlDataReader reader = cmd.ExecuteReader())
        {
            while (reader.Read())
            {
                //snip
            }
        }
    }
}

while (reader.Read()) 行加下划线。

我的问题是读者对象何时会为空?我从来没有遇到它,文档没有提到它可能。我应该检查它是否为空或忽略是否安全?

为什么ReSharper认为它可能为null,例如它允许我使用SqlCommand而不建议检查null?我猜是ExecuteReader方法有一个属性。


6754
2017-07-02 02:08


起源



答案:


这是误报。

反思SqlDataReader.ExecuteReader,我可以看到读取器返回null的唯一方法是,如果内部RunExecuteReader方法为returnStream传递'false',它不是。

在SqlDataReader的深处, 一个 读者构造函数总是在某个时候被调用,所以我很确定ExecuteReader在物理上不可能返回null。


11
2017-07-02 03:03





Resharper是正确的,它可以返回null潜力。

如果具体实现,则无关紧要 ExecuteReader() 不允许冒出一个空值 - 事实上,IDataReader是一个可以包含(或指向)null的对象。

  • 如果您将来决定使用不同的实现,该怎么办? IDbCommand
  • 如果该IDbCommnd实现的下一次更新将在代码中包含一个允许冒泡null的不同流程怎么办?

您不需要知道接口实现中发生了什么,以便正确使用它  - 你只需要知道接口,现在接口允许null作为返回值。


3
2017-12-24 17:21





我在其他几个方面遇到过这个问题。看起来他们已经对CLR的各个部分中的代码路径进行了分析。当他们发现可以想到返回null时,那就是他们抱怨它的时候。

在我抱怨的特定情况下,null实际上不会发生。但是,在某些情况下,它们将调用图跟踪到一个可以返回null的方法,并且可以想象空值可以传播到顶部。

所以,我称之为ReSharper错误(我之前称之为CLR错误)。


2
2017-07-02 02:56





我已经确定了ExecuteReader()可以返回null的一个原因。

在我获得null的情况下,我向客户端发送了一个脚本来更新存储过程。设置了我的客户端的Sql Server(2000),以便DB用户需要权限来执行存储过程。当他们更新SP时,权限被删除而不是重新分配。在这个实例中,SqlCommand.ExecuteReader()返回null。

重新分配权限修复此问题。


0
2018-01-18 10:20





我有一个问题,我查询.dbo.sysfiles的日志文件,得到了一个 null 作为回报。 我让我的客户端连接为系统管理员的SYSTEM用户,不确定发生了什么...


0
2018-03-17 12:12