SQL Server 2008 - выбор нескольких строк из оператора OPENXML - PullRequest
1 голос
/ 09 ноября 2009

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

<Student>
   <name>XYZ</name>
   <id>123</id>
   <fathersname>XYS</fathersname>
   <fathersid>3489</fathersid>
</Student>".

Теперь мне нужно добавить это как две разные строки, и БД должна выглядеть так
Name ID
XYZ 123
XYS 3489
Как я могу прочитать из этого XML и вставить как две разные строки, используя один оператор OPENXML?

1 Ответ

1 голос
/ 09 ноября 2009
CREATE TABLE dbo.Person(ID int, [Name] varchar(50))

DECLARE @docHandle int

DECLARE @xmlDocument XML
SET @xmlDocument = N'<ROOT>
<Student>
  <name>XYZ</name>
  <id>123</id>
  <fathersname>XYS</fathersname>
  <fathersid>3489</fathersid>
</Student>
<Student>
  <name>ABC</name>
  <id>456</id>
  <fathersname>DEF</fathersname>
  <fathersid>7859</fathersid>
</Student>
</ROOT>'

EXEC sp_xml_preparedocument @docHandle OUTPUT, @xmlDocument

-- student's data first
INSERT INTO dbo.Person
SELECT * 
  FROM OPENXML(@docHandle, N'/ROOT/Student',2) 
    WITH (id int, name varchar(50))

-- now insert father's data
INSERT INTO dbo.Person
SELECT * 
  FROM OPENXML(@docHandle, N'/ROOT/Student',2) 
    WITH (fathersid int, fathersname varchar(50))


SELECT * FROM dbo.Person

EXEC sp_xml_removedocument @docHandle 
DROP TABLE dbo.Person

Чтобы открыть из файла:

declare @xmlDocument XML
SET @xmlDocument=(SELECT * FROM OPENROWSET(
   BULK 'c:\Temp\Student.xml',
   SINGLE_BLOB) AS x)

UPDATE:
Извините, не увидел, что вы пытаетесь разбить <father> на другой ряд, я просто добавил для этого еще одну INSERT. Если вам нужен больший контроль над процессом загрузки, вы всегда можете подумать о создании задания ETL в SSIS.

ОБНОВЛЕНИЕ 2
Что ж, вот креативный способ только с одной вставкой, но с двумя вариантами выбора - совсем не уверен в производительности. Опять же, мы разбиваем одну запись на две строки.

INSERT INTO dbo.Person
    SELECT 
        x.e.value('id[1]', 'int') AS "id"
        ,x.e.value('name[1]', 'varchar(10)') AS "Name"  
    FROM @xmlDocument.nodes('/ROOT/Student') AS x(e)
    UNION
    SELECT 
        x.e.value('fathersid[1]', 'int') AS "id"
        ,x.e.value('fathersname[1]', 'varchar(10)') AS "Name"
    FROM @xmlDocument.nodes('/ROOT/Student') AS x(e);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...