Sql-Server
exec(sql) 的安全替代方案
我發現了一些
exec(sql)
隱藏在程式碼中的語句。它們存在是有充分理由的,因為這些語句不能直接編寫,但它們是明顯的攻擊媒介。有安全的替代方案
exec(some sql)
嗎?可以正確參數化的東西,包括語句中的表名?
對於某些類型的參數化,是否使用
EXEC()
or並不重要sp_executesql
,因為有些東西無論如何都無法參數化。例如,您在評論中表示(請更新您的問題以更具體地說明您的要求!)您正在參數化表名,但這些不能參數化,因為它們需要按字面意思表達給 SQL Server(它不能標記它並在執行時交換)。為了保護自己免受表名漏洞的影響,您可以像這樣輕鬆保護自己:
DECLARE @tablename sysname; -- pretend this is a parameter SET @tablename = N'this_is_not_a_table'; -- in procedure body: IF NOT EXISTS (SELECT 1 FROM sys.tables WHERE name = @tablename) BEGIN RAISERROR(N'Table does not exist.', 1, 11); RETURN; END SET @sql = N'SELECT ... FROM dbo.' + QUOTENAME(@tablename) + ...; -- EXEC(@sql) or EXEC sys.sp_executesql @sql
現在,我更喜歡使用
sp_executesql
always,部分原因是它促進使用強類型參數(避免 SQL 注入問題以及雙單引號問題),還因為在某些情況下,您將同時為可參數化和不可參數化的值傳遞參數(是的,我編造了這些話)。更多資訊:現在您唯一需要擔心的是是否有人能夠創建表並可以創建一個名為的表
sys.objects; DROP TABLE foo; --
- 但是如果您有一個您不信任但能夠在您的數據庫中創建表的人……