參數化查詢
-
使用參數化查詢的情景有很多,但最常用的情景是需要用戶在查詢中進行輸入的情況。
有兩種方法可供使用。第一,可以講用戶輸入嵌入到查詢字符串中,例如可能使用.NET Framework中的String.Format函數。
第二種方法是構造一種參數化查詢。
在開始時執行如下所示的基本查詢:
1 select count(*) from UserInfo 2
3
4 where UserName=‘{0}’ and PassWord=‘{1}’
然后利用用戶的輸入構造如下查詢:
1 select count(*) from UserInfo 2 3 4 where UserName=‘myUserName’ and PassWord=‘myPassWord’’
如果對正在執行的查詢有一些了解,輸入如下內容:NonUser' or 1=1 --,那么代碼就會執行如下查詢。
1 select count(*) from UserInfo 2 3 4 where UserName=‘NonUser' or 1=1 --" and PassWord=‘myPassWord’’
雙連字符在SQL Server的查詢語法中特別重要。它表示:該行后面的內容是注釋。換句話說,and PassWord=‘myPassWord’被忽略了。
現在,UserName=‘NonUser'並不成立,但where子句的另一半(1=1)對於所有行均成立。因此,該查詢將成功執行。
-
使用參數化查詢。
代碼示例:
1 SqlConnectionStringBuilder connstr = new SqlConnectionStringBuilder(); 2
3 connstr.DataSource = "ZHANG-PC"; 4
5 connstr.InitialCatalog = "sq"; 6
7 connstr.IntegratedSecurity = true; 8
9 using (SqlConnection conn = new SqlConnection(connstr.ConnectionString)) 10 { 11
12 conn.Open(); 13
14 SqlCommand cmd = new SqlCommand(); 15
16 cmd.CommandText = "select count(*) from UserInfo where UserName=@username and PassWord=@password"; 17
18 cmd.Parameters.AddWithValue("@username","zyb12345"); 19
20 cmd.Parameters.AddWithValue("@password","654321"); 21
22 cmd.Connection = conn; 23
24 SqlDataReader read = cmd.ExecuteReader(); 25
26 while (read.Read()) 27 { 28
29 Console.WriteLine("userName:{0}", read.GetString(0)); 30
31 } 32
33 conn.Close(); 34
35 }
在ADO.NET中執行一個參數化查詢,需要向Command對象的Parameters集合中添加Parameters對象。生成Parameters最簡單的方法是:
調用SqlCommand對象的Parameters集合的AddWithValue函數。
1 SqlCommand的Parameters集合中的AddWithValue方法。 2 3 cmd.Parameters.AddWithValue("@username","zyb12345"); 4 5 cmd.Parameters.AddWithValue("@password","654321");
或者
1 SqlParameter[] p = new SqlParameter[2]; 2
3 p[0].ParameterName = "@username"; 4
5 p[0].Value = "zyb12345"; 6
7 p[1].ParameterName = "@password"; 8
9 p[1].Value = "654321"; 10
11 cmd.Parameters.AddRange(p); 12
13 SqlDataReader read = cmd.ExecuteReader();
-
參數數據類型
可以設置SqlParameters對象的SqlDbType屬性,以控制在向SQL Server數據庫中傳遞參數信息時所使用的數據類型,即SqlDbType枚舉中的值。
SqlDbType的枚舉值有:Int,DateTime,Bit,Money,Image,NVarChar等,在下面的示例中,NVarChar對應的是.NET中的string類型。size(即15)代表字符串的長度,可根據需要設置size的值。
1 SqlParameter p;
2 p = new qlParameter("@username",SqlDbType.NVarChar,15);
3 p.Value = "zyb12345";
-
參數方向
在本例中Sqlparameters是輸入參數,有時需要輸出參數,這時就要設置SqlParameter的參數方向了。此時不需要設置Value屬性。代碼如下:
1 SqlParameter w; 2 3 w = cmd.Parameters.Add("@username", SqlDbType.NVarChar); 4 5 w.Direction = ParameterDirection.Output; //設置參數方向 6 7 cmd.ExecuteNonQuery(); //執行語句 8 9 Console.Write(w.Value); //獲取輸出值(執行完數據查詢后才能獲取Value值)