我遇到一个错误,说我的datareader已经打开了。
我的代码看起来像这样
public static Users GetByID(int ID, SqlConnection connection)
{
SqlCommand command = new SqlCommand("Select Name, Email, LastLogin, FK_Role_ID from Users where ID=@id");
command.Connection = connection;
command.Parameters.Add(new SqlParameter("id", ID));
SqlDataReader reader = command.ExecuteReader();
if (reader.Read())
{
Users user = new Users();
user.ID = ID;
user.Name = reader.GetString(0);
user.Email = reader.GetString(1);
user.LastLogin = reader.GetString(2);
user.role = Role.GetRoleByID(reader.GetInt32(3), connection);
reader.Close();
return user;
}
else
{
reader.Close();
return null;
}
}
Role.GetRoleByID中出现错误,表示datareader命令是alreader open。这是真的,但我如何使用读者的信息调用Role.GetRoleByID。
我在c#和ASP.NET中编码
答案 0 :(得分:4)
您的Role.GetRoleByID
似乎会尝试重复使用该连接。
选项:
SqlDataReader
中GetByID
获取所需数据,关闭该读卡器,然后调用Role.GetRoleByID
(因此您只有一个活跃的读者一次)如果我是你,我会选择第一个选项 - 或者可能是最后一个选项。我还会使用using
语句自动关闭阅读器:
private const string GetUserByIdSql =
"Select Name, Email, LastLogin, FK_Role_ID from Users where ID=@id";
public static Users GetByID(int ID, SqlConnection connection)
{
var sql = ;
Users user;
int roleId;
using (var command = new SqlCommand(GetUserByIdSql, connection))
{
command.Parameters.Add(new SqlParameter("id", ID));
using (var reader = command.ExecuteReader())
{
if (!reader.Read())
{
return null;
}
user = new Users
{
Name = reader.GetString(0),
Email = reader.GetString(1),
LastLogin = reader.GetString(2),
};
// Remember this so we can call GetRoleByID after closing the reader
roleID = reader.GetInt32(3);
}
}
user.Role = Role.GetRoleByID(roleID, connection);
return user;
}
作为第四个选项 - 为什么不在现有查询中执行GetRoleByID
所需的加入?这意味着你只需要一次数据库之旅。
答案 1 :(得分:2)
您可以考虑使用带有必需连接的Select查询,以便能够从同一查询中接收角色。
此外,建议使用(using reader = command.ExecuteReader() )
,以便在范围结束后关闭阅读器并进行处理。
答案 2 :(得分:1)
您是否允许MARS连接字符串(MultipleActiveResultSets=true
)?