Published on

September 29, 2007

Понимание пространств имен XML в SQL Server

В этой статье мы рассмотрим концепцию пространств имен XML в SQL Server. Пространства имен XML используются для избегания конфликтов имен при работе с XML-данными. Мы обсудим пространства имен по умолчанию и способы генерации и чтения XML с информацией о пространствах имен.

Пространство имен по умолчанию

Пространство имен по умолчанию применяется ко всем элементам XML-документа без префикса. Оно может быть объявлено в корне документа или для конкретного элемента XML. Когда пространство имен по умолчанию объявлено, все элементы без префикса принадлежат этому пространству имен.

Рассмотрим пример:

<Configuration
xmlns="urn:www.dotnetquest.com/DbConnection"
xmlns:net="urn:www.dotnetquest.com/NetConnection">
  <net:Connection>
    <net:Provider>Провайдер всемирной паутины</net:Provider>
    <net:Speed>512 КБ/с</net:Speed>
  </net:Connection>
  <Connection>
    <Provider>Провайдер SQL-клиента</Provider>
    <Protocol>TCP/IP</Protocol>
    <Authentication>Windows</Authentication>
  </Connection>
</Configuration>

В приведенном выше XML первое пространство имен объявлено как пространство имен по умолчанию. Все элементы без префикса принадлежат этому пространству имен. XML также можно записать с использованием объявления пространства имен по умолчанию:

<Configuration
xmlns="urn:www.dotnetquest.com/DbConnection"
xmlns:net="urn:www.dotnetquest.com/NetConnection">
  <net:Connection>
    <net:Provider>Провайдер всемирной паутины</net:Provider>
    <net:Speed>512 КБ/с</net:Speed>
  </net:Connection>
  <Connection>
    <Provider>Провайдер SQL-клиента</Provider>
    <Protocol>TCP/IP</Protocol>
    <Authentication>Windows</Authentication>
  </Connection>
</Configuration>

Приведенный выше XML эквивалентен предыдущему, но он использует объявление пространства имен по умолчанию. Единственное отличие заключается в том, что новая версия XML использует пространство имен по умолчанию.

Генерация XML с пространством имен по умолчанию

Для генерации XML с пространством имен по умолчанию в SQL Server мы можем использовать оператор WITH XMLNAMESPACES. Вот пример:

WITH XMLNAMESPACES
(
  DEFAULT 'urn:www.dotnetquest.com/DbConnection',
  'urn:www.dotnetquest.com/NetConnection' AS net
)
SELECT
  net.Provider AS 'net:Connection/net:Provider',
  net.Speed AS 'net:Connection/net:Speed',
  db.Provider AS 'Connection/Provider',
  db.Protocol AS 'Connection/Protocol',
  db.[Authentication] AS 'Connection/Authentication'
FROM NetConnection net
CROSS JOIN DbConnection db
FOR XML PATH('Configuration')

Приведенный выше запрос генерирует XML с объявлением пространства имен по умолчанию. Пространство имен по умолчанию установлено на ‘urn:www.dotnetquest.com/DbConnection’, а префикс ‘net’ используется для пространства имен ‘urn:www.dotnetquest.com/NetConnection’.

Чтение значений из XML с пространством имен

Для чтения значений из переменной XML, содержащей информацию о пространствах имен, мы можем использовать метод value() вместе с оператором declare namespace. Вот пример:

DECLARE @x xml
SET @x = '
<Configuration
xmlns:db="urn:www.dotnetquest.com/DbConnection"
xmlns:net="urn:www.dotnetquest.com/NetConnection">
  <net:Connection>
    <net:Provider>Провайдер всемирной паутины</net:Provider>
    <net:Speed>512 КБ/с</net:Speed>
  </net:Connection>
  <db:Connection>
    <db:Provider>Провайдер SQL-клиента</db:Provider>
    <db:Protocol>TCP/IP</db:Protocol>
    <db:Authentication>Windows</db:Authentication>
  </db:Connection>
</Configuration>
'

SELECT
  x.c.value('declare namespace net="urn:www.dotnetquest.com/NetConnection";
  (net:Connection/net:Provider)[1]', 'varchar(max)') AS NetProvider,
  x.c.value('declare namespace net="urn:www.dotnetquest.com/NetConnection";
  (net:Connection/net:Speed)[1]', 'varchar(max)') AS Speed,
  x.c.value('declare namespace db="urn:www.dotnetquest.com/DbConnection";
  (db:Connection/db:Provider)[1]', 'varchar(max)') AS DbProvider,
  x.c.value('declare namespace db="urn:www.dotnetquest.com/DbConnection";
  (db:Connection/db:Protocol)[1]', 'varchar(max)') AS Protocol,
  x.c.value('declare namespace db="urn:www.dotnetquest.com/DbConnection";
  (db:Connection/db:Authentication)[1]', 'varchar(max)') AS [Authentication]
FROM @x.nodes('/Configuration') x(c)

Приведенный выше запрос читает значения из переменной XML с использованием метода value() и оператора declare namespace. Он извлекает значения из элементов ‘net:Connection’ и ‘Connection’.

Кроме того, мы можем упростить запрос, используя оператор WITH XMLNAMESPACES:

DECLARE @x xml
SET @x = '
<Configuration
xmlns:db="urn:www.dotnetquest.com/DbConnection"
xmlns:net="urn:www.dotnetquest.com/NetConnection">
  <net:Connection>
    <net:Provider>Провайдер всемирной паутины</net:Provider>
    <net:Speed>512 КБ/с</net:Speed>
  </net:Connection>
  <db:Connection>
    <db:Provider>Провайдер SQL-клиента</db:Provider>
    <db:Protocol>TCP/IP</db:Protocol>
    <db:Authentication>Windows</db:Authentication>
  </db:Connection>
</Configuration>
'

;WITH XMLNAMESPACES
(
  'urn:www.dotnetquest.com/NetConnection' AS net,
  'urn:www.dotnetquest.com/DbConnection' AS db
)
SELECT
  x.c.value('(net:Connection/net:Provider)[1]', 'varchar(20)') AS NetProvider,
  x.c.value('(net:Connection/net:Speed)[1]', 'varchar(10)') AS Speed,
  x.c.value('(db:Connection/db:Provider)[1]', 'varchar(20)') AS DbProvider,
  x.c.value('(db:Connection/db:Protocol)[1]', 'varchar(10)') AS Protocol,
  x.c.value('(db:Connection/db:Authentication)[1]', 'varchar(10)') AS [Authentication]
FROM @x.nodes('/Configuration') x(c)

Приведенный выше запрос дает те же результаты, что и предыдущий, но он использует оператор WITH XMLNAMESPACES для упрощения синтаксиса.

Заключение

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

Click to rate this post!
[Total: 0 Average: 0]

Let's work together

Send us a message or book free introductory meeting with us using button below.