簡體   English   中英

如何根據條件從 Oracle XMLTYPE 中刪除節點?

[英]How to delete a node from Oracle XMLTYPE based on a condition?

我有一個存儲在CLOB列中的 XML 數據,我想根據特定條件刪除一些節點。

XML 數據示例:

<?xml version="1.0" encoding="UTF-8"?>
<payment>
  <person>
    <surname>Marco</surname>
    <name>Gralike</name>
    <salary>2345</salary>
  </person>
  <person>
    <surname>ABC</surname>
    <name>TEST</name>
    <salary>1234</salary>
    <person>
    <surname>Tiger</surname>
    <name>Scott</name>
    <salary>2222</salary>
  </person>
  </person>
 </payment>
 <payment>
  <person>
    <surname>BertJan</surname>
    <name>Meinders</name>
    <salary>3456</salary>
    <salary>125</salary>
  </person>
  <person>
    <surname>XYZ</surname>
    <name>TEST</name>
    <salary>1234</salary>
  </person>
 </payment>
 <payment>
  <person>
    <surname>Chris</surname>
    <name>Gralike</name>
    <salary>4567</salary>
  </person>
  <person>
    <surname>LMN</surname>
    <name>TEST</name>
    <salary>1234</salary>
  </person>
 </payment>

如果包含 TEST,我需要一個 Oracle PLSQL 腳本來刪除所有人員標簽。

最終輸出將是:

<?xml version="1.0" encoding="UTF-8"?>
<payment>
  <person>
    <surname>Marco</surname>
    <name>Gralike</name>
    <salary>2345</salary>
  </person>
 </payment>
 <payment>
  <person>
    <surname>BertJan</surname>
    <name>Meinders</name>
    <salary>3456</salary>
    <salary>125</salary>
  </person>
 </payment>
 <payment>
  <person>
    <surname>Chris</surname>
    <name>Gralike</name>
    <salary>4567</salary>
  </person>
 </payment>

提前致謝。

您提供的XML沒有根,因此XML解析器無法對其進行解析。

假設確實如此(例如payments ),如下所示:

create table t(txt clob);
insert into t values('<?xml version="1.0" encoding="UTF-8"?>
<payments>
    <payment>
        <person>
            <surname>Marco</surname>
            <name>Gralike</name>
            <salary>2345</salary>
        </person>
        <person>
            <surname>ABC</surname>
            <name>TEST</name>
            <salary>1234</salary>
            <person>
                <surname>Tiger</surname>
                <name>Scott</name>
                <salary>2222</salary>
            </person>
        </person>
    </payment>
    <payment>
        <person>
            <surname>BertJan</surname>
            <name>Meinders</name>
            <salary>3456</salary>
            <salary>125</salary>
        </person>
        <person>
            <surname>XYZ</surname>
            <name>TEST</name>
            <salary>1234</salary>
        </person>
    </payment>
    <payment>
        <person>
            <surname>Chris</surname>
            <name>Gralike</name>
            <salary>4567</salary>
        </person>
        <person>
            <surname>LMN</surname>
            <name>TEST</name>
            <salary>1234</salary>
        </person>
    </payment>
</payments>');

您可以使用此:

update t
set txt = to_clob(deletexml(
  xmltype(t.txt),
  '//payment/person[./name[text()="TEST"]]'
));

產生:

<?xml version="1.0" encoding="UTF-8"?>
<payments>
    <payment>
        <person>
            <surname>Marco</surname>
            <name>Gralike</name>
            <salary>2345</salary>
        </person>
    </payment>
    <payment>
        <person>
            <surname>BertJan</surname>
            <name>Meinders</name>
            <salary>3456</salary>
            <salary>125</salary>
        </person>
    </payment>
    <payment>
        <person>
            <surname>Chris</surname>
            <name>Gralike</name>
            <salary>4567</salary>
        </person>
    </payment>
</payments>

編輯:

如果要刪除沒有給定子節點的節點,請使用以下命令:

update t
set txt = to_clob(deletexml(
  xmltype(t.txt),
  '//payment[not(./person)]'
));

它將刪除所有沒有人的付款標簽。

deleteXML()已被棄用。 如果可能的話,您應該使用XQuery更新。 如果完整路徑是固定的,也請嘗試避免使用'//'。

with XML_TABLE as 
(
   select XMLTYPE('<?xml version="1.0" encoding="UTF-8"?>
<payments>
<payment>
    <person>
        <surname>Marco</surname>
        <name>Gralike</name>
        <salary>2345</salary>
    </person>
    <person>
        <surname>ABC</surname>
        <name>TEST</name>
        <salary>1234</salary>
        <person>
            <surname>Tiger</surname>
            <name>Scott</name>
            <salary>2222</salary>
        </person>
    </person>
</payment>
<payment>
    <person>
        <surname>BertJan</surname>
        <name>Meinders</name>
        <salary>3456</salary>
        <salary>125</salary>
    </person>
    <person>
        <surname>XYZ</surname>
        <name>TEST</name>
        <salary>1234</salary>
    </person>
</payment>
<payment>
    <person>
        <surname>Chris</surname>
        <name>Gralike</name>
        <salary>4567</salary>
    </person>
    <person>
        <surname>LMN</surname>
        <name>TEST</name>
        <salary>1234</salary>
    </person>
</payment>
</payments>') as XML_COLUMN from dual
)
SELECT XMLQuery(
    'copy $NEWXML := $XML modify (
      delete nodes $NEWXML/payments/payment/person[name[text()=$NAME]]
     )
     return $NEWXML'
     passing XML_COLUMN as "XML",
             'TEST' as "NAME"
     returning CONTENT
   )
from XML_TABLE
/

您可以在livesql.oracle.com上嘗試使用SQL Workbench刪除此代碼

感謝您的樣品。

<payment> 
<person>
 <surname>XYZ</surname> 
 <name>TEST</name> 
 <salary>1234</salary> 
 </person> 
<id>person 4</id> 
</payment> 

如果節點之一包含上述數據,則在使用deletexml之后,我得到以下信息:

<payment> 
<id>person 4</id> 
</payment> 

如果該節點不包含任何<person>標記,如何刪除?

即如何刪除下面的節點,因為它不包含<person>標簽:

   <payment> 
    <id>person 4</id> 
    </payment>

這有效

with XML_TABLE as
(
   select XMLTYPE('<?xml version="1.0" encoding="UTF-8"?>
<payments>
  <payment>
    <person>
     <surname>XYZ</surname>
  <name>TEST</name>
  <salary>1234</salary>
</person>
<id>person 4</id>
 </payment>
 <payment>
<id>person 5</id>
</payment>
 </payments>') as XML_COLUMN from dual
)
SELECT XMLQuery(
'copy $NEWXML := $XML modify (
  delete nodes $NEWXML/payments/payment[not(person)]
 )
 return $NEWXML'
 passing XML_COLUMN as "XML",
         'TEST' as "NAME"
 returning CONTENT
)
from XML_TABLE

<?xml version="1.0" encoding="WINDOWS-1252"?>
<payments>
  <payment>
 <person>
  <surname>XYZ</surname>
  <name>TEST</name>
  <salary>1234</salary>
</person>
  <id>person 4</id>
 </payment>
</payments>

SQL>

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM