2013-06-26 2 views
0

Мне нужно выполнить длинную динамическую строку запроса на основе переменной xml, тогда мне нужно было разделить строку на несколько переменных varchar, каждая из которых содержит часть обновления в таблицу внутри курсора.Выполнение нескольких строк запроса с использованием объявленной сначала переменной

Я вывешу часть запроса:

DECLARE @QUERY1 VARCHAR(8000); 
DECLARE @QUERY2 VARCHAR(8000); 
DECLARE @QUERY3 VARCHAR(8000); 
DECLARE @QUERY4 VARCHAR(8000); 

DECLARE @cols AS VARCHAR(8000); 

DECLARE @begin INT 
DECLARE @totalid INT 
DECLARE @groupsize INT 
SET @groupsize = 0 
SELECT @totalid = MAX(IntegrationId) FROM Integration 
set @QUERY1 = N' 
BEGIN TRANSACTION 
DECLARE @xml XML 
DECLARE @XMLReceiverID int 
DECLARE XMLRowItem CURSOR FOR 
SELECT XMLReceiverID,XMLContent FROM XMLReceiver WHERE FlagImportData = 0 and Typology = ''XXXX'' 
OPEN XMLRowItem 
FETCH XMLRowItem INTO @XMLReceiverID,@xml 
WHILE @@Fetch_Status = 0 

BEGIN 
'; 
set @QUERY2 = N' 
INSERT INTO IntegrationData (XmlReceiverID) 
'; 
set @QUERY3 = N' 
SELECT @XMLReceiverID 
';  
--PRINT @QUERY1 + @QUERY2 + @QUERY3 
EXEC (@QUERY1 + @QUERY2 + @QUERY3)  
WHILE @groupsize <= @totalid 
BEGIN 
SET @begin = @groupsize 
SET @groupsize = @groupsize + 10 
select @cols = 
(select STUFF((SELECT distinct ',', QUOTENAME(FieldName), ' = ' , CASE WHEN XMLPath IS NULL THEN 'NULL' ELSE '(SELECT TOP 1 c.value(''(' + (REVERSE(LEFT(REVERSE(XMLPath), CHARINDEX('/', REVERSE(XMLPath)) - 1))) + ')[1]'',''VARCHAR(50)'') FROM @xml.nodes(''' + REPLACE(XMLPath,'/' + REVERSE(LEFT(REVERSE(XMLPath), CHARINDEX('/', REVERSE(XMLPath)) - 1)), '') + ''') t(c)) ' END 
from IntegracaoOpcaoLayout 
where FlagIntegration = 1 
AND XMLPath IS NOT NULL 
AND IntegrationId > @begin 
AND IntegrationId <= @groupsize 
order by QUOTENAME(FieldName) asc 

FOR XML PATH(''), TYPE 
).value('.', 'NVARCHAR(MAX)') ,1,1,'')) 

set @QUERY2 = N' 
UPDATE IntegrationData SET ' + @cols + ' WHERE XmlReceiverID = @XMLReceiverID 
'; 
EXEC (@QUERY2) 
--PRINT @QUERY2 
END 
set @QUERY4 = N'  
UPDATE XMLReceiver SET FlagIntegration = 1 WHERE XMLReceiverID = @XMLReceiverID AND FlagImportData = 0 
FETCH NEXT FROM XMLRowItem into @XMLReceiverID,@xml 
END 
PRINT @XMLReceiverID 
CLOSE XMLRowItem 

DEALLOCATE XMLRowItem 
COMMIT TRANSACTION 
'; 
EXEC (@QUERY4) 
--PRINT @QUERY4 

Если я запускаю этот код печатает строки запроса и выполнить все это прекрасно работает!

Но если я бегу нормально, я получаю сильфон ошибки (о, ни объявить переменную, объявленную в первом ехес заявлении):

Msg 102, Level 15, State 1, Line 15 
Incorrect syntax near '@XMLReceiverID'. 
Msg 137, Level 15, State 2, Line 2 
Must declare the scalar variable "@xml". 

ли кто-либо работу вокруг или предложение?

Вот запрос напечатал:

BEGIN TRANSACTION 
DECLARE @xml XML 
DECLARE @XMLReceiverID int 
DECLARE XMLRowItem CURSOR FOR 
SELECT XMLReceiverID,XMLContent FROM XMLReceiver WHERE FlagImportData = 0 and Typology = 'XXXX' 
OPEN XMLRowItem 
FETCH XMLRowItem INTO @XMLReceiverID,@xml 
WHILE @@Fetch_Status = 0 

BEGIN 

INSERT INTO IntegrationData (XmlReceiverID) 

SELECT @XMLReceiverID 

UPDATE IntegrationData SET [Field1] = (SELECT TOP 1 c.value('(test1)[1]','VARCHAR(50)') FROM @xml.nodes('/xmlPath/test1') t(c)) , 
[Field2] = (SELECT TOP 1 c.value('(test2)[1]','VARCHAR(50)') FROM @xml.nodes('/xmlPath/test2') t(c)) , 
[Field3] = (SELECT TOP 1 c.value('(test3)[1]','VARCHAR(50)') FROM @xml.nodes('/xmlPath/test3') t(c)) 
UPDATE XMLReceiver SET FlagImportData = 1 WHERE XMLReceiverID = @XMLReceiverID AND FlagImportData = 0 
FETCH NEXT FROM XMLRowItem into @XMLReceiverID,@xml 
END 
PRINT @XMLReceiverID 
CLOSE XMLRowItem 

DEALLOCATE XMLRowItem 
COMMIT 
+0

Какой выход, который вы получаете от печати? –

+0

i posted @ bastos.sergio – raddesso

+0

Пожалуйста, напишите таблицу DDL, данные образца и ожидаемые результаты, иначе мы можем только догадываться, что вам действительно нужно. Если вы действительно чувствуете, что ваша проблема может быть решена только с помощью dynamc T-SQL, пожалуйста, прочитайте следующую статью на эту тему, написанную Эрландом Соммарскогом: http://www.sommarskog.se/dynamic_sql.html ML –

ответ

1

Причина код бросает ошибки, потому что весь код выходит за рамки.

Это ваша проблема.

set @QUERY2 = N' 
    UPDATE IntegrationData SET ' + @cols + ' WHERE XmlReceiverID = @XMLReceiverID 
    '; 
    EXEC (@QUERY2) 
    --PRINT @QUERY2 
    END 
    set @QUERY4 = N'  
    UPDATE XMLReceiver SET FlagIntegration = 1 WHERE XMLReceiverID = @XMLReceiverID AND FlagImportData = 0 
    FETCH NEXT FROM XMLRowItem into @XMLReceiverID,@xml 
    END 
    PRINT @XMLReceiverID 
    CLOSE XMLRowItem 

    DEALLOCATE XMLRowItem 
    COMMIT TRANSACTION 
    '; 

Вы можете видеть, что вы переназначить @ Query2 с утверждением, что требует @XMLReceiverID, но переменная не была объявлена ​​для нового назначения @ QUERY2. То же самое справедливо для @query 4. Две переменные @ XML, @ XMLReceiverId не входят в ту же область, что и @ Query1.

По сути, вам нужно объединить все утверждения в одну переменную или объединить их в один кадр.

+0

Проблема я не могу объединить все из-за максимального размера переменной. Запрос будет длиннее 8000. Мне потребуется некоторое время для выполнения нескольких обновлений, потому что полное обновление длиннее 8000 – raddesso

+0

Вы не можете изменить переменную на varchar (max)? –

+0

Какую версию SQL Server вы используете? Можете ли вы использовать VARCHAR (MAX) (SQL 2005+) вместо этого? –