我是C#的新手,并且编写了以下代码。阅读文档之后,我意识到我的代码应该容易受到SQL注入的攻击,因为我没有为参数使用参数(据我所知,您可以通过注入不需要的查询search.Text)。因为我实际上是将我的值锁定在“”引号内,所以我什至不必担心吗?
我在这里找到了一些指示,但无法使它起作用: 如何在sql语句中使用字符串变量
public void InvokeDataGridAddress()
{
switch (ComboBoxSelection.Text)
{
case "NASLOV":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [ADDRESS] LIKE '%" + search.Text + "%' COLLATE Latin1_general_CI_AI";
break;
case "LASTNIK":
comboBoxValue = "SELECT [cbu_naslovi].* FROM [cbu_deli], [cbu_naslovi] WHERE [cbu_deli].LASTNIK LIKE '%" + search.Text + "%' COLLATE Latin1_general_CI_AI AND [cbu_deli].IDX = [cbu_naslovi].ID";
break;
case "OBJEKT":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [SO] LIKE '%" + search.Text + "%'";
break;
case "PARCELA":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [P1] LIKE '%" + search.Text + "%' OR [P2] LIKE '%" + search.Text + "%' OR [P3] LIKE '%" + search.Text + "%' OR [P4] LIKE '%" + search.Text + "%' OR [P5] LIKE '%" + search.Text + "%' OR [P6] LIKE '%" + search.Text + "%' OR [P7] LIKE '%" + search.Text + "%' OR [P8] LIKE '%" + search.Text + "%' OR [P9] LIKE '%" + search.Text + "%' OR [P10] LIKE '%" + search.Text + "%' OR [P11] LIKE '%" + search.Text + "%' OR [P12] LIKE '%" + search.Text + "%' OR [P13] LIKE '%" + search.Text + "%' OR [P14] LIKE '%" + search.Text + "%' OR [P15] LIKE '%" + search.Text + "%' OR [P16] LIKE '%" + search.Text + "%' OR [P17] LIKE '%" + search.Text + "%'";
break;
}
comboBoxValue = comboBoxValue + " ORDER BY [ULICA] ASC, [OBMOCJE] ASC, LEN ([HS]) ASC, [HS] ASC, [HID] ASC";
SqlCommand cmd = new SqlCommand
{
CommandText = comboBoxValue,
Connection = con
};
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
SqlDataAdapter da = new SqlDataAdapter(cmd);
dtAddress.Clear();
da.Fill(dtAddress);
dg_address.ItemsSource = dtAddress.DefaultView;
Mouse.OverrideCursor = System.Windows.Input.Cursors.Arrow;
}
Run Code Online (Sandbox Code Playgroud)
编辑:工作解决方案使Olivier Belanger和MindSwipe成为可能。我还留下了有关如何使%参数使用 LIKE的参考:在SQL LIKE子句中使用SqlParameter不起作用
public void InvokeDataGridAddress()
{
switch (ComboBoxSelection.Text)
{
case "NASLOV":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [ADDRESS] LIKE @SearchText COLLATE Latin1_general_CI_AI";
break;
case "LASTNIK":
comboBoxValue = "SELECT [cbu_naslovi].* FROM [cbu_deli], [cbu_naslovi] WHERE [cbu_deli].LASTNIK LIKE @SearchText COLLATE Latin1_general_CI_AI AND [cbu_deli].IDX = [cbu_naslovi].ID";
break;
case "OBJEKT":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [SO] LIKE @SearchText";
break;
case "PARCELA":
comboBoxValue = "SELECT * FROM [cbu_naslovi] WHERE [P1] LIKE @SearchText OR [P2] LIKE @SearchText OR [P3] LIKE @SearchText OR [P4] LIKE @SearchText OR [P5] LIKE @SearchText OR [P6] LIKE @SearchText OR [P7] LIKE @SearchText OR [P8] LIKE @SearchText OR [P9] LIKE @SearchText OR [P10] LIKE @SearchText OR [P11] LIKE @SearchText OR [P12] LIKE @SearchText OR [P13] LIKE @SearchText OR [P14] LIKE @SearchText OR [P15] LIKE @SearchText OR [P16] LIKE @SearchText OR [P17] LIKE @SearchText";
break;
}
comboBoxValue = comboBoxValue + " ORDER BY [ULICA] ASC, [OBMOCJE] ASC, LEN ([HS]) ASC, [HS] ASC, [HID] ASC";
SqlCommand cmd = new SqlCommand
{
CommandText = comboBoxValue,
Connection = con
};
cmd.Parameters.AddWithValue("@SearchText", '%' + search.Text + '%');
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
SqlDataAdapter da = new SqlDataAdapter(cmd);
dtAddress.Clear();
da.Fill(dtAddress);
dg_address.ItemsSource = dtAddress.DefaultView;
Mouse.OverrideCursor = System.Windows.Input.Cursors.Arrow;
}
Run Code Online (Sandbox Code Playgroud)
简短的回答,是的,您始终需要担心SQL注入,您不会相信某些黑客如何利用这些知识。
尽管我对C#很有经验,但是我从未在C#中使用直接SQL,但是我一直将EF与LINQ一起用于数据库,
无论如何,这里是这样:
using (var con = new SqlClient.SqlConnection(conectionString))
using (var cmd = SqlClient.SqlCommand())
{
con.Open();
cmd.Connection = con;
cmd.CommandType = CommandType.Text;
cmd.CommandText = "SELECT * FROM [cbu_naslovi] WHERE [ADDRESS] LIKE '%@Title%' COLLATE Latin1_general_CI_AI";
cmd.Parameters.Add("@Title", search.Text);
}
Run Code Online (Sandbox Code Playgroud)
一些解释:
using: using关键字非常简单。基本上,您放在括号之间的任何内容(例如Class c = new Class();)都需要实现IDisposable,此变量将在Curly Braces
Syntatic Candy之后放置:通常using()需要大括号{}后跟,除非它是单个语句或另一个使用语句
Sql Stuff: con.Open打开与数据库的连接,并将其设置为我们的命令将使用的Connection cmd.Connection = con。
现在我们需要说说它是什么类型的命令。通过这样做,cmd.CommandType = CommandType.Text我们告诉命令它是一个SQL查询。
现在,我们需要实际定义查询,而不是将字符串作为占位符进行压缩。+我们@SomeName
最后,我们代替我们@SomeName做我们的实际值cmd.Parameters.Add("@SomeName", value),其中@SomeName可以是任何东西,但它必须是相同的,因为我们要在SQL查询来替换占位符
,这是我们真正保护自己免受SQL注入攻击,因为cmd.Parameters.Add()确实我们需要的一切否则将需要手动执行
希望这会有所帮助并且不会让您感到困惑
注意:如果您对Entity Framework(EF)或LINQ感兴趣,那么这里是一个很好的来源:EF Database First教程