PostgreSQL11 xpath-запрос не работает должным образом - PullRequest
1 голос
/ 17 апреля 2020

Когда я выполняю запрос ниже в Postgres 10.12, он работает правильно.

SELECT (xpath('./sid/text()', c.node))[1]::text::bigint AS STUDENT_ID,
       (xpath('./name/text()', c.node))[1]::text AS STUDENT_NAME
from (    
  select unnest(xpath('/data', '<data><sid>112233</sid><name>John</name></data>'::xml)) AS node    
) c;

Вывод:

enter image description here

Но когда я выполняю тот же запрос в Postgres 11.7, он не работает.

enter image description here

Как решить эту проблему?

1 Ответ

2 голосов
/ 17 апреля 2020

Это вызвано этим изменением :

Правильно обрабатывать относительные выражения пути в xmltable (), xpath () и других XML функциях обработки (Markus Winand) )

В соответствии со стандартом SQL относительные пути начинаются с узла документа входного документа XML, а не с узла root, как это делали ранее эти функции.

поэтому вам нужно изменить его на:

SELECT (xpath('/data/sid/text()', c.node))[1]::text::bigint AS STUDENT_ID,
       (xpath('/data/name/text()', c.node))[1]::text AS STUDENT_NAME
from (    
  select unnest(xpath('/data', '<data><sid>112233</sid><name>John</name></data>'::xml)) AS node    
) c;

, поскольку внутренний xpath также вернет тег <data>:

select unnest(xpath('/data', '<data><sid>112233</sid><name>John</name></data>'::xml)) AS node

приведет к:

<data>
  <sid>112233</sid>
  <name>John</name>
</data>

Однако для этого я бы использовал xmltable:

select *
from xmltable('/data'
               passing xml('<data><sid>112233</sid><name>John</name></data>')
               columns 
                  student_id bigint path 'sid', 
                  student_name text path 'name')
...