2010-10-21 67 views
2

我有一個更新變量列的簡單查詢。後來這個查詢string.Formatted並傳遞到的SqlCommand(C#)(TABLEID是SomeTable列):是否有可能更新存儲過程中的變量字段?

"UPDATE SomeTable set {0}[email protected] where [email protected]" 

我需要將此查詢轉換爲一個存儲過程。它有可能嗎?

+1

「的SqlCommand」的使用意味着SQL服務器 – 2010-10-21 19:05:43

+0

是'TableId'在表或SYS列引用該對象? – Brad 2010-10-21 19:06:15

+0

它是SQL和TableId是SomeTable中的列(剛編輯問題) – kateroh 2010-10-21 19:08:49

回答

6

它只能通過動態SQL存儲過程完成(如布拉德alreayd回答,當然你會使用QUOTENAME(@columnName)正常防止SQL注入,並使用sysname參數類型)。如果你沿着這條路走下去,我建議你先閱讀The Curse and Blessings of Dynamic SQL

更新時間:

我不得不張貼代碼,因爲布拉德的代碼剛剛太多的錯誤。

create procedure myCustomUpdate 
    @columnName sysname, 
    @value sql_variant, 
    @id int 
AS 
declare @sql NVARCHAR(max); 
set @sql = N'UPDATE SomeTable SET ' + QUOTENAME(@columnName) 
    + N' = @value WHERE TableId = @id'; 
exec sp_executesql @sql, N'@value sql_variant, @id int', @value, @id; 
+2

+1 - 他們真的應該只是編碼到StackOverflow中,只要輸入「動態SQL」,就會自動鏈接到該文章的超鏈接... – JNK 2010-10-21 19:13:47

+0

感謝您的改進Remuss。我想這是毫無疑問,你有56K代表,我還沒有達到2K :)我同意你應該防止注射,但你真的*使用報價周圍的列名? – Brad 2010-10-21 19:20:11

+0

如果這些數據中的任何一個沒有實際硬編碼,那麼您應該......我不得不說,我對這一點很好奇。使用基本上運行完全由其參數定義的查詢的存儲過程有什麼目的?爲什麼不完全跳過SP並在代碼中編寫整個查詢? – 2010-10-21 19:31:25

4

我對你正在做什麼做了一些假設,但評估這段代碼。

CREATE PROCEDURE UpdateTableValue 
    (
    @tableId INT 
    ,@columnName sql_variant 
    ,@value VARCHAR(10) 
    ) 
AS 
    BEGIN 

     DECLARE @sql NVARCHAR(MAX) 
     SET @sql = N'UPDATE SomeTable ' 
        + N'SET ' + QUOTENAME(@columnName) + N' = = @value ' 
        + N'WHERE TableId = @tableId' 

    EXEC sp_executesql @sql 
      , N'@value sql_variant, @tableId int' 
      , @value, @tableId; 

    END 
1

我認爲在Remus提到的文章中有一個更好的解決方案:The Curse and Blessings of Dynamic SQL 。我結束了使用CASE切換的文章中,以優化性能(動態SQL未被緩存),如:

UPDATE tbl 
SET col1 = CASE @colname WHEN 'col1' THEN @value ELSE col1 END, 
     col2 = CASE @colname WHEN 'col2' THEN @value ELSE col2 END, 
相關問題