Oracle11g ORA-19279 XPTY0004-Xquery动态类型不匹配:预期的单例序列-获取的多项序列
我在CLOB列中有下面的xml消息:Oracle11g ORA-19279 XPTY0004-Xquery动态类型不匹配:预期的单例序列-获取的多项序列,oracle11g,oracle-sqldeveloper,xml-namespaces,xmltable,Oracle11g,Oracle Sqldeveloper,Xml Namespaces,Xmltable,我在CLOB列中有下面的xml消息: <Message type="Close Subscription" creationdatetime="15/01/2010 07:48" market="01" xmlns="http://test.org/"> <Customer userId="data" market="01"> <UserAccount>test@hotmail.com</UserAccount> <Exp
<Message type="Close Subscription" creationdatetime="15/01/2010 07:48" market="01" xmlns="http://test.org/">
<Customer userId="data" market="01">
<UserAccount>test@hotmail.com</UserAccount>
<ExpireDate>15/02/2016 07:48:11</ExpireDate>
<Member>
<MemberReferency number="000003" digit="85" market="01" name="John Rambo"/>
</Member>
<Email Id="700">
<Address>test@hotmail.com</Address>
<IsConfirmed>True</IsConfirmed>
<Privacies>
<Privacy type="C" value="I"/>
<Privacy type="M" value="I"/>
</Privacies>
</Email>
<Newsletter mailService="NL">
<language>N</language>
<frequency>0</frequency>
<promotion/>
<origin/>
</Newsletter>
</Customer>
</Message>
注意:当xml标记privacy在xml消息中出现一次时,不会引发错误。根据您在只有M-type节点时希望发生的情况,您可以显式搜索C:
select x.privacy
from notification_log a
cross join XMLTable(XMLNamespaces('http://test.org/' AS "XML"),
'/XML:Message'
passing XMLType(ntl_msg)
columns privacy varchar2(1)
path 'XML:Customer/XML:Email/XML:Privacies/XML:Privacy[@type="C"]/@value') x
where a.ntl_type = 'Message';
PRIVACY
-------
I
或者,您可以通过第二级XMLTable提取所有隐私节点的类型和值,然后决定保留哪一个:
select min(x2.privacy) keep (dense_rank first order by x2.type) as privacy
from notification_log a
cross join XMLTable(XMLNamespaces('http://test.org/' AS "XML"),
'/XML:Message' passing XMLType(ntl_msg)
columns privacies XMLType path 'XML:Customer/XML:Email/XML:Privacies') x1
cross join XMLTable(XMLNAMESPACES('http://test.org/' AS "XML"),
'XML:Privacies/XML:Privacy'
passing privacies
columns type varchar2(1) path '@type',
privacy varchar2(1) path '@value') x2
where a.ntl_type = 'Message';
PRIVACY
-------
I
如果您运行相同的查询,但是选择了x2.type,x2.value from…,那么您会看到:
TYPE PRIVACY
---- -------
C I
M I
。。
min(x2.privacy)keep(density_rank first order by x2.type)
从“lower”(根据字符串比较)类型值中获取值类型;这意味着如果两者都存在,它会优先考虑C而不是M,但是如果只有一个隐私节点,它会使用任意一个,如果只有一个隐私节点,但它的类型是M,您希望看到什么?换句话说,你是只想要那些有C的,还是你想优先考虑C而不是M,但如果这是唯一的一个,仍然要显示M?非常感谢你,很好的解决方案。
select min(x2.privacy) keep (dense_rank first order by x2.type) as privacy
from notification_log a
cross join XMLTable(XMLNamespaces('http://test.org/' AS "XML"),
'/XML:Message' passing XMLType(ntl_msg)
columns privacies XMLType path 'XML:Customer/XML:Email/XML:Privacies') x1
cross join XMLTable(XMLNAMESPACES('http://test.org/' AS "XML"),
'XML:Privacies/XML:Privacy'
passing privacies
columns type varchar2(1) path '@type',
privacy varchar2(1) path '@value') x2
where a.ntl_type = 'Message';
PRIVACY
-------
I
TYPE PRIVACY
---- -------
C I
M I