2008-09-30 3 views
3

Мы пытаемся обновить нашу классическую поисковую систему asp, чтобы защитить ее от SQL-инъекции. У нас есть функция VB 6, которая строит запрос динамически, объединяя запрос вместе на основе различных параметров поиска. Мы преобразовали это в хранимую процедуру, используя динамический sql для всех параметров, за исключением ключевых слов.Динамический SQL-запрос поиска - переменная Количество ключевых слов

Проблема с ключевыми словами заключается в том, что существуют слова с переменным числом, предоставленные пользователем, и мы хотим найти несколько столбцов для каждого ключевого слова. Поскольку мы не можем создать отдельный параметр для каждого ключевого слова, как мы можем создать безопасный запрос?

Пример:

@CustomerId AS INT 
@Keywords AS NVARCHAR(MAX) 

@sql = 'SELECT event_name FROM calendar WHERE customer_id = @CustomerId ' 

--(loop through each keyword passed in and concatenate) 

@sql = @sql + 'AND (event_name LIKE ''%' + @Keywords + '%'' OR event_details LIKE ''%' + @Keywords + '%'')' 

EXEC sp_executesql @sql N'@CustomerId INT, @CustomerId = @CustomerId 

Что такое лучший способ справиться с этим и поддержание защиты от SQL инъекций?

ответ

3

Возможно, вам не нравится это слышать, но вам может быть лучше вернуться к динамическому построению вашего SQL-запроса в коде перед выпуском базы данных. Если вы используете помещики параметров в строке SQL, вы получаете защиту от атак SQL-инъекций.

Пример:

string sql = "SELECT Name, Title FROM Staff WHERE [email protected]"; 
using (SqlCommand cmd = new SqlCommand(sql)) 
{ 
    cmd.Parameters.Add("@UserId", SqlType.VarChar).Value = "smithj"; 

Вы можете создать строку SQL в зависимости от набора столбцов, которые необходимо запросить, а затем добавить значения параметров после того, как строка будет завершена. Это немного больно, но я думаю, что это намного проще, чем действительно сложный TSQL, который лишает много возможных перестановок возможных входов.

+0

+1 этот подход позволит избежать убегающую проблему полностью – 2008-09-30 22:36:10

1

У вас есть 3 варианта здесь.

  1. Используйте function that converts lists tables и присоединитесь к нему. Так что у вас будет что-то вроде этого.

    SELECT * 
    FROM calendar c 
        JOIN dbo.fnListToTable(@Keywords) k 
         ON c.keyword = k.keyword 
    
  2. имеет фиксированный набор Params, и только позволяет максимум N ключевых слов для поиска на

    CREATE PROC spTest 
    @Keyword1 varchar(100), 
    @Keyword2 varchar(100), 
    .... 
    
  3. Написать ускользающую функцию строки в TSQL и избежать ключевых слов.

0
  • Если вам это нужно, вы можете просто вырезать любой символ, который не в [A-Za-Z] - большинство из этих вещей не будет в поиске, и вы не должны быть в состоянии таким образом, и вам не нужно беспокоиться о ключевых словах или что-то в этом роде. Однако, если вы разрешаете кавычки, вам нужно быть более осторожным.

  • Подобно sambo99 # 1, вы можете вставить ключевые слова во временную таблицу или табличную переменную и присоединиться к нему (даже с использованием подстановочных знаков) без опасности инъекций:

Это не очень динамичный :

SELECT DISTINCT event_name 
FROM calendar 
INNER JOIN #keywords 
    ON event_name LIKE '%' + #keywords.keyword + '%' 
    OR event_description LIKE '%' + #keywords.keyword + '%' 
  • Вы можете фактически генерировать SP с большим количеством параметров вместо кодирования его вручную (устанавливается по умолчанию в «» или NULL в зависимости от ваших предпочтений в кодирование ваших поисков).Если вы обнаружили, что вам нужны дополнительные параметры, было бы просто увеличить количество сгенерированных параметров.

  • Вы можете переместить поиск в полнотекстовый индекс за пределами базы данных, например Lucene, а затем использовать результаты Lucene, чтобы вытащить соответствующие строки базы данных.

0

Вы можете попробовать это:

SELECT * FROM [tablename] WHERE LIKE % +keyword% 
Смежные вопросы