2008-09-18 2 views
2

У меня есть хранимая процедура в моей базе данных, которая выглядит следующим образомВставка строки формы «guid1, guid2, GUID3 ...» в операторе IN в TSQL

ALTER PROCEDURE [dbo].[GetCountingAnalysisResults] 
    @RespondentFilters varchar 
AS 
BEGIN 

@RespondentFilters = '''8ec94bed-fed6-4627-8d45-21619331d82a, 114c61f2-8935-4755-b4e9-4a598a51cc7f''' 

DECLARE @SQL nvarchar(600) 

SET @SQL = 
    'SELECT * 
    FROM Answer 
    WHERE Answer.RespondentId IN ('[email protected]+''')) 
    GROUP BY ChosenOptionId' 

exec sp_executesql @SQL 

END 

Он компилирует и выполняет , но почему-то это не дает мне хороших результатов, точно так же, как заявление IN не работает. Пожалуйста, если кто-нибудь знает решение этой проблемы, помогите мне.

+0

Как в стороне, вы всегда можете использовать print @SQL, чтобы посмотреть, что выглядит statemtent SQL например, когда он выполняется. Y0ou может найти что-то там. – Craig 2008-09-18 15:41:29

ответ

1

Похоже, что вы не закрывающие кавычки вокруг ваших @RespondentFilters

'8ec94bed-fed6-4627-8d45-21619331d82a, 114c61f2-8935-4755-b4e9-4a598a51cc7f'

Поскольку идентификаторы GUID сделать строку сравнения, это не будет работать.

Лучше всего использовать код для разбивки списка на несколько значений.

Что-то вроде этого:


-- This would be the input parameter of the stored procedure, if you want to do it that way, or a UDF 
declare @string varchar(500) 
set @string = 'ABC,DEF,GHIJK,LMNOPQRS,T,UV,WXY,Z' 


declare @pos int 
declare @piece varchar(500) 

-- Need to tack a delimiter onto the end of the input string if one doesn't exist 
if right(rtrim(@string),1) ',' 
set @string = @string + ',' 

set @pos = patindex('%,%' , @string) 
while @pos 0 
begin 
set @piece = left(@string, @pos - 1) 

-- You have a piece of data, so insert it, print it, do whatever you want to with it. 
print cast(@piece as varchar(500)) 

set @string = stuff(@string, 1, @pos, '') 
set @pos = patindex('%,%' , @string) 
end 

Код украдена из Raymond Lewallen

1

Я думаю, что вам нужно кавычки внутри строки тоже. Попробуйте:

@RespondentFilters = '''8ec94bed-fed6-4627-8d45-21619331d82a'',''114c61f2-8935-4755-b4e9-4a598a51cc7f''' 

Вы также можете рассмотреть разбор @RespondentFilters во временную таблицу.

2

Вы нужны одиночные кавычки каждого GUID в списке

@RespondentFilters = '''8ec94bed-fed6-4627-8d45-21619331d82a'', ''114c61f2-8935-4755-b4e9-4a598a51cc7f''' 
3

Вы должны обязательно посмотреть на расщеплении список GUIDs в таблицу и присоединение к этой таблице. Вы должны быть в состоянии найти множество примеров онлайн для функции с таблицей, которая разбивает входную строку на таблицу.

В противном случае ваша хранимая процедура уязвима для SQL-инъекции. Рассмотрим следующее значение для @RespondentFilters:

@RespondentFilters = '''''); SELECT * FROM User; /*' 

Ваш запрос будет более безопасным синтаксический (т.е. проверки) значения параметров и присоединения:

SELECT * 
FROM Answer 
WHERE Answer.RespondentId IN (SELECT [Item] FROM dbo.ParseList(@RespondentFilters)) 
GROUP BY ChosenOptionId 

или

SELECT * 
FROM Answer 
INNER JOIN dbo.ParseList(@RespondentFilters) Filter ON Filter.Item = Answer.RespondentId 
GROUP BY ChosenOptionId 

Это немного больше, так как вы не имеете дело с динамическим SQL (sp_executesql будет кэшировать планы запросов, но я не уверен, будет ли он точно идентифицировать ваш запрос как с параметризованным запросом, поскольку он имеет переменный список элементов в предложении IN).

0

Танк для всех вас. Они все очень помогли. Я столкнулся с проблемой, написав функцию split, и она отлично работает. Это из-за того, что я мог бы сделать, но вы знаете, крайний срок скрывается за углом :)

 Смежные вопросы

  • Нет связанных вопросов^_^