Skip to Main Content
  • Questions
  • Moving XML data from BASICFILE CLOB to BINARY XML

Breadcrumb

Question and Answer

Connor McDonald

Thanks for the question, Nikhil.

Asked: August 04, 2016 - 6:31 am UTC

Last updated: August 23, 2016 - 8:28 am UTC

Version: Oracle 11g

Viewed 1000+ times

You Asked

Currently I have table which stores xml in XMLType column which internally stores XML in BasicFile Clob,I have to migrate the XML data to store XMLType column which stores XML in secure file Binary XML. I have tried using examples given in link

https://community.oracle.com/thread/2396094?tstart=0

It works for normal XML which have no xsd/namespace reference but fails if we convert xml without namespace. Please suggest the solution.

Belows are DDL and error:

CREATE TABLE clob_table (x SYS.XMLTYPE,y VARCHAR2(30)) XMLTYPE x STORE AS BASICFILE CLOB;

CREATE TABLE binaryxml_table (x XMLTYPE,y VARCHAR2(30)) XMLTYPE x STORE AS BINARY XML;

Clob table has below xml in xmltype column

<?xml version="1.0"?>

<HwInt:Request>

<HwInt:Handle>

<HwInt:RequestD>

<HwInt:Ref>7Z</HwInt:Ref>

</HwInt:RequestD>

</HwInt:Handle></HwInt:Request>

When i run below insert query

insert into binaryxml_table (x,y)select x,y from clob_table;

it gives belows error

ORA-31061: XDB error: XML event error

ORA-19202: Error occurred in XML processing

In line 2 of orastream:

LPX-00234: namespace prefix "HwInt" is not declared

Is there any way we can ignore the namspace check while moving data ?

and Chris said...

I'm struggling to understand how you inserted the XML into your clob table in the first place. Passing the document without a namespace to XMLType fails!

CREATE TABLE clob_table (x SYS.XMLTYPE,y VARCHAR2(30)) XMLTYPE x STORE AS BASICFILE CLOB;
CREATE TABLE binaryxml_table (x XMLTYPE,y VARCHAR2(30)) XMLTYPE x STORE AS BINARY XML;

insert into clob_table values (xmltype(
'<?xml version="1.0"?>
<HwInt:Request>
<HwInt:Handle>
<HwInt:RequestD>
<HwInt:Ref>7Z</HwInt:Ref>
</HwInt:RequestD>
</HwInt:Handle></HwInt:Request>'), 'stuff');

SQL Error: ORA-31011: XML parsing failed


Unless you cheat and tell Oracle the document is well formed when it isn't:

insert into clob_table values (xmlparse(document
'<?xml version="1.0"?>
<HwInt:Request>
<HwInt:Handle>
<HwInt:RequestD>
<HwInt:Ref>7Z</HwInt:Ref>
</HwInt:RequestD>
</HwInt:Handle></HwInt:Request>' wellformed), 'stuff');


I think your best bet it to convert it back to a string. Then change it to either remove the HwInt namespaces or define it!

insert into binaryxml_table (x,y)
  select xmltype(replace(xmlserialize(content x), 'HwInt:')),y 
  from clob_table;
 
select * from binaryxml_table;

X
------------------------------

Y
------------------------------
<?xml version="1.0"?>
<Request>
  <Handle>
    <RequestD>
      <Ref>7Z</Ref>
    </RequestD>
  </Handle>
</Request>
stuff

Rating

  (4 ratings)

Is this answer out of date? If it is, please let us know via a Comment

Comments

Inserting XML using CLOB from java program

Nikhil Mehrotra, August 10, 2016 - 10:51 am UTC

Thanks for your quick response.

We are able to insert XML in xmltype using CLOB by using stored procedure given and calling it from java program

CREATE OR REPLACE PROCEDURE "IS_INSERT_XMLTYPE" (
piCLXML CLOB,
piID VARCHAR2,
) AS
BEGIN
INSERT INTO clob_table (
x,y
)
VALUES (
XMLTYPE(piCLXML,NULL,1,1),
piID,
);
EXCEPTION
WHEN OTHERS THEN
RAISE;

END;

So by using this we able to insert all the xmls without namespace.
I have tried using same store procedure for binary xml but it gives the namespace error.

Actually we are looking options to store xml in some different data type where we can have save some space.

Currently our 50% of tablespace is utilized by lob storage.


Chris Saxon
August 11, 2016 - 3:37 pm UTC

XML documents can be quite large! I'm not sure how you expect to save space just by moving to a different data type.

Why do you need the namespace without defining it? Trimming that off your input could save a fair chunk of space...

Nikhil Mehrotra, August 17, 2016 - 10:45 am UTC

Thanks for the update.

I have used the following link to test size of Basic File clob and Binary XML and found huge difference.Thats why we decided to move the data from XML clob to binary xml ,but we are facing the issue with namespace XML.

http://stackoverflow.com/questions/24764707/how-big-is-an-oracle-xmltype-when-stored-as-binary-xml

The XML, Non-XML messages are being stored in CLOB and BLOB columns respectively in our XML storage table.
We have to store the XML as it is recieved from client.We can not modify the content.

Due to increasing traffic , there is a constant need to defragment the Oracle tablespace that stores data blocks belonging to XML storage table.

Also, the size of the above table has an impact on sequential read performance of its data by application.

IS there any way we can stop increasing the XML type table size ?
Chris Saxon
August 17, 2016 - 12:04 pm UTC

there is a constant need to defragment the Oracle tablespace that stores data blocks belonging to XML storage table.

I'm not sure why you have need to defragment. Could you clarify?

Defrag requirement to cleanup space

Nikhil Mehrotra, August 19, 2016 - 5:36 am UTC

Actually we are inserting 1 million XML daily in table which holds the XML data .Due to which our tablespace is growing very fast and occupying ample space.We also delete data from this table but that does not free up the space.

For reclaiming tablespace and to free up space DBA needs to run defragmentation (clean up space) at regular intervals.
As per DBA cleaning up lob segments needs lot of downtime for the database which is not possible for us. Some time it takes 12-14 hours to clean up (free) lob space segments.

So we are looking feasible options to store XML which takes less space and reclaiming the table space is also smooth.

Can you suggest some ways where we can improve on this part .
Connor McDonald
August 19, 2016 - 8:42 am UTC

Have you looked at daily/weekly/monthly partitioning? Each partition can have its own tablespace.

Then, instead of deleting data, you can drop old partitions and even remove the tablespaces. Provided you haven't put anything else in it! ;)

I'm assuming that the delete is a "get rid of rows older than X" style. If it's randomly scattered though rows this approach may not help.

Enable row movement and shrink space

Nikhil Mehrotra, August 23, 2016 - 5:42 am UTC

Currently there is no partitioning available for our tables.We have the option for creating the partitioned table but for that we have to redefine all of our tables which may further require long downtime.

I have look for enable row movement and shrink space option which i found to be very useful as it free up the space online without any downtime .Is it advisable to use enable row movement and shrink space?

I can run the the below dbmsspace package and use the recommendations for the cleaning activity

select tablespace_name, segment_name, segment_type, partition_name,
recommendations, c1 from
table(dbms_space.asa_recommendations('FALSE', 'FALSE', 'FALSE'));
Connor McDonald
August 23, 2016 - 8:28 am UTC

If you want to recover space, shrink is the way to go:

https://asktom.oracle.com/pls/apex/f?p=100:11:::NO:RP:P11_QUESTION_ID:9527343800346989243

If you want to explore partitioning you can minimize the downtime by using DBMS_redefinition:

https://oracle-base.com/articles/9i/high-availability-enhancements-9i#OnlineTableRedefinition

If you have the auto segment advisor running, then yes, that query will give you the latest recommendations.

More to Explore

CLOB/BLOB/etc

Complete documentation on Securefiles and Large Objects here