ADO.NET笔记——调用存储过程

相关知识:

  1. 在ADO.NET访问SQL Server时,鼓励使用存储过程取代常规的SQL语句。
  2. 存储过程有下列优点:
    • 存储过程中的SQL语句将会经过预先的解析和编译,然后存放在数据库服务器上行。调用的时候不必在此解析语法和编译,因此效率比采用常规SQL语句高
    • 带参数的存储过程在一定程度上可以降低SQL注入攻击的风险
    • 存储过程便于在数据库服务器上统一管理,减少了程序员维护SQL代码的工作量
    • 存储过程有利于重用某些数据库的访问逻辑

 

代码示例:

  1. 在数据库中创建存储过程沿用SQLInjection案例描述的数据库。请确保Account表中有若干行数据

    • 不带参数的存储过程:forAccountGetAll
          CREATE PROCEDURE forAccountGetAll
          AS
          SELECT AccountID, AccountName, Password FROM Account
    • 带输入参数的存储过程:forAccountInsert
          CREATE PROCEDURE forAccountInsert
          (@AccountID int,
           @AccountName nvarchar(50),
           @Password nvarchar(50)
           )AS
           INSERT INTO Account(AccountID, AccountName, password) VALUES(@AccountID, @AccountName, @password)
    • 带输入和输出从参数的存储过程:根据用户名和密码,找到匹配的AccountID作为输出参数:forAccountLogin
           CREATE PROCEDURE forAccountLogin
           (@AccountName nvarchar(50),
            @Password nvarchar(50),
            @AccountID int output
            )AS
            SELECT @AccountID=AccountID FROM Account WHERE AccountName=@AccountName AND password=@password
  2. 代码
     1 using System;
     2 using System.Collections.Generic;
     3 using System.Linq;
     4 using System.Text;
     5 using System.Threading.Tasks;
     6 using System.Data;
     7 using System.Data.SqlClient;
     8 
     9 namespace ConsoleApplication12
    10 {
    11     class Program
    12     {
    13         static string strConn = @"server=Joe-PC;database=AccountDBforSQLInjection;uid=sa;pwd=root";
    14         static SqlConnection conn = new SqlConnection(strConn);
    15         static void Main(string[] args)
    16         {
    17             //调用不带参数的存储过程
    18             //CallProcedureGetAll();    
    19             //调用带输入参数的存储过程
    20             //CallProcedureInsert();
    21             //调用带输入和输出参数的存储过程
    22             //CallProcedureLogin();
    23         }
    24 
    25         static void CallProcedureGetAll()
    26         {
    27             string sql = "forAccountGetAll";//存储过程名字
    28 
    29             SqlDataAdapter da = new SqlDataAdapter(sql, conn);
    30             da.SelectCommand.CommandType = CommandType.StoredProcedure;//指定调用存储过程(默认是SQL文本)
    31             
    32             DataSet ds = new DataSet();
    33             da.Fill(ds, "AccountGetAll");
    34 
    35             DataTable dt = ds.Tables["AccountGetAll"];
    36             DataView dv = new DataView(dt);
    37 
    38             dv.Sort = "AccountID ASC";
    39 
    40             Console.WriteLine("调用存储过程 forAccountGetAll:");
    41 
    42             foreach (DataRowView drv in dv)
    43             {
    44                 Console.WriteLine("{0}:{1},{2}", drv["AccountID"], drv["AccountName"], drv["password"]);
    45             }
    46         }
    47         
    48         static void CallProcedureInsert()
    49         {
    50             string sql = "forAccountInsert";
    51             SqlCommand cmd = new SqlCommand(sql, conn);
    52 
    53             cmd.CommandType = CommandType.StoredProcedure;
    54             //设置参数值,并添加到Command对象的参数集合中
    55             cmd.Parameters.AddWithValue("@AccountID", 100);
    56             cmd.Parameters.AddWithValue("@AccountName", "new");
    57             cmd.Parameters.AddWithValue("@password", "123456");
    58 
    59             conn.Open();
    60             cmd.ExecuteNonQuery();
    61             conn.Close();
    62         }
    63 
    64         static void CallProcedureLogin()
    65         {
    66             string sql = "forAccountLogin";
    67             SqlCommand cmd = new SqlCommand(sql, conn);
    68 
    69             cmd.CommandType = CommandType.StoredProcedure;
    70             //设置输入参数值
    71             cmd.Parameters.AddWithValue("@AccountName", "Joe");
    72             cmd.Parameters.AddWithValue("@password", "123456");
    73             //准备输出参数
    74             SqlParameter param = new SqlParameter("@AccountID", SqlDbType.Int);
    75             param.Direction = ParameterDirection.Output;//指定是输出参数
    76 
    77             cmd.Parameters.Add(param); // 将输出参数添加到Command对象的参数集合中
    78 
    79             conn.Open();
    80             cmd.ExecuteNonQuery();
    81             //如果没有满足条件的用户名和密码,那么输出参数@AccountID的值将为DBNull.Value
    82             if (param.Value == DBNull.Value)
    83             {
    84                 Console.WriteLine("failed");
    85             }
    86             else
    87             {
    88                 Console.WriteLine("Done");
    89             }
    90             conn.Close();
    91         }
    92     }
    93 }

     

 

posted @ 2015-03-21 01:28  .Joe.Chen  阅读(315)  评论(0编辑  收藏  举报