即使表达式值为空,如何强制执行 xmlforest creat 元素?

2021-10-01 00:00:00 xml sql oracle

我想使用 oracle XMLFOREST 函数.(定义链接)

示例语法:

<块引用>

XMLFOREST( [值表达式 AS 别名], [...])

我的问题是,如果值表达式为 NULL,则不会为该值表达式创建任何元素.

如何强制它添加一个空的 XML 片段?

解决方案

您可以使用 XMLFOREST:

<块引用>

如果 value_expr 为空,则不会为该 value_expr 创建任何元素.

也不是类似的XMLCOLATTVAL 功能:

<块引用>

您必须为 value_expr 指定一个值.如果 value_expr 为 null,则不返回任何元素.

XMLELEMENT 另一方面,根据请求返回一个空元素:

SQL>选择 xmlelement("EMP", xmlelement("ENAME", ename),2 xmlelement("工作", 工作),3 xmlelement("MGR", mgr)4 ).getclobval() xml5 来自 scott.emp;XML----------------------------------------------------------------<EMP><ENAME>KING</ENAME><JOB>PRESIDENT</JOB><MGR></MGR></EMP><EMP><ENAME>布莱克</ENAME><JOB>经理</JOB><MGR>7839</MGR></EMP>...

<小时>

为了完整性,还可以使用另外两个 Oracle 工具(灵感来自 这篇文章在 OTN 论坛上).首先,您可以使用 XMLQUERY(在 11.2 上?):

SQL>选择2 xml查询(3 '(#ora:view_on_null 空#) {4 <EMPS>{5 for $c in fn:collection("oradb:/SCOTT/EMP")/ROW6 返回元素 EMP {7 $c/ENAME8 , $c/JOB9 , $c/MGR10 }11}</EMPS>12 }'13 次传球(10 次为数字)为mid"14 返回内容15 ).getClobval() 结果16 从双;结果----------------------------------------------------------------------<EMPS><EMP><ENAME>KING</ENAME><JOB>PRESIDENT</JOB><MGR></MGR></EMP><EMP><ENAME>布莱克</ENAME>...

您也可以使用DBMS_XMLGEN 包:

SQL>宣布2 ctx dbms_xmlgen.ctxHandle;3 sqlstr varchar2(4000)4 := 'SELECT ename, job, mgr FROM scott.emp WHERE ename=''KING''';5 res clob;6 开始7 ctx:= dbms_xmlgen.newContext(sqlstr);8 dbms_xmlgen.setNullHandling(ctx, dbms_xmlgen.EMPTY_TAG);9 res:= dbms_xmlgen.getXML(ctx);10 dbms_xmlgen.closeContext(ctx);11 dbms_output.put_line(res);12 结束;13/<?xml version="1.0"?><行集><行><ENAME>KING</ENAME><职位>总裁</职位><MGR/></ROW></ROWSET>

I would like to use the oracle XMLFOREST function. (Link for definition)

Example Syntax:

XMLFOREST( [value expression AS alias], [...])

My problem is that if value expression is NULL, then no element is created for that value expression.

How can I enforce it to add an empty XML fragment?

解决方案

You can' use XMLFOREST:

If value_expr is null, then no element is created for that value_expr.

Nor the similar XMLCOLATTVAL function:

You must specify a value for value_expr. If value_expr is null, then no element is returned.

XMLELEMENT on the other hand returns an empty element as requested:

SQL> select xmlelement("EMP", xmlelement("ENAME", ename), 
  2                           xmlelement("JOB", job),
  3                           xmlelement("MGR", mgr)
  4         ).getclobval() xml
  5    from scott.emp;

XML
----------------------------------------------------------------
<EMP><ENAME>KING</ENAME><JOB>PRESIDENT</JOB><MGR></MGR></EMP>
<EMP><ENAME>BLAKE</ENAME><JOB>MANAGER</JOB><MGR>7839</MGR></EMP>
...


For completeness, two more Oracle tools can also be used (inspired by this post on the OTN forums). First you can use an XMLQUERY (on 11.2? ):

SQL> select
  2    xmlquery(
  3     '(#ora:view_on_null empty #) {
  4      <EMPS> {
  5          for $c in fn:collection("oradb:/SCOTT/EMP")/ROW
  6          return element EMP {
  7            $c/ENAME
  8          , $c/JOB
  9          , $c/MGR
 10       }
 11      }</EMPS>
 12     }'
 13    passing cast(10 as number) as "mid"
 14    returning content
 15  ).getClobval() as result
 16  from dual;

RESULT 
----------------------------------------------------------------------
<EMPS>
   <EMP><ENAME>KING</ENAME><JOB>PRESIDENT</JOB><MGR></MGR></EMP>
   <EMP><ENAME>BLAKE</ENAME>...

You can also use the DBMS_XMLGEN package:

SQL> DECLARE
  2    ctx    dbms_xmlgen.ctxHandle;
  3    sqlstr varchar2(4000)
  4       := 'SELECT ename, job, mgr FROM scott.emp WHERE ename=''KING''';
  5    res    clob;
  6  BEGIN
  7    ctx := dbms_xmlgen.newContext(sqlstr);
  8    dbms_xmlgen.setNullHandling(ctx, dbms_xmlgen.EMPTY_TAG);
  9    res := dbms_xmlgen.getXML(ctx);
 10    dbms_xmlgen.closeContext(ctx);
 11    dbms_output.put_line(res);
 12  END;
 13  /

<?xml version="1.0"?>
<ROWSET>
 <ROW>
  <ENAME>KING</ENAME>
  <JOB>PRESIDENT</JOB>
  <MGR/>
 </ROW>
</ROWSET>

相关文章