Thursday, November 14, 2013

Processing No Namespace XML Messages SOA 11g

Many a time, we encounter messages that are communicable but grammatically unsound.

Applying the analogy of modern day SMS (Simple Messaging Service) or IM (Instant Messaging) conversations, where messages communicated are something like shown below.

hw r u?
doin grt
wassup?

Although these convey intents, yet if you lookup these on a dictionary you will never be able to find a synonym :)

Often in IT sphere, especially in service-oriented architectures where XML is bread & butter, we see transactions from external sources which are XML-ish which are well-formed but doesn't subscribe/conform to a grammar (XSD).

This is more prevalent in cases where XML is constructed by a legacy system where namespaces are ignored.

Okay, how do we then process these XML messages - we don't have any control whatsoever on the sender/generation of the message.

Consider the following example;

<?xml version="1.0" encoding="UTF-8" ?>
<Order>
    <OrderNumber>101</OrderNumber>
    <ProductName>Apple IPad</ProductName>
    <Description>32 GB</Description>
    <Quantity>1</Quantity>
    <Cost>899</Cost>
</Order>

We are facing the same situation as the aforesaid analogy - Although the XML document is well-formed, ensures data integrity, it just doesn't conform to the rule book and hence SOA rejects messages that are not grammatically sound.

If you try and generate a XML schema from the above XML, the XSD will have a target namespace associated.
Based on this XSD, if the SOA project & XML transformations (XSLT) are built, the incoming XML in the above format will not be processed as it doesn't exactly conform to the XSD (No Namespace Definition).

In such cases, XSD must be manually edited to remove targetnamespace and namespace prefixes.

Also, XSLT transformations must be edited based on incoming XML. If there are no namespace, then remove the namespace prefixes in your XPath - disassociating elements from the namespace.

In a little more complex scenario, you may encounter XMLs in the following format (Notice the empty namespaces in sub-elements);

<?xml version="1.0" encoding="UTF-8" ?>
<Order xmlns="http://www.sathyam-soa.blogspot.com">
    <OrderNumber xmlns="">101</OrderNumber>
    <ProductName xmlns="">Apple IPad</ProductName>
    <Description xmlns="">32 GB</Description>
    <Quantity xmlns="">1</Quantity>
    <Cost xmlns="">899</Cost>
</Order>

In this case, the XML document will be consumed successfully by your SOA project but transformations (XSLT) will not be successful. This is because of the empty namespace URIs in the sub-elements although root element contains the proper namespace as per XSD.

To resolve transformation issues, ensure that in your XSLT/XPath, the namespace prefixes for all elements with empty namespace URIs are removed.

/tns:Order/tns:OrderNumber
/tns:Order/tns:Quantity

must be modified to reflect as shown below

/tns:Order/OrderNumber
/tns:Order/Quantity

Reason: Although the root element in the XML document <Order> is qualified with a namespace, empty namespaces for child nodes (xmlns="") negates the qualification and hence these will become hanging nodes.

1 comment:

  1. Hi Sathya,
    Can you please explain this little bit more for me.

    i have below requirement as output in XML without namespace.


    1234
    5


    In XSLT if i remove name space prefix i'm getting below output

    1234
    5


    Below is the XSLT Transformation:











    Please suggest on this.

    Thanks,

    ReplyDelete