XML VALUE: примеры (SQL)
XML_VALUE(XQuery, SQLType): Specified SQLTypeОписание функции XML_VALUE
Функция XML_VALUE в MS SQL Server предназначена для извлечения скалярных значений из XML-документов с использованием XQuery выражений. Эта функция применяется при необходимости получить одиночное значение из XML-поля или переменной, например, при разборе конфигурационных данных, логов или структур с регулярной схемой.
Синтаксис функции:XML_VALUE ( expression, XQuery )
Параметры:
expression - выражение типа XML, содержащее анализируемый документ или фрагмент. Может быть столбцом, переменной или результатом другой функции.
XQuery - строковое выражение XQuery, указывающее путь к извлекаемому узлу. Должно возвращать скалярное значение или пустую последовательность.
Возвращаемое значение:
Функция возвращает скалярное значение типа SQL, соответствующее результату XQuery выражения. Если XQuery возвращает пустую последовательность, результатом будет NULL. Тип возвращаемого значения определяется контекстом или требует явного приведения при необходимости.
Базовые примеры использования
Извлечение значения атрибута из XML элемента:
DECLARE @xml XML = 'Monitor ';
SELECT XML_VALUE(@xml, '/product/@id') AS ProductID;ProductID
----------
123
Получение текстового содержимого элемента:
DECLARE @xml XML = 'Иван 30 ';
SELECT XML_VALUE(@xml, '/user/name') AS UserName;UserName
--------
Иван
Использование с приведением типа данных:
DECLARE @xml XML = '42.5 ';
SELECT CAST(XML_VALUE(@xml, '/data/value') AS DECIMAL(5,2)) AS NumericValue;NumericValue
------------
42.50
Похожие функции в MS SQL
XML_QUERY - возвращает XML фрагмент вместо скалярного значения. Применяется для извлечения поддеревьев XML. Отличие состоит в том, что XML_QUERY сохраняет XML структуру результата.
XML_EXIST - проверяет существование узлов, возвращает битовое значение. Используется в условиях WHERE для фильтрации строк по наличию элементов.
Метод .value() - аналогичная функциональность через методы типа данных XML. Синтаксис: @xml.value('XQuery', 'SQLType'). Требует явного указания типа результата, что повышает безопасность.
Выбор функции зависит от задачи: для одиночных значений удобна XML_VALUE, для фрагментов - XML_QUERY, для проверок - XML_EXIST. Метод .value() часто предпочтительнее в запросах к таблицам.
Распространенные ошибки
Ожидание единственного узла при возврате нескольких:
DECLARE @xml XML = '- 1
- 2
';
SELECT XML_VALUE(@xml, '/items/item');Сообщение 2370, уровень 16
XQuery: В методе value() требуется одиночный узел, найдено 2 узлов
Некорректный XQuery путь:
DECLARE @xml XML = 'test ';
SELECT XML_VALUE(@xml, '/root/missing');NULL
Попытка извлечь XML структуру как скалярное значение:
DECLARE @xml XML = 'value ';
SELECT XML_VALUE(@xml, '/root/child');value
Эта ошибка возникает при использовании .value() для узла, содержащего дочерние элементы. XML_VALUE возвращает текстовое содержимое первого дочернего текстового узла.
Изменения в последних версиях
В SQL Server 2016 и более новых версиях улучшена производительность обработки XML, включая функцию XML_VALUE. Добавлена лучшая интеграция с системами in-memory, хотя сама функция не может использоваться в индексированных представлениях памяти. Изменений в синтаксисе или основных возможностях функции с момента ее появления не было.
В SQL Server 2017 улучшена обработка ошибок XQuery, что влияет на сообщения об ошибках при некорректных запросах. Также расширена поддержка стандарта XQuery 3.0, что позволяет использовать более сложные выражения в качестве второго параметра.
Расширенные примеры
Извлечение значений с пространствами имен:
DECLARE @xml XML = 'Data ';
SELECT XML_VALUE(@xml, 'declare namespace n="http://example.com"; /n:root/n:value');Data
Использование в сочетании с CROSS APPLY для разбора коллекций:
DECLARE @xml XML = ' ';
SELECT n.value('@id', 'INT') AS ProductID
FROM @xml.nodes('/products/product') AS t(n);ProductID
----------
1
2
Обработка условий в XQuery:
DECLARE @xml XML = 'A 100 ';
SELECT XML_VALUE(@xml, '/data/value[../type="A"]');100
Работа с глубоко вложенными структурами:
DECLARE @xml XML = 'Success ';
SELECT XML_VALUE(@xml, '/level1/level2/level3/target');Success
Извлечение данных с преобразованием даты:
DECLARE @xml XML = '2023-12-31 ';
SELECT CAST(XML_VALUE(@xml, '/event/date') AS DATE) AS EventDate;EventDate
----------
2023-12-31
Аналоги в других СУБД
PostgreSQL - функция xpath() или оператор ->>:
SELECT (xpath('/product/@id', ' '))[1]::text;?column?
----------
123
Oracle - EXTRACTVALUE (устаревшая) или XMLTABLE:
SELECT EXTRACTVALUE(XMLType(' '), '/product/@id') FROM dual;EXTRACTVALUE
------------
123
MySQL - ExtractValue():
SELECT ExtractValue(' ', '/product/@id');ExtractValue
------------
123
Отличие MS SQL в более строгой типизации и интеграции с XQuery стандартом. В SQLite аналогичные операции требуют использования расширений или обработки в приложении.