检查XMLType节点值并在必要时进行更新

时间:2015-12-08 10:53:14

标签: xml oracle oracle11g xmltype

我有一个像这样的simle xml:

<Parameters>
 <Parameter>
  <Index>0</Index>
  <Name>Date</Name>
  <Value>@Today</Value>
 </Parameter>
 <Parameter>
  <Index>1</Index>
  <Name>Id</Name>
  <Value>22</Value>
 </Parameter>
</Parameters>

我想迭代每个参数,如果值以&#39; @&#39;开头。调用一个函数,该函数将值作为参数并返回一个新值 使用newvalue更新xml 我已经找到了如何使用updatexml,但没有运气如何实现我的场景。

2 个答案:

答案 0 :(得分:4)

您可以通过每个参数节点循环执行,按功能更改值(我的代码中的内部CheckXmlValue) -

declare
  cur_xml  sys_refcursor;
  v_val varchar2(3000);
  n_val varchar2(3000);
  xml_     XMLType := XMLType(
        '<Parameters>
         <Parameter>
          <Index>0</Index>
          <Name>Date</Name>
          <Value>@Today</Value>
         </Parameter>
         <Parameter>
          <Index>1</Index>
          <Name>Id</Name>
          <Value>22</Value>
         </Parameter>
        </Parameters>'
);
    function CheckXmlValue(val_ in varchar2) return varchar2 is
    begin
        return 
            case lower(val_)
                when '@today' then to_char(sysdate, 'dd/mm/yyyy')
                when '@yesterday' then to_char(sysdate-1, 'dd/mm/yyyy')
                else val_
            end;
    end;
begin
  open cur_xml for
    select extractValue(column_value, '//Value') str
      from table(XMLSequence(extract(xml_, '/Parameters/Parameter')));
  loop
    fetch cur_xml into v_val;
    n_val := CheckXmlValue(v_val);
    exit when cur_xml%notfound;
    select updateXml (
                xml_,
                '//Parameters/Parameter/Value[text()="'||v_val||'"]/text()',
                n_val
           )
    into xml_
    from DUAL;
  end loop;
  close cur_xml;
  -- result:
  dbms_output.put_line(xml_.extract('*').getStringVal());
end;
/

答案 1 :(得分:1)

这个怎么样?如果在PL * SQL中使用,只需使用函数。

  select updatexml(xmltype('<Parameters>
         <Parameter>
          <Index>0</Index>
          <Name>Date</Name>
          <Value>@Today</Value>
         </Parameter>
         <Parameter>
          <Index>1</Index>
          <Name>Id</Name>
          <Value>22</Value>
         </Parameter>
        </Parameters>'), '/Parameters/Parameter/Value[text()="@Today"]', to_char(sysdate, 'dd/mm/yyyy')) 
from dual;

请注意,这是我调用的函数,如果已经发布,请替换为您自己的函数。

对于许多不同的变体,只需在upatexml中添加一个此类更改,例如:

  select updatexml(xmltype('<Parameters>
         <Parameter>
          <Index>0</Index>
          <Name>Date</Name>
          <Value>@Today</Value>
         </Parameter>
         <Parameter>
          <Index>1</Index>
          <Name>Id</Name>
          <Value>22</Value>
         </Parameter>
         <Parameter>
          <Index>2</Index>
          <Name>Id</Name>
          <Value>@Yesterday</Value>
         </Parameter>
        </Parameters>'), '/Parameters/Parameter/Value[text()="@Today"]/text()'    , to_char(sysdate    , 'dd/mm/yyyy')
                       , '/Parameters/Parameter/Value[text()="@Yesterday"]/text()', to_char(sysdate - 1, 'dd/mm/yyyy')) 
from dual;