Sqlserver
 sql >> Baza danych >  >> RDS >> Sqlserver

Jak wyczyścić (zapobiec wstrzyknięciu SQL) dynamiczny SQL w SQL Server?

Uważam, że istnieją trzy różne przypadki, o które musisz się martwić:

  • strings (wszystko, co wymaga cudzysłowów):'''' + replace(@string, '''', '''''') + ''''
  • nazwy (wszystko, gdzie cudzysłowy nie są dozwolone):quotename(@string)
  • rzeczy, których nie można zacytować:wymaga to umieszczenia na białej liście

Uwaga :Wszystko w zmiennej łańcuchowej (char , varchar , nchar , nvarchar itp.), które pochodzą ze źródeł kontrolowanych przez użytkownika, muszą korzystać z jednej z powyższych metod. Oznacza to, że nawet rzeczy, które mają być liczbami, są cytowane, jeśli są przechowywane w zmiennych łańcuchowych.

Więcej informacji znajdziesz w Microsoft Magazine (Przestarzały link:2016-10-19) .

Oto przykład wykorzystujący wszystkie trzy metody:

EXEC 'SELECT * FROM Employee WHERE Salary > ''' +
     REPLACE(@salary, '''', '''''') +   -- replacing quotes even for numeric data
     ''' ORDER BY ' + QUOTENAME(@sort_col) + ' ' +  -- quoting a name
     CASE @sort_dir WHEN 'DESC' THEN 'DESC' END     -- whitelisting

Zwróć też uwagę, że wykonując wszystkie operacje na ciągach znaków w pliku EXEC oświadczenie, że nie ma problemu z obcięciem. Jeśli przypiszesz wyniki pośrednie do zmiennych, musisz upewnij się, że zmienne są wystarczająco duże, aby pomieścić wyniki. Jeśli zrobisz SET @result = QUOTENAME(@name) powinieneś zdefiniować @result mieć co najmniej 258 (2 * 128 + 2) znaków. Jeśli wykonasz SET @result = REPLACE(@str, '''', '''''') powinieneś zdefiniować @result być dwukrotnie większy od @str (przyjmij każdy znak w @str może być cytat). I oczywiście zmienna łańcuchowa zawierająca końcową instrukcję SQL musi być wystarczająco duża, aby pomieścić cały statyczny kod SQL oraz wszystkie zmienne wynikowe.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Dlaczego SQL Server automatycznie ignoruje puste miejsce na końcu?

  2. Przegląd typów złączeń SQL wraz z przykładami

  3. Domyślna kolejność wierszy w zapytaniu SELECT — SQL Server 2008 vs SQL 2012

  4. Jak uzyskać listę podstawowych ograniczeń klucza ze wszystkich baz danych w instancji SQL Server — SQL Server / TSQL Tutorial, część 60

  5. Jak COUNT_BIG() działa w SQL Server