Sunday, 24 April 2016

XPath by example in Oracle Service Bus

"Growing old ...So copied the below reference from Chris Tompkins blog as a reference  :)  "



Oracle Service Bus (and the other products in the SOA Suite) is designed to help you solve the majority of common integration scenarios without writing any code. However, as one customer pointed out to me recently:
Lets assume the XML below forms the message payload (i.e. the contents of the body variable, $body) in Oracle Service Bus and we are just using a Log action to print out the result.
<?xml version="1.0" encoding="UTF-8"?>
<p:PurchaseOrder id="1234" xmlns:p="
http://www.someshop.com/PurchaseOrder"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.someshop.com/PurchaseOrder PurchaseOrder.xsd ">
  <p:date>2010-04-02</p:date>
  <p:custID>C7123843</p:custID>
  <p:items>
    <p:item id="GF234324">
      <p:description>Denim Jeans</p:description>
      <p:department>Clothing</p:department>
      <p:price>30.99</p:price>
      <p:quantity>2</p:quantity>
    </p:item>
    <p:item id="HD312782">
      <p:description>iPod 80Gb White</p:description>
      <p:department>Electrical</p:department>
      <p:price>99.99</p:price>
      <p:quantity>1</p:quantity>
    </p:item>
    <p:item id="HD998775">
      <p:description>iPod Headphones</p:description>
      <p:department>Electrical</p:department>
      <p:price>19.99</p:price>
      <p:quantity>1</p:quantity>
    </p:item>
    <p:item id="KD123984">
      <p:description>Frying Pan</p:description>
      <p:department>Home</p:department>
      <p:price>9.99</p:price>
      <p:quantity>1</p:quantity>
    </p:item>
  </p:items>
  <p:cardDetails>
    <p:type>Mastercard</p:type>
    <p:cardNumber>1234-5678-1234-5678</p:cardNumber>
  </p:cardDetails>
</p:PurchaseOrder>
Below are the XPath expressions you will need to log the various information from the payload:
a) The purchase order id:
$body/pur:PurchaseOrder/@id
Note: The actual namespace prefix, i.e. pur (the default assigned by Oracle Service Bus in this case), does not have to match the namespace prefix in the original XML document (p), however they both need to point to the namespace URL http://www.someshop.com/PurchaseOrder.
b) The customer id:
$body/pur:PurchaseOrder/pur:custID/text()
Note: In contrast to attributes, XML elements (nodes) can contain a variety of different types of data or even other complex elements, hence the use of the text() function to get the textual data from the element.
c) The card number (assuming you don’t know its path):
$body//pur:cardNumber/text()
Note: The use of // in XPath is not advised (unless absolutely necessary) as it does involve searching through the whole XML tree and so is not  very performant particularly for large payloads.
d) The card number (assuming you don’t know its path or namespace):
$body//*:cardNumber/text()
e) The number of items in the purchase order:
count($body/pur:PurchaseOrder/pur:items/pur:item)
Note: We are using the count function and pointing to the repeating item element in the XML payload.
f) The id of the first item in the order:
$body/pur:PurchaseOrder/pur:items/pur:item[1]/@id
Note: We are using the [1] to select the first item – XPath is unlike most programming languages which index  arrays from 0 rather than 1.
g) The item(s) with id GF234324:
$body/pur:PurchaseOrder/pur:items/pur:item[@id="GF234324"]
Note: This expression will actually return a list of all items whose id attribute is GF234324 – in our example there is only one item with this id.
h) The description of the item with id GF234324:
$body/pur:PurchaseOrder/pur:items/pur:item[@id="GF234324"]/pur:description/text()

Note: This works because there is only one item with this id in the payload.
i) The electrical items in the purchase order:
$body/pur:PurchaseOrder/pur:items/pur:item[pur:department="Electrical"]
j) The second electrical item in the purchase order:
$body/pur:PurchaseOrder/pur:items/pur:item[pur:department="Electrical"][2]
k) The last item in the purchase order:
$body/pur:PurchaseOrder/pur:items/pur:item[last()]
Note: We are using the last() function here to determine the last item in the purchase order.
l) The second item in the purchase order:
$body/pur:PurchaseOrder/pur:items/pur:item[position()=2]
Note: We are using the position() function here to determine the second item in the purchase order.
m) The purchase order date in UK date format (i.e. DD/MM/YYYY)
translate('AB/CD/EFGH','EFGH-CD-AB', xs:string($body/pur:PurchaseOrder/pur:date))
Note: We are using the translate function here to convert the date to UK format. The first argument represents the output format (i.e. UK date format), the second argument represents the incoming format (i.e. XML schema date format) and the third argument represents the thing we are translating (i.e. the purchase order date).
Note: The translate function only works on strings and so we need to convert the purchase order date into a string, hence the use of the xs:string function.




No comments:

Post a Comment