2011-01-12 11 views
2

Ich habe eine gespeicherte Prozedur, die den Namen einer Tabelle als Parameter übernimmt und dynamisches SQL verwendet, um die Auswahl durchzuführen. Ich habe versucht, @TableName als Parameter übergeben und sp_executesql verwenden, aber das hat einen Fehler ausgelöst. Ich entschied mich, mit dynamischem sql ohne sp_executesql zu gehen.Wie sichere dynamische SQL gespeicherte Prozedur?

Gibt es noch etwas, was ich tun sollte, um den Parameter @TableName zu sichern, um SQL-Injection-Angriffe zu vermeiden?

Stored Procedure unter:

CREATE PROCEDURE dbo.SP_GetRecords 
    ( 
    @TableName VARCHAR(128) = NULL 
    ) 
AS 
BEGIN 

    /* Secure the @TableName Parameter */   
    SET @TableName = REPLACE(@TableName, ' ','')  
    SET @TableName = REPLACE(@TableName, ';','')  
    SET @TableName = REPLACE(@TableName, '''','') 

    DECLARE @query NVARCHAR(MAX)  

    /* Validation */  
    IF @TableName IS NULL 
    BEGIN  
     RETURN -1 
    END 

    SET @query = 'SELECT * FROM ' + @TableName 
    EXEC(@query)   
END 

Dies schlug fehl, wenn sp_executesql anstelle:

SET @query = 'SELECT * FROM @TableName' 
EXEC sp_executesql @query, N'@TableName VARCHAR(128)', @TableName 

ERROR: Must declare the table variable "@TableName".

+1

Unabhängig davon, welche Lösung Sie sich entscheiden, sich bewusst sein, dass, wenn Sie dynamische SQL in einer gespeicherten Prozedur ausführen, dass SQL standardmäßig mit den Berechtigungen des gespeicherten proc * Anrufers *. Während normales SQL in einer gespeicherten Prozedur standardmäßig mit den Berechtigungen des gespeicherten proc * owner * ausgeführt wird. – RoadWarrior

Antwort

2

Sie natürlich auf der Sysobjects Tabelle schauen und sicherstellen, dass es existiert

Select id from sysobjects where xType = 'U' and [name] = @TableName 

Weitere (Vollständigeres Beispiel):

DECLARE @TableName nVarChar(255) 
DECLARE @Query nVarChar(512) 

SET @TableName = 'YourTable' 
SET @Query = 'Select * from ' + @TableName 

-- Check if @TableName is valid 
IF NOT (Select id from sysobjects where xType = 'U' and [name] = @TableName) IS NULL 
    exec(@Query) 
+0

Wäre die unsichere Zeichenfolge in der Abfrage nicht enthalten, um die Existenz der Tabellen zu überprüfen? –

+4

@jms, aber hier können Sie Bindeparameter verwenden –

+0

@Markus zugestimmt. –

Verwandte Themen