在C#中读取SQL Server存储过程的返回值?

New*_*0x0 -1 c# sql sql-server stored-procedures

我想捕捉从 C# 中的 SQL Server 存储过程返回的 -1, 0, 1 值。

SQL 服务器:

IF EXISTS(SELECT * FROM _Users WHERE UserName = @UserName AND [Password] != @Password)
BEGIN
    RETURN -1
END

IF EXISTS(SELECT * FROM _Users WHERE UserName != @UserName AND [Password] != @Password)
BEGIN
    RETURN 0
END

IF EXISTS(SELECT * FROM _Users WHERE UserName = @UserName AND [Password]= @Password)
BEGIN
    RETURN 1
END
Run Code Online (Sandbox Code Playgroud)

C#

我们是否可以按照自己的意愿更改下面代码的返回值?

public User getUser(string name, string password)
{
    User user = null;

    using (var connection = Database.GetConnection())
    {
        var command = new SqlCommand("SP_GetUser @UserName, @Password", connection);
        command.Parameters.Add(new SqlParameter("UserName", name));
        command.Parameters.Add(new SqlParameter("Password", password));

        connection.Open();

        using (var reader = command.ExecuteReader())
        {
            while (reader.Read())
            {
                user = new User();
                user.UserId = Convert.ToInt32(reader["UserId"]);
                user.userName = Convert.ToString(reader["UserName"]);
                user.password = Convert.ToString(reader["Password"]);
            }
        }

        connection.Close();
    }

    return user; // I want to return -1, 0, 1
}
Run Code Online (Sandbox Code Playgroud)

在此处输入图片说明

Dal*_*e K 6

SqlParameter returnValueParam = new SqlParameter() { Direction = ParameterDirection.ReturnValue };
command.Parameters.Add(returnValueParam);

// Read everything from your DataReader before trying to obtain the return value
// In fact after you close the connection

var returnValue = returnValueParam.Value;
Run Code Online (Sandbox Code Playgroud)

笔记:

  1. 确保您设置command.CommandType = CommandType.StoredProcedure;(并从 中删除参数,CommandText因为在使用时它只能是 SP 名称CommandType.StoredProcedure)。

  2. 在创建 a 时,您应该始终指定数据类型和比例/精度(如果相关),SqlParameter因为可能会出现意外的副作用,允许自动设置数据类型。完整命名参数也是最佳实践,包括@, 所以

new SqlParameter("UserName", name);
Run Code Online (Sandbox Code Playgroud)

真的应该

// Where the type and length match your SP
new SqlParameter("@UserName", SqlDbType.NVarChar, 128) { Value = name };
Run Code Online (Sandbox Code Playgroud)
  1. 从技术上讲,存储过程的返回值是针对存储过程的“执行状态”。您通常会使用OUTPUT参数来返回用户数据。但是,在我看来,您的用例与任何用例一样好。

  2. 正如@marc_s 所指出的:您不应sp_为存储过程使用前缀。Microsoft 已保留该前缀供自己使用(请参阅命名存储过程),并且您确实会在将来的某个时候冒名称冲突的风险。这对您的存储过程性能也不利。最好只是简单地避免sp_并使用其他东西作为前缀 - 或者根本不使用前缀!