【问题标题】:How to send Boolean value to an Insert stored procedure in SQL Server?如何将布尔值发送到 SQL Server 中的插入存储过程?
【发布时间】:2014-03-05 19:24:14
【问题描述】:

我正在尝试将一些值发送到 Insert 存储过程,在我的代码中:

    private void btnEnter_Click(object sender, EventArgs e)
    {
        string[] parName = new string[6];
        parName[0] = "@username";
        parName[1] = "@password";
        parName[2] = "@fName";
        parName[3] = "@lName";
        parName[4] = "@gender";
        parName[5] = "@post";
        string[] parValue = new string[6];
        string gender = (rbWoman.Checked) ? "0" : "1";
        parValue[0] = txtUserName.Text;
        parValue[1] = txtPassword.Text;
        parValue[2] = txtFName.Text;
        parValue[3] = txtLName.Text;
        parValue[4] = gender;
        parValue[5] = (cb.SelectedIndex + 1).ToString();
        int affect = _clsT.Insert_Data("sp_Insert_User", parName, parValue);
        if (affect > 0)
            MessageBox.Show("ok");
        else
            MessageBox.Show(affect.ToString());
    }

这里是Insert_Data 函数,它调用存储过程并向其发送参数...

protected int executeCommand(string query, Param[] p)
{
        try
        {
            connect();
            int affect = 0;
            SqlCommand cmd = new SqlCommand(query, _con);
            cmd.CommandType = CommandType.StoredProcedure;
            int count = p.GetUpperBound(0) + 1;
            for (int i = 0; i < count; i++)
                cmd.Parameters.AddWithValue(p[i].parName, p[i].parValue);
            affect = cmd.ExecuteNonQuery();
            return affect;
        }
        catch(SqlException ex)
        {
            return ex.Number;
        }
    }

最后是存储过程代码:

ALTER PROCEDURE [dbo].[sp_Insert_User]
     @username varchar(20), 
     @password varchar(20),
     @fName nvarchar(20),
     @lName nvarchar(20),
     @gender bit,
     @post tinyint
AS
BEGIN
    INSERT INTO admin(username, password, fName, lName, gender, post)
    VALUES (@username, @password, @fName, @lName, @gender, @post)
END

当我使用这些值 (j123, s123, john, smith, true, 1) 执行此存储过程时,存储过程正常执行并影响值,但当我尝试执行 C# 代码时,我收到 8114 错误。

所以我搜索并发现原因错误,因为它的类型是 bool 的性别值。

之后我尝试发送 0 或 1 而不是 false 或 true,但错误仍然存​​在。

那么您能告诉我一些消除此错误的指南吗?

【问题讨论】:

  • 不要以纯文本形式存储密码
  • 旁注:您应该为您的存储过程使用sp_ 前缀。微软有reserved that prefix for its own use (see Naming Stored Procedures),你确实会在未来某个时候冒着名称冲突的风险。 It's also bad for your stored procedure performance。最好只是简单地避免 sp_ 并使用其他东西作为前缀 - 或者根本不使用前缀!
  • "之后我尝试发送 0 或 1 而不是 false 或 true,但错误仍然存​​在。"- 现在尝试发送 'false' 或 'true'
  • 很抱歉我早早做出了判断。感谢所有,但 marc_s 是对的,我想知道只是一个前缀会导致这个错误:|
  • return ex.Number; 是您可能忽略错误的最无意义的邪恶方式。

标签: c# stored-procedures sql-server-2008-r2


【解决方案1】:

如果您read the documentation,CLR 会将 Sql Server 数据类型 bit 映射到 C# boolNullable&lt;bool&gt;(又名bool?)或SqlBoolean

所以...

给定一张桌子,

create table dbo.foo
(
  id         int          not null identity(1,1) primary key clustered ,
  name       varchar(200) not null ,
  gender     bit              null ,
  send_email bit          not null ,
)

给定一个存储过程,

create procedure dbo.InsertFoo

  @name       varchar(200) ,
  @gender     bit ,
  @send_email bit 

as

  insert dbo.foo ( name , gender , send_email )
  values ( @name , @gender , @send_email )

go

你应该能够说出神奇的话:

[编辑注意,您必须跳过视图箍以使可为空的 bool 与空值一起正常工作。一致性是小脑袋里的妖精。]

static int InsertFoo( string name , bool? gender , bool sendEmail )
{
  int rowcount ;

  using ( SqlConnection conn = new SqlConnection("your-connect-string-here"))
  using ( SqlCommand cmd = conn.CreateCommand() )
  {

    cmd.CommandText = @"dbo.InsertFoo"                       ;
    cmd.CommandType = CommandType.StoredProcedure            ;
    cmd.Parameters.AddWithValue( "@name"       , name      ) ;
    cmd.Parameters.AddWithValue( "@gender"     , gender.HasValue ? (object) gender : (object)DBNull.Value    ) ;
    cmd.Parameters.AddWithValue( "@send_email" , sendEmail ) ;

    conn.Open() ;
    rowcount = cmd.ExecuteNonQuery() ;
    conn.Close() ;

  }
  return rowcount ;
}

得到你想要的。这是一个测试用例:

int rc1 = InsertFoo( "john"    , null  , false ) ;
int rc2 = InsertFoo( "jane"    , null  , true  ) ;
int rc3 = InsertFoo( "sally"   , false , false ) ;
int rc4 = InsertFoo( "rebecca" , false , true  ) ;
int rc5 = InsertFoo( "emily"   , true  , false ) ;
int rc6 = InsertFoo( "zoe"     , true  , true  ) ;

哪个产生

id name    gender send_email
-- ------- ------ ----------
 1 john     NULL      0
 2 jane     NULL      1
 3 sally     0        0
 4 rebecca   0        1
 5 emily     1        0
 6 zoe       1        1

如你所料。

【讨论】:

  • 不错的方法谢谢,但我的问题是在 SP_ 前缀作为 marc_s 的评论
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2013-07-06
  • 1970-01-01
  • 1970-01-01
  • 2015-05-15
  • 1970-01-01
  • 2013-06-14
  • 2020-06-02
相关资源
最近更新 更多