Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Microsoft SQL Server Новый топик    Ответить
 добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
Добрый день!

Вопрос: каким образом добавить данные переменной типа xml в другую переменную типа xml?

Набросал скрипт:

use AdventureWorks

declare @xml1 xml, @xml2 xml

set @xml1 =
(select top 2 ContactID, FirstName, LastName
from Person.Contact
for xml raw('Contact'), root('DataInfo'), elements)

set @xml2 =
(select top 2 AddressID, PostalCode
from Person.Address
for xml raw('Address'), root('DataInfo'), elements)
-- так работает ...
set @xml1.modify(
'insert (<comment> 8745684 </comment>) after (DataInfo/Contact)[2]')

select @xml1

-- так не работает ... что я делаю не правильно?
set @xml1.modify(
'insert @xml2 after (DataInfo/Contact)[2]')

в этом случае выдается сообщение:
Msg 2390, Level 16, State 1, Line 17
XQuery [modify()]: Top-level attribute nodes are not supported

select @xml1

Помогите пожалуйста разобраться.
1 ноя 08, 17:36    [6388953]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
efdm
Member

Откуда: Москва
Сообщений: 310
sql-dsk

-- так не работает ... что я делаю не правильно?
set @xml1.modify(
'insert @xml2 after (DataInfo/Contact)[2]')



Вы пытаетесь вставить строку "@xml",
а не значение переменной @xml.
1 ноя 08, 18:47    [6389074]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
efdm
sql-dsk

-- так не работает ... что я делаю не правильно?
set @xml1.modify(
'insert @xml2 after (DataInfo/Contact)[2]')


Вы пытаетесь вставить строку "@xml",
а не значение переменной @xml.


возможно и так ...
Вопрос: как вставить значение переменной @xml2?
1 ноя 08, 19:15    [6389104]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
TimonSP
Member

Откуда:
Сообщений: 107
sql-dsk
efdm
sql-dsk

-- так не работает ... что я делаю не правильно?
set @xml1.modify(
'insert @xml2 after (DataInfo/Contact)[2]')


Вы пытаетесь вставить строку "@xml",
а не значение переменной @xml.


возможно и так ...
Вопрос: как вставить значение переменной @xml2?


А для чего (какая стоит задача), может можно обойтись?

PS: Ответа на этот вопрос я не знаю :(
1 ноя 08, 20:30    [6389229]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
TimonSP
Member

Откуда:
Сообщений: 107
В 2008 помоглобы sql:variable()
1 ноя 08, 21:29    [6389319]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
daw
Member

Откуда: Муром -> Москва
Сообщений: 7381
>Вопрос: как вставить значение переменной @xml2?

если 2005-ый, то читайте это: http://blogs.msdn.com/denisruc/archive/2006/05/17/600250.aspx

Posted via ActualForum NNTP Server 1.4

2 ноя 08, 15:26    [6390207]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
TimonSP
sql-dsk
efdm
sql-dsk

-- так не работает ... что я делаю не правильно?
set @xml1.modify(
'insert @xml2 after (DataInfo/Contact)[2]')


Вы пытаетесь вставить строку "@xml",
а не значение переменной @xml.


возможно и так ...
Вопрос: как вставить значение переменной @xml2?


А для чего (какая стоит задача), может можно обойтись?

PS: Ответа на этот вопрос я не знаю :(

Для выгрузки данных во внешние системы хочу выборку данных из разных таблиц запихнуть в xml ...

задумка такая: внешняя система вызывает метод web-сервиса, метод вызывает функцию БД, которая возвращает xml, следовательно метод web-сервиса возвращает данные в формате xml ...

внешняя система принимает эти данные и делает с ними необходимые манипуляции ...

daw

если 2005-ый, то читайте это: http://blogs.msdn.com/denisruc/archive/2006/05/17/600250.aspx

да, юзаю 2005-ый сервер
спасибо, прочитал ...

описанные методы не подойдут, т.к. все они пытаются слепить две xml-переменные используя nvarchar ... а если у меня выборка из таблицы будет 10 000 записей, то nvarchar не поможет ...

т.к. в функции БД не получается слепить один большой набор данных xml, то наверное прийдётся его лепить в методе web-сервиса ... буду вызывать функцию БД возвращающую xml столько раз сколько нужно и полученные данные буду объединять ... хотя, конечно, хотелось бы чтобы объединенный xml возвращала функция БД ...
2 ноя 08, 16:53    [6390327]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
Mnior
Member

Откуда: Кишинёв
Сообщений: 6724
TimonSP
В 2008 помоглобы sql:variable()
Ну наконец-то. Вот если бы они могли это разрешить в 2005. Хотя так больше повода купить 2008.
sql-dsk
Для выгрузки данных во внешние системы хочу выборку данных из разных таблиц запихнуть в xml ...
А почему бы не делать сразу один XML?:
DECLARE	@xml	XML

SELECT	@xml	= (
SELECT	Top(2)
	 ContactID
	,(	SELECT	Top(2)
			 AddressID
			,PostalCode
		FROM	Person.Address
	--	WHERE	A.ContactID = C.ContactID ...
		FOR	XML Raw('Address'),Root('DataInfo'),Elements,Type)
	,FirstName
	,LastName
FROM	Person.Contact
FOR	XML Raw('Contact'),Root('DataInfo'),Elements)

SELECT	@xml
Что мешает?
2 ноя 08, 21:31    [6390806]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
TimonSP
Member

Откуда:
Сообщений: 107
Для связанных таблиц запрос, который написал Mnior самое то.
А для объединения независимых запросов можно использовать:

DECLARE @xml XML

SET @xml = (
    SELECT
    (  
        SELECT Top(2)
             ContactID
            ,FirstName
            ,LastName
        FROM Person.Contact
        FOR XML Raw('Contact'),Elements,Type
    ) 
    ,
    (    
        SELECT Top(2)
            AddressID
           ,PostalCode
        FROM Person.Address
        FOR XML Raw('Address'),Elements,Type
    ) 
    FOR XML PATH (''),Root('DataInfo')
)

SELECT @xml

Кстати этот же метод можно использовать для объединения двух переменных типа XML, если вставлять именно в корневой каталог - просто сами переменные надо заводить без ROOT, а его указывать в объединении:
use AdventureWorks

declare @xml1 xml, @xml2 xml

set @xml1 = 
(select top 2 ContactID, FirstName, LastName 
from Person.Contact
for xml raw('Contact')/*, root('DataInfo')*/, elements)

set @xml2 = 
(select top 2 AddressID, PostalCode
from Person.Address
for xml raw('Address')/*, root('DataInfo')*/, elements)
-- так работает ...
set @xml1.modify(
'insert (<comment> 8745684 </comment>) after (DataInfo/Contact)[2]')

select @xml1

set @xml1 = (select @xml1,@xml2 for xml path(''), root('DataInfo'))

select @xml1
2 ноя 08, 21:57    [6390846]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
Mnior
А почему бы не делать сразу один XML?:
DECLARE	@xml	XML

SELECT	@xml	= (
SELECT	Top(2)
	 ContactID
	,(	SELECT	Top(2)
			 AddressID
			,PostalCode
		FROM	Person.Address
	--	WHERE	A.ContactID = C.ContactID ...
		FOR	XML Raw('Address'),Root('DataInfo'),Elements,Type)
	,FirstName
	,LastName
FROM	Person.Contact
FOR	XML Raw('Contact'),Root('DataInfo'),Elements)

SELECT	@xml
Что мешает?

мешает недостаток опыта работы с xml в MS SQL Server ... :)
Спасибо!
3 ноя 08, 14:48    [6391925]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
TimonSP
Для связанных таблиц запрос, который написал Mnior самое то.
А для объединения независимых запросов можно использовать:

DECLARE @xml XML

SET @xml = (
    SELECT
    (  
        SELECT Top(2)
             ContactID
            ,FirstName
            ,LastName
        FROM Person.Contact
        FOR XML Raw('Contact'),Elements,Type
    ) 
    ,
    (    
        SELECT Top(2)
            AddressID
           ,PostalCode
        FROM Person.Address
        FOR XML Raw('Address'),Elements,Type
    ) 
    FOR XML PATH (''),Root('DataInfo')
)

SELECT @xml

Кстати этот же метод можно использовать для объединения двух переменных типа XML, если вставлять именно в корневой каталог - просто сами переменные надо заводить без ROOT, а его указывать в объединении:
use AdventureWorks

declare @xml1 xml, @xml2 xml

set @xml1 = 
(select top 2 ContactID, FirstName, LastName 
from Person.Contact
for xml raw('Contact')/*, root('DataInfo')*/, elements)

set @xml2 = 
(select top 2 AddressID, PostalCode
from Person.Address
for xml raw('Address')/*, root('DataInfo')*/, elements)
-- так работает ...
set @xml1.modify(
'insert (<comment> 8745684 </comment>) after (DataInfo/Contact)[2]')

select @xml1

set @xml1 = (select @xml1,@xml2 for xml path(''), root('DataInfo'))

select @xml1

Спасибо! Фактически то, что нужно!

Ещё маленький вопросик:
после выполнения первого запроса получается xml следующей структуры:
<DataInfo>
<Contact>
....
</Contact>
<Contact>
...
</Contact>
<Address>
...
</Address>
<Address>
...
</Address>
</DataInfo>

а каким образом получить такой xml:
<DataInfo>
<Contact>
<row>
...
</row>
<row>
...
</row>
</Contact>
<Address>
<row>
...
</row>
<row>
...
</row>
</Address>
</DataInfo>
3 ноя 08, 15:01    [6391960]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
TimonSP
Member

Откуда:
Сообщений: 107
sql-dsk,

Попробуйте вот так:
DECLARE @xml XML

SET @xml = (
    SELECT
    (  
        SELECT Top(2)
             ContactID
            ,FirstName
            ,LastName
        FROM Person.Contact
        FOR XML Raw('Row'),Root('Contact'),Elements,Type
    ) 
    ,
    (    
        SELECT Top(2)
            AddressID
           ,PostalCode
        FROM Person.Address
        FOR XML Raw('Row'),Root('Address'),Elements,Type
    ) 
    FOR XML PATH (''),Root('DataInfo')
)

SELECT @xml
3 ноя 08, 16:52    [6392246]     Ответить | Цитировать Сообщить модератору
 Re: добавление данных в переменную типа xml  [new]
sql-dsk
Member

Откуда:
Сообщений: 6
TimonSP
sql-dsk,

Попробуйте вот так:
DECLARE @xml XML

SET @xml = (
    SELECT
    (  
        SELECT Top(2)
             ContactID
            ,FirstName
            ,LastName
        FROM Person.Contact
        FOR XML Raw('Row'),Root('Contact'),Elements,Type
    ) 
    ,
    (    
        SELECT Top(2)
            AddressID
           ,PostalCode
        FROM Person.Address
        FOR XML Raw('Row'),Root('Address'),Elements,Type
    ) 
    FOR XML PATH (''),Root('DataInfo')
)

SELECT @xml

Большое спасибо!
Всё получилось!

Можно считать вопрос закрытым!
3 ноя 08, 18:47    [6392482]     Ответить | Цитировать Сообщить модератору
Между сообщениями интервал более 1 года.
 Re: добавление данных в переменную типа xml  [new]
Кесарь
Member

Откуда:
Сообщений: 671
TimonSP
А для объединения независимых запросов можно использовать
...
Кстати этот же метод можно использовать для объединения двух переменных типа XML, если вставлять именно в корневой каталог - просто сами переменные надо заводить без ROOT, а его указывать в объединении


Это нормальный метод, если точно знаешь что куда и надо сделать один раз. А если не один? Ну то есть не сцепить два набора, а вставить набор значений промежду другого? Первый случай ведь редуцированный случай последнего...

Вот так примерно можно (можно наверное и лучше, но я сделал так):

declare @a as xml,@b as xml, @str nvarchar(1000), @n int, @n_max int;

select @a='';
select @n = 0;
set @b='<form id="1" /><form id="2" />';

select @a = cast(cast(@a as nvarchar(max)) + '<root>' + cast(@b as nvarchar(max)) + '</root>' as xml)

select @n_max = COUNT(1)
from (select 11 as 'str' from @a.nodes('/root/form') T(c)) R

-- здесь помещаем один и тот же кусок комментария, но пользуясь данной схемой его тоже можно менять.
-- Главное здесь - это подстановка по номерам узла, который проставляются динамически
while @n < @n_max
begin
  --set @str = 'set @a.modify('+''insert (<comment> 8745684 </comment>) after (root/form)[' + convert(varchar(100), @n) + ']'')'
  --set @str = 'set @a.modify('+''insert (<comment> 8745684 </comment>) after (root/form)[' + convert(varchar(100), @n) + ']'')'
  select @n = @n + 1

  select @str = 'set @a.modify(''' + 'insert (<comment> 8745684 </comment>) after (root/form)['+ convert(varchar(100), @n) +']'')'

  select @str

  exec sp_executesql @str, N' @a xml out', @a = @a out
end

select @a
9 мар 17, 17:47    [20278854]     Ответить | Цитировать Сообщить модератору
Все форумы / Microsoft SQL Server Ответить